Use FallbackDesktopCapturerWrapper in ScreenCapturerWinMagnifier

This is a trivial change to remove duplicate logic, i.e. fallback capturer, from
ScreenCapturerWinMagnifier.

BUG=webrtc:7215

Review-Url: https://codereview.webrtc.org/2704943002
Cr-Commit-Position: refs/heads/master@{#16781}
This commit is contained in:
zijiehe
2017-02-22 13:47:00 -08:00
committed by Commit bot
parent 72694a04e4
commit 3fa87f782e
3 changed files with 29 additions and 51 deletions

View File

@ -13,6 +13,7 @@
#include "webrtc/modules/desktop_capture/desktop_capturer.h"
#include "webrtc/modules/desktop_capture/desktop_capture_options.h"
#include "webrtc/modules/desktop_capture/fallback_desktop_capturer_wrapper.h"
#include "webrtc/modules/desktop_capture/win/screen_capturer_win_directx.h"
#include "webrtc/modules/desktop_capture/win/screen_capturer_win_gdi.h"
#include "webrtc/modules/desktop_capture/win/screen_capturer_win_magnifier.h"
@ -31,7 +32,12 @@ std::unique_ptr<DesktopCapturer> DesktopCapturer::CreateRawScreenCapturer(
}
if (options.allow_use_magnification_api()) {
capturer.reset(new ScreenCapturerWinMagnifier(std::move(capturer)));
// ScreenCapturerWinMagnifier cannot work on Windows XP or earlier, as well
// as 64-bit only Windows, and it may randomly crash on multi-screen
// systems. So we may need to fallback to use original capturer.
capturer.reset(new FallbackDesktopCapturerWrapper(
std::unique_ptr<DesktopCapturer>(new ScreenCapturerWinMagnifier()),
std::move(capturer)));
}
return capturer;

View File

@ -35,10 +35,7 @@ static LPCTSTR kMagnifierWindowName = L"MagnifierWindow";
Atomic32 ScreenCapturerWinMagnifier::tls_index_(TLS_OUT_OF_INDEXES);
ScreenCapturerWinMagnifier::ScreenCapturerWinMagnifier(
std::unique_ptr<DesktopCapturer> fallback_capturer)
: fallback_capturer_(std::move(fallback_capturer)) {}
ScreenCapturerWinMagnifier::ScreenCapturerWinMagnifier() = default;
ScreenCapturerWinMagnifier::~ScreenCapturerWinMagnifier() {
// DestroyWindow must be called before MagUninitialize. magnifier_window_ is
// destroyed automatically when host_window_ is destroyed.
@ -61,9 +58,7 @@ void ScreenCapturerWinMagnifier::Start(Callback* callback) {
callback_ = callback;
if (!InitializeMagnifier()) {
LOG_F(LS_WARNING) << "Switching to fallback screen capturer becuase "
"magnifier initialization failed.";
StartFallbackCapturer();
LOG_F(LS_WARNING) << "Magnifier initialization failed.";
}
}
@ -73,16 +68,10 @@ void ScreenCapturerWinMagnifier::SetSharedMemoryFactory(
}
void ScreenCapturerWinMagnifier::CaptureFrame() {
if (!magnifier_initialized_ ||
!magnifier_capture_succeeded_ ||
GetSystemMetrics(SM_CMONITORS) != 1) {
// Do not try to use the magnifier if it failed before and in multi-screen
// setup (where the API crashes sometimes).
LOG_F(LS_WARNING) << "Switching to the fallback screen capturer because "
"initialization or last capture attempt failed, or "
"execute on multi-screen system.";
StartFallbackCapturer();
fallback_capturer_->CaptureFrame();
RTC_DCHECK(callback_);
if (!magnifier_initialized_) {
LOG_F(LS_WARNING) << "Magnifier initialization failed.";
callback_->OnCaptureResult(Result::ERROR_PERMANENT, nullptr);
return;
}
@ -108,10 +97,8 @@ void ScreenCapturerWinMagnifier::CaptureFrame() {
// CaptureImage may fail in some situations, e.g. windows8 metro mode. So
// defer to the fallback capturer if magnifier capturer did not work.
if (!CaptureImage(rect)) {
LOG_F(LS_WARNING) << "Switching to the fallback screen capturer because "
"last capture attempt failed.";
StartFallbackCapturer();
fallback_capturer_->CaptureFrame();
LOG_F(LS_WARNING) << "Magnifier capturer failed to capture a frame.";
callback_->OnCaptureResult(Result::ERROR_PERMANENT, nullptr);
return;
}
@ -131,17 +118,12 @@ bool ScreenCapturerWinMagnifier::GetSourceList(SourceList* sources) {
}
bool ScreenCapturerWinMagnifier::SelectSource(SourceId id) {
bool valid = IsScreenValid(id, &current_device_key_);
// Set current_screen_id_ even if the fallback capturer is being used, so we
// can switch back to the magnifier when possible.
if (valid)
if (IsScreenValid(id, &current_device_key_)) {
current_screen_id_ = id;
return true;
}
if (fallback_capturer_started_)
fallback_capturer_->SelectSource(id);
return valid;
return false;
}
void ScreenCapturerWinMagnifier::SetExcludedWindow(WindowId excluded_window) {
@ -210,6 +192,15 @@ BOOL ScreenCapturerWinMagnifier::OnMagImageScalingCallback(
// include and function calls instead of a dynamical loaded library.
bool ScreenCapturerWinMagnifier::InitializeMagnifier() {
RTC_DCHECK(!magnifier_initialized_);
if (GetSystemMetrics(SM_CMONITORS) != 1) {
// Do not try to use the magnifier in multi-screen setup (where the API
// crashes sometimes).
LOG_F(LS_WARNING) << "Magnifier capturer cannot work on multi-screen "
"system.";
return false;
}
desktop_dc_ = GetDC(nullptr);
mag_lib_handle_ = LoadLibrary(L"Magnification.dll");
@ -376,14 +367,4 @@ void ScreenCapturerWinMagnifier::CreateCurrentFrameIfNecessary(
}
}
void ScreenCapturerWinMagnifier::StartFallbackCapturer() {
RTC_DCHECK(fallback_capturer_);
if (!fallback_capturer_started_) {
fallback_capturer_started_ = true;
fallback_capturer_->Start(callback_);
fallback_capturer_->SelectSource(current_screen_id_);
}
}
} // namespace webrtc

View File

@ -40,11 +40,7 @@ class DesktopRect;
// be used if that functionality is necessary.
class ScreenCapturerWinMagnifier : public DesktopCapturer {
public:
// |fallback_capturer| will be used to capture the screen if a non-primary
// screen is being captured, or the OS does not support Magnification API, or
// the magnifier capturer fails (e.g. in Windows8 Metro mode).
explicit ScreenCapturerWinMagnifier(
std::unique_ptr<DesktopCapturer> fallback_capturer);
ScreenCapturerWinMagnifier();
~ScreenCapturerWinMagnifier() override;
// Overridden from ScreenCapturer:
@ -103,13 +99,8 @@ class ScreenCapturerWinMagnifier : public DesktopCapturer {
// Makes sure the current frame exists and matches |size|.
void CreateCurrentFrameIfNecessary(const DesktopSize& size);
// Start the fallback capturer and select the screen.
void StartFallbackCapturer();
static Atomic32 tls_index_;
std::unique_ptr<DesktopCapturer> fallback_capturer_;
bool fallback_capturer_started_ = false;
Callback* callback_ = nullptr;
std::unique_ptr<SharedMemoryFactory> shared_memory_factory_;
ScreenId current_screen_id_ = kFullDesktopScreenId;