Cleanup shared memory handling in DesktopCapturer interface.
Previously shared memory buffers for DesktopCapturer were created using DesktopCapturer::Callback::CreateSharedBuffer(). That made it difficult to proxy DesktopCapturer interface from one thread to another. This CL adds SharedBufferFactory interface that's allowed to be called on a background thread. This also simplifies clients that don't need to use shared memory, as they no longer need to override CreateSharedBuffer(). Review URL: https://codereview.webrtc.org/1678073003 Cr-Commit-Position: refs/heads/master@{#11543}
This commit is contained in:
parent
c815c60f8a
commit
cc9669c6b8
@ -31,6 +31,11 @@ void CroppingWindowCapturer::Start(DesktopCapturer::Callback* callback) {
|
||||
window_capturer_->Start(callback);
|
||||
}
|
||||
|
||||
void CroppingWindowCapturer::SetSharedMemoryFactory(
|
||||
rtc::scoped_ptr<SharedMemoryFactory> shared_memory_factory) {
|
||||
window_capturer_->SetSharedMemoryFactory(std::move(shared_memory_factory));
|
||||
}
|
||||
|
||||
void CroppingWindowCapturer::Capture(const DesktopRegion& region) {
|
||||
if (ShouldUseScreenCapturer()) {
|
||||
if (!screen_capturer_.get()) {
|
||||
@ -69,10 +74,6 @@ bool CroppingWindowCapturer::BringSelectedWindowToFront() {
|
||||
return window_capturer_->BringSelectedWindowToFront();
|
||||
}
|
||||
|
||||
SharedMemory* CroppingWindowCapturer::CreateSharedMemory(size_t size) {
|
||||
return callback_->CreateSharedMemory(size);
|
||||
}
|
||||
|
||||
void CroppingWindowCapturer::OnCaptureCompleted(DesktopFrame* frame) {
|
||||
rtc::scoped_ptr<DesktopFrame> screen_frame(frame);
|
||||
|
||||
|
||||
@ -29,6 +29,8 @@ class CroppingWindowCapturer : public WindowCapturer,
|
||||
|
||||
// DesktopCapturer implementation.
|
||||
void Start(DesktopCapturer::Callback* callback) override;
|
||||
void SetSharedMemoryFactory(
|
||||
rtc::scoped_ptr<SharedMemoryFactory> shared_memory_factory) override;
|
||||
void Capture(const DesktopRegion& region) override;
|
||||
void SetExcludedWindow(WindowId window) override;
|
||||
|
||||
@ -39,7 +41,6 @@ class CroppingWindowCapturer : public WindowCapturer,
|
||||
|
||||
// DesktopCapturer::Callback implementation, passed to |screen_capturer_| to
|
||||
// intercept the capture result.
|
||||
SharedMemory* CreateSharedMemory(size_t size) override;
|
||||
void OnCaptureCompleted(DesktopFrame* frame) override;
|
||||
|
||||
protected:
|
||||
|
||||
@ -136,6 +136,11 @@ void DesktopAndCursorComposer::Start(DesktopCapturer::Callback* callback) {
|
||||
desktop_capturer_->Start(this);
|
||||
}
|
||||
|
||||
void DesktopAndCursorComposer::SetSharedMemoryFactory(
|
||||
rtc::scoped_ptr<SharedMemoryFactory> shared_memory_factory) {
|
||||
desktop_capturer_->SetSharedMemoryFactory(std::move(shared_memory_factory));
|
||||
}
|
||||
|
||||
void DesktopAndCursorComposer::Capture(const DesktopRegion& region) {
|
||||
if (mouse_monitor_.get())
|
||||
mouse_monitor_->Capture();
|
||||
@ -146,10 +151,6 @@ void DesktopAndCursorComposer::SetExcludedWindow(WindowId window) {
|
||||
desktop_capturer_->SetExcludedWindow(window);
|
||||
}
|
||||
|
||||
SharedMemory* DesktopAndCursorComposer::CreateSharedMemory(size_t size) {
|
||||
return callback_->CreateSharedMemory(size);
|
||||
}
|
||||
|
||||
void DesktopAndCursorComposer::OnCaptureCompleted(DesktopFrame* frame) {
|
||||
if (frame && cursor_.get() && cursor_state_ == MouseCursorMonitor::INSIDE) {
|
||||
DesktopFrameWithCursor* frame_with_cursor =
|
||||
|
||||
@ -20,8 +20,8 @@ namespace webrtc {
|
||||
// A wrapper for DesktopCapturer that also captures mouse using specified
|
||||
// MouseCursorMonitor and renders it on the generated streams.
|
||||
class DesktopAndCursorComposer : public DesktopCapturer,
|
||||
public DesktopCapturer::Callback,
|
||||
public MouseCursorMonitor::Callback {
|
||||
public DesktopCapturer::Callback,
|
||||
public MouseCursorMonitor::Callback {
|
||||
public:
|
||||
// Creates a new blender that captures mouse cursor using |mouse_monitor| and
|
||||
// renders it into the frames generated by |desktop_capturer|. If
|
||||
@ -33,12 +33,13 @@ class DesktopAndCursorComposer : public DesktopCapturer,
|
||||
|
||||
// DesktopCapturer interface.
|
||||
void Start(DesktopCapturer::Callback* callback) override;
|
||||
void SetSharedMemoryFactory(
|
||||
rtc::scoped_ptr<SharedMemoryFactory> shared_memory_factory) override;
|
||||
void Capture(const DesktopRegion& region) override;
|
||||
void SetExcludedWindow(WindowId window) override;
|
||||
|
||||
private:
|
||||
// DesktopCapturer::Callback interface.
|
||||
SharedMemory* CreateSharedMemory(size_t size) override;
|
||||
void OnCaptureCompleted(DesktopFrame* frame) override;
|
||||
|
||||
// MouseCursorMonitor::Callback interface.
|
||||
|
||||
@ -168,8 +168,6 @@ class DesktopAndCursorComposerTest : public testing::Test,
|
||||
}
|
||||
|
||||
// DesktopCapturer::Callback interface
|
||||
SharedMemory* CreateSharedMemory(size_t size) override { return NULL; }
|
||||
|
||||
void OnCaptureCompleted(DesktopFrame* frame) override { frame_.reset(frame); }
|
||||
|
||||
protected:
|
||||
|
||||
@ -13,13 +13,14 @@
|
||||
|
||||
#include <stddef.h>
|
||||
|
||||
#include "webrtc/base/scoped_ptr.h"
|
||||
#include "webrtc/modules/desktop_capture/desktop_capture_types.h"
|
||||
#include "webrtc/modules/desktop_capture/shared_memory.h"
|
||||
|
||||
namespace webrtc {
|
||||
|
||||
class DesktopFrame;
|
||||
class DesktopRegion;
|
||||
class SharedMemory;
|
||||
|
||||
// Abstract interface for screen and window capturers.
|
||||
class DesktopCapturer {
|
||||
@ -27,10 +28,10 @@ class DesktopCapturer {
|
||||
// Interface that must be implemented by the DesktopCapturer consumers.
|
||||
class Callback {
|
||||
public:
|
||||
// Creates a new shared memory buffer for a frame create by the capturer.
|
||||
// Should return null shared memory is not used for captured frames (in that
|
||||
// case the capturer will allocate memory on the heap).
|
||||
virtual SharedMemory* CreateSharedMemory(size_t size) = 0;
|
||||
// Deprecated.
|
||||
// TODO(sergeyu): Remove this method once all references to it are removed
|
||||
// from chromium.
|
||||
virtual SharedMemory* CreateSharedMemory(size_t size) { return nullptr; }
|
||||
|
||||
// Called after a frame has been captured. Handler must take ownership of
|
||||
// |frame|. If capture has failed for any reason |frame| is set to NULL
|
||||
@ -47,6 +48,13 @@ class DesktopCapturer {
|
||||
// valid until capturer is destroyed.
|
||||
virtual void Start(Callback* callback) = 0;
|
||||
|
||||
// Sets SharedMemoryFactory that will be used to create buffers for the
|
||||
// captured frames. The factory can be invoked on a thread other than the one
|
||||
// where Capture() is called. It will be destroyed on the same thread. Shared
|
||||
// memory is currently supported only by some DesktopCapturer implementations.
|
||||
virtual void SetSharedMemoryFactory(
|
||||
rtc::scoped_ptr<SharedMemoryFactory> shared_memory_factory) {}
|
||||
|
||||
// Captures next frame. |region| specifies region of the capture target that
|
||||
// should be fresh in the resulting frame. The frame may also include fresh
|
||||
// data for areas outside |region|. In that case capturer will include these
|
||||
|
||||
@ -77,15 +77,38 @@ DesktopFrame* BasicDesktopFrame::CopyOf(const DesktopFrame& frame) {
|
||||
return result;
|
||||
}
|
||||
|
||||
// static
|
||||
rtc::scoped_ptr<DesktopFrame> SharedMemoryDesktopFrame::Create(
|
||||
DesktopSize size,
|
||||
SharedMemoryFactory* shared_memory_factory) {
|
||||
size_t buffer_size =
|
||||
size.width() * size.height() * DesktopFrame::kBytesPerPixel;
|
||||
rtc::scoped_ptr<SharedMemory> shared_memory;
|
||||
shared_memory = shared_memory_factory->CreateSharedMemory(buffer_size);
|
||||
if (!shared_memory)
|
||||
return nullptr;
|
||||
|
||||
return rtc_make_scoped_ptr(new SharedMemoryDesktopFrame(
|
||||
size, size.width() * DesktopFrame::kBytesPerPixel,
|
||||
std::move(shared_memory)));
|
||||
}
|
||||
|
||||
SharedMemoryDesktopFrame::SharedMemoryDesktopFrame(DesktopSize size,
|
||||
int stride,
|
||||
SharedMemory* shared_memory)
|
||||
: DesktopFrame(size,
|
||||
stride,
|
||||
reinterpret_cast<uint8_t*>(shared_memory->data()),
|
||||
shared_memory) {}
|
||||
|
||||
SharedMemoryDesktopFrame::SharedMemoryDesktopFrame(
|
||||
DesktopSize size,
|
||||
int stride,
|
||||
SharedMemory* shared_memory)
|
||||
: DesktopFrame(size, stride,
|
||||
rtc::scoped_ptr<SharedMemory> shared_memory)
|
||||
: DesktopFrame(size,
|
||||
stride,
|
||||
reinterpret_cast<uint8_t*>(shared_memory->data()),
|
||||
shared_memory) {
|
||||
}
|
||||
shared_memory.release()) {}
|
||||
|
||||
SharedMemoryDesktopFrame::~SharedMemoryDesktopFrame() {
|
||||
delete shared_memory_;
|
||||
|
||||
@ -110,10 +110,18 @@ class BasicDesktopFrame : public DesktopFrame {
|
||||
// A DesktopFrame that stores data in shared memory.
|
||||
class SharedMemoryDesktopFrame : public DesktopFrame {
|
||||
public:
|
||||
static rtc::scoped_ptr<DesktopFrame> Create(
|
||||
DesktopSize size,
|
||||
SharedMemoryFactory* shared_memory_factory);
|
||||
|
||||
// Takes ownership of |shared_memory|.
|
||||
// TODO(sergeyu): Remove this constructor and keep the second one.
|
||||
SharedMemoryDesktopFrame(DesktopSize size,
|
||||
int stride,
|
||||
SharedMemory* shared_memory);
|
||||
SharedMemoryDesktopFrame(DesktopSize size,
|
||||
int stride,
|
||||
rtc::scoped_ptr<SharedMemory> shared_memory);
|
||||
~SharedMemoryDesktopFrame() override;
|
||||
|
||||
private:
|
||||
|
||||
@ -10,6 +10,8 @@
|
||||
|
||||
#include "webrtc/modules/desktop_capture/desktop_frame_win.h"
|
||||
|
||||
#include <utility>
|
||||
|
||||
#include "webrtc/system_wrappers/include/logging.h"
|
||||
|
||||
namespace webrtc {
|
||||
@ -17,22 +19,23 @@ namespace webrtc {
|
||||
DesktopFrameWin::DesktopFrameWin(DesktopSize size,
|
||||
int stride,
|
||||
uint8_t* data,
|
||||
SharedMemory* shared_memory,
|
||||
rtc::scoped_ptr<SharedMemory> shared_memory,
|
||||
HBITMAP bitmap)
|
||||
: DesktopFrame(size, stride, data, shared_memory),
|
||||
: DesktopFrame(size, stride, data, shared_memory.get()),
|
||||
bitmap_(bitmap),
|
||||
owned_shared_memory_(shared_memory_) {
|
||||
}
|
||||
owned_shared_memory_(std::move(shared_memory)) {}
|
||||
|
||||
DesktopFrameWin::~DesktopFrameWin() {
|
||||
DeleteObject(bitmap_);
|
||||
}
|
||||
|
||||
// static
|
||||
DesktopFrameWin* DesktopFrameWin::Create(DesktopSize size,
|
||||
SharedMemory* shared_memory,
|
||||
HDC hdc) {
|
||||
DesktopFrameWin* DesktopFrameWin::Create(
|
||||
DesktopSize size,
|
||||
SharedMemoryFactory* shared_memory_factory,
|
||||
HDC hdc) {
|
||||
int bytes_per_row = size.width() * kBytesPerPixel;
|
||||
int buffer_size = bytes_per_row * size.height();
|
||||
|
||||
// Describe a device independent bitmap (DIB) that is the size of the desktop.
|
||||
BITMAPINFO bmi = {};
|
||||
@ -43,21 +46,24 @@ DesktopFrameWin* DesktopFrameWin::Create(DesktopSize size,
|
||||
bmi.bmiHeader.biSize = sizeof(bmi.bmiHeader);
|
||||
bmi.bmiHeader.biSizeImage = bytes_per_row * size.height();
|
||||
|
||||
HANDLE section_handle = NULL;
|
||||
if (shared_memory)
|
||||
section_handle = shared_memory->handle();
|
||||
void* data = NULL;
|
||||
rtc::scoped_ptr<SharedMemory> shared_memory;
|
||||
HANDLE section_handle = nullptr;
|
||||
if (shared_memory_factory) {
|
||||
shared_memory = shared_memory_factory->CreateSharedMemory(buffer_size);
|
||||
if (shared_memory)
|
||||
section_handle = shared_memory->handle();
|
||||
}
|
||||
void* data = nullptr;
|
||||
HBITMAP bitmap = CreateDIBSection(hdc, &bmi, DIB_RGB_COLORS, &data,
|
||||
section_handle, 0);
|
||||
if (!bitmap) {
|
||||
LOG(LS_WARNING) << "Failed to allocate new window frame " << GetLastError();
|
||||
delete shared_memory;
|
||||
return NULL;
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
return new DesktopFrameWin(size, bytes_per_row,
|
||||
reinterpret_cast<uint8_t*>(data),
|
||||
shared_memory, bitmap);
|
||||
std::move(shared_memory), bitmap);
|
||||
}
|
||||
|
||||
} // namespace webrtc
|
||||
|
||||
@ -25,7 +25,7 @@ class DesktopFrameWin : public DesktopFrame {
|
||||
public:
|
||||
virtual ~DesktopFrameWin();
|
||||
static DesktopFrameWin* Create(DesktopSize size,
|
||||
SharedMemory* shared_memory,
|
||||
SharedMemoryFactory* shared_memory_factory,
|
||||
HDC hdc);
|
||||
|
||||
HBITMAP bitmap() { return bitmap_; }
|
||||
@ -34,7 +34,7 @@ class DesktopFrameWin : public DesktopFrame {
|
||||
DesktopFrameWin(DesktopSize size,
|
||||
int stride,
|
||||
uint8_t* data,
|
||||
SharedMemory* shared_memory,
|
||||
rtc::scoped_ptr<SharedMemory> shared_memory,
|
||||
HBITMAP bitmap);
|
||||
|
||||
HBITMAP bitmap_;
|
||||
|
||||
@ -80,10 +80,6 @@ TEST_F(ScreenCapturerMacTest, Capture) {
|
||||
.WillOnce(Invoke(this, &ScreenCapturerMacTest::CaptureDoneCallback1))
|
||||
.WillOnce(Invoke(this, &ScreenCapturerMacTest::CaptureDoneCallback2));
|
||||
|
||||
EXPECT_CALL(callback_, CreateSharedMemory(_))
|
||||
.Times(AnyNumber())
|
||||
.WillRepeatedly(Return(static_cast<SharedMemory*>(NULL)));
|
||||
|
||||
SCOPED_TRACE("");
|
||||
capturer_->Start(&callback_);
|
||||
|
||||
|
||||
@ -35,7 +35,6 @@ class MockScreenCapturerCallback : public ScreenCapturer::Callback {
|
||||
MockScreenCapturerCallback() {}
|
||||
virtual ~MockScreenCapturerCallback() {}
|
||||
|
||||
MOCK_METHOD1(CreateSharedMemory, SharedMemory*(size_t));
|
||||
MOCK_METHOD1(OnCaptureCompleted, void(DesktopFrame*));
|
||||
|
||||
private:
|
||||
|
||||
@ -28,8 +28,6 @@ namespace webrtc {
|
||||
|
||||
class ScreenCapturerTest : public testing::Test {
|
||||
public:
|
||||
SharedMemory* CreateSharedMemory(size_t size);
|
||||
|
||||
void SetUp() override {
|
||||
capturer_.reset(
|
||||
ScreenCapturer::Create(DesktopCaptureOptions::CreateDefault()));
|
||||
@ -54,9 +52,18 @@ class FakeSharedMemory : public SharedMemory {
|
||||
RTC_DISALLOW_COPY_AND_ASSIGN(FakeSharedMemory);
|
||||
};
|
||||
|
||||
SharedMemory* ScreenCapturerTest::CreateSharedMemory(size_t size) {
|
||||
return new FakeSharedMemory(new char[size], size);
|
||||
}
|
||||
class FakeSharedMemoryFactory : public SharedMemoryFactory {
|
||||
public:
|
||||
FakeSharedMemoryFactory() {}
|
||||
~FakeSharedMemoryFactory() override {}
|
||||
|
||||
rtc::scoped_ptr<SharedMemory> CreateSharedMemory(size_t size) override {
|
||||
return rtc_make_scoped_ptr(new FakeSharedMemory(new char[size], size));
|
||||
}
|
||||
|
||||
private:
|
||||
RTC_DISALLOW_COPY_AND_ASSIGN(FakeSharedMemoryFactory);
|
||||
};
|
||||
|
||||
TEST_F(ScreenCapturerTest, GetScreenListAndSelectScreen) {
|
||||
webrtc::ScreenCapturer::ScreenList screens;
|
||||
@ -77,10 +84,6 @@ TEST_F(ScreenCapturerTest, Capture) {
|
||||
EXPECT_CALL(callback_, OnCaptureCompleted(_))
|
||||
.WillOnce(SaveArg<0>(&frame));
|
||||
|
||||
EXPECT_CALL(callback_, CreateSharedMemory(_))
|
||||
.Times(AnyNumber())
|
||||
.WillRepeatedly(Return(static_cast<SharedMemory*>(NULL)));
|
||||
|
||||
capturer_->Start(&callback_);
|
||||
capturer_->Capture(DesktopRegion());
|
||||
|
||||
@ -109,11 +112,9 @@ TEST_F(ScreenCapturerTest, UseSharedBuffers) {
|
||||
EXPECT_CALL(callback_, OnCaptureCompleted(_))
|
||||
.WillOnce(SaveArg<0>(&frame));
|
||||
|
||||
EXPECT_CALL(callback_, CreateSharedMemory(_))
|
||||
.Times(AnyNumber())
|
||||
.WillRepeatedly(Invoke(this, &ScreenCapturerTest::CreateSharedMemory));
|
||||
|
||||
capturer_->Start(&callback_);
|
||||
capturer_->SetSharedMemoryFactory(
|
||||
rtc_make_scoped_ptr(new FakeSharedMemoryFactory()));
|
||||
capturer_->Capture(DesktopRegion());
|
||||
|
||||
ASSERT_TRUE(frame);
|
||||
|
||||
@ -17,6 +17,7 @@
|
||||
#include <windows.h>
|
||||
#endif
|
||||
|
||||
#include "webrtc/base/scoped_ptr.h"
|
||||
#include "webrtc/base/constructormagic.h"
|
||||
#include "webrtc/typedefs.h"
|
||||
|
||||
@ -26,8 +27,8 @@ namespace webrtc {
|
||||
// parameters of the buffer, but doesn't have any logic to allocate or destroy
|
||||
// the actual buffer. DesktopCapturer consumers that need to use shared memory
|
||||
// for video frames must extend this class with creation and destruction logic
|
||||
// specific for the target platform and then implement
|
||||
// DesktopCapturer::Delegate::CreateSharedMemory() as appropriate.
|
||||
// specific for the target platform and then call
|
||||
// DesktopCapturer::SetSharedMemoryFactory().
|
||||
class SharedMemory {
|
||||
public:
|
||||
#if defined(WEBRTC_WIN)
|
||||
@ -62,6 +63,18 @@ class SharedMemory {
|
||||
RTC_DISALLOW_COPY_AND_ASSIGN(SharedMemory);
|
||||
};
|
||||
|
||||
// Interface used to create SharedMemory instances.
|
||||
class SharedMemoryFactory {
|
||||
public:
|
||||
SharedMemoryFactory() {}
|
||||
virtual ~SharedMemoryFactory() {}
|
||||
|
||||
virtual rtc::scoped_ptr<SharedMemory> CreateSharedMemory(size_t size) = 0;
|
||||
|
||||
private:
|
||||
RTC_DISALLOW_COPY_AND_ASSIGN(SharedMemoryFactory);
|
||||
};
|
||||
|
||||
} // namespace webrtc
|
||||
|
||||
#endif // WEBRTC_MODULES_DESKTOP_CAPTURE_SHARED_MEMORY_H_
|
||||
|
||||
@ -12,6 +12,8 @@
|
||||
|
||||
#include <assert.h>
|
||||
|
||||
#include <utility>
|
||||
|
||||
#include "webrtc/modules/desktop_capture/desktop_capture_options.h"
|
||||
#include "webrtc/modules/desktop_capture/desktop_frame.h"
|
||||
#include "webrtc/modules/desktop_capture/desktop_frame_win.h"
|
||||
@ -34,6 +36,22 @@ const UINT DWM_EC_ENABLECOMPOSITION = 1;
|
||||
|
||||
const wchar_t kDwmapiLibraryName[] = L"dwmapi.dll";
|
||||
|
||||
// SharedMemoryFactory that creates SharedMemory using the deprecated
|
||||
// DesktopCapturer::Callback::CreateSharedMemory().
|
||||
class CallbackSharedMemoryFactory : public SharedMemoryFactory {
|
||||
public:
|
||||
CallbackSharedMemoryFactory(DesktopCapturer::Callback* callback)
|
||||
: callback_(callback) {}
|
||||
~CallbackSharedMemoryFactory() override {}
|
||||
|
||||
rtc::scoped_ptr<SharedMemory> CreateSharedMemory(size_t size) override {
|
||||
return rtc_make_scoped_ptr(callback_->CreateSharedMemory(size));
|
||||
}
|
||||
|
||||
private:
|
||||
DesktopCapturer::Callback* callback_;
|
||||
};
|
||||
|
||||
} // namespace
|
||||
|
||||
ScreenCapturerWinGdi::ScreenCapturerWinGdi(const DesktopCaptureOptions& options)
|
||||
@ -70,6 +88,11 @@ ScreenCapturerWinGdi::~ScreenCapturerWinGdi() {
|
||||
FreeLibrary(dwmapi_library_);
|
||||
}
|
||||
|
||||
void ScreenCapturerWinGdi::SetSharedMemoryFactory(
|
||||
rtc::scoped_ptr<SharedMemoryFactory> shared_memory_factory) {
|
||||
shared_memory_factory_ = std::move(shared_memory_factory);
|
||||
}
|
||||
|
||||
void ScreenCapturerWinGdi::Capture(const DesktopRegion& region) {
|
||||
TickTime capture_start_time = TickTime::Now();
|
||||
|
||||
@ -148,6 +171,8 @@ void ScreenCapturerWinGdi::Start(Callback* callback) {
|
||||
assert(callback);
|
||||
|
||||
callback_ = callback;
|
||||
if (!shared_memory_factory_)
|
||||
shared_memory_factory_.reset(new CallbackSharedMemoryFactory(callback));
|
||||
|
||||
// Vote to disable Aero composited desktop effects while capturing. Windows
|
||||
// will restore Aero automatically if the process exits. This has no effect
|
||||
@ -237,12 +262,8 @@ bool ScreenCapturerWinGdi::CaptureImage() {
|
||||
assert(desktop_dc_ != NULL);
|
||||
assert(memory_dc_ != NULL);
|
||||
|
||||
size_t buffer_size = size.width() * size.height() *
|
||||
DesktopFrame::kBytesPerPixel;
|
||||
SharedMemory* shared_memory = callback_->CreateSharedMemory(buffer_size);
|
||||
|
||||
rtc::scoped_ptr<DesktopFrame> buffer(
|
||||
DesktopFrameWin::Create(size, shared_memory, desktop_dc_));
|
||||
rtc::scoped_ptr<DesktopFrame> buffer(DesktopFrameWin::Create(
|
||||
size, shared_memory_factory_.get(), desktop_dc_));
|
||||
if (!buffer.get())
|
||||
return false;
|
||||
queue_.ReplaceCurrentFrame(buffer.release());
|
||||
|
||||
@ -34,6 +34,8 @@ class ScreenCapturerWinGdi : public ScreenCapturer {
|
||||
|
||||
// Overridden from ScreenCapturer:
|
||||
void Start(Callback* callback) override;
|
||||
void SetSharedMemoryFactory(
|
||||
rtc::scoped_ptr<SharedMemoryFactory> shared_memory_factory) override;
|
||||
void Capture(const DesktopRegion& region) override;
|
||||
bool GetScreenList(ScreenList* screens) override;
|
||||
bool SelectScreen(ScreenId id) override;
|
||||
@ -52,6 +54,7 @@ class ScreenCapturerWinGdi : public ScreenCapturer {
|
||||
void CaptureCursor();
|
||||
|
||||
Callback* callback_;
|
||||
rtc::scoped_ptr<SharedMemoryFactory> shared_memory_factory_;
|
||||
ScreenId current_screen_id_;
|
||||
std::wstring current_device_key_;
|
||||
|
||||
|
||||
@ -81,6 +81,11 @@ void ScreenCapturerWinMagnifier::Start(Callback* callback) {
|
||||
InitializeMagnifier();
|
||||
}
|
||||
|
||||
void ScreenCapturerWinMagnifier::SetSharedMemoryFactory(
|
||||
rtc::scoped_ptr<SharedMemoryFactory> shared_memory_factory) {
|
||||
shared_memory_factory_ = std::move(shared_memory_factory);
|
||||
}
|
||||
|
||||
void ScreenCapturerWinMagnifier::Capture(const DesktopRegion& region) {
|
||||
TickTime capture_start_time = TickTime::Now();
|
||||
|
||||
@ -422,18 +427,12 @@ void ScreenCapturerWinMagnifier::CreateCurrentFrameIfNecessary(
|
||||
// Note that we can't reallocate other buffers at this point, since the caller
|
||||
// may still be reading from them.
|
||||
if (!queue_.current_frame() || !queue_.current_frame()->size().equals(size)) {
|
||||
size_t buffer_size =
|
||||
size.width() * size.height() * DesktopFrame::kBytesPerPixel;
|
||||
SharedMemory* shared_memory = callback_->CreateSharedMemory(buffer_size);
|
||||
|
||||
rtc::scoped_ptr<DesktopFrame> buffer;
|
||||
if (shared_memory) {
|
||||
buffer.reset(new SharedMemoryDesktopFrame(
|
||||
size, size.width() * DesktopFrame::kBytesPerPixel, shared_memory));
|
||||
} else {
|
||||
buffer.reset(new BasicDesktopFrame(size));
|
||||
}
|
||||
queue_.ReplaceCurrentFrame(buffer.release());
|
||||
rtc::scoped_ptr<DesktopFrame> frame =
|
||||
shared_memory_factory_
|
||||
? SharedMemoryDesktopFrame::Create(size,
|
||||
shared_memory_factory_.get())
|
||||
: rtc::scoped_ptr<DesktopFrame>(new BasicDesktopFrame(size));
|
||||
queue_.ReplaceCurrentFrame(frame.release());
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -44,6 +44,8 @@ class ScreenCapturerWinMagnifier : public ScreenCapturer {
|
||||
|
||||
// Overridden from ScreenCapturer:
|
||||
void Start(Callback* callback) override;
|
||||
void SetSharedMemoryFactory(
|
||||
rtc::scoped_ptr<SharedMemoryFactory> shared_memory_factory) override;
|
||||
void Capture(const DesktopRegion& region) override;
|
||||
bool GetScreenList(ScreenList* screens) override;
|
||||
bool SelectScreen(ScreenId id) override;
|
||||
@ -104,6 +106,7 @@ class ScreenCapturerWinMagnifier : public ScreenCapturer {
|
||||
rtc::scoped_ptr<ScreenCapturer> fallback_capturer_;
|
||||
bool fallback_capturer_started_;
|
||||
Callback* callback_;
|
||||
rtc::scoped_ptr<SharedMemoryFactory> shared_memory_factory_;
|
||||
ScreenId current_screen_id_;
|
||||
std::wstring current_device_key_;
|
||||
HWND excluded_window_;
|
||||
|
||||
@ -30,8 +30,6 @@ class WindowCapturerTest : public testing::Test,
|
||||
void TearDown() override {}
|
||||
|
||||
// DesktopCapturer::Callback interface
|
||||
SharedMemory* CreateSharedMemory(size_t size) override { return NULL; }
|
||||
|
||||
void OnCaptureCompleted(DesktopFrame* frame) override { frame_.reset(frame); }
|
||||
|
||||
protected:
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user