Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1026)

Side by Side Diff: webrtc/modules/desktop_capture/win/dxgi_duplicator_controller.cc

Issue 2682913002: [DesktopCapture] Detect screen resolution changes in DirectX capturer (Closed)
Patch Set: Resolve review comments Created 3 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 /* 1 /*
2 * Copyright (c) 2016 The WebRTC project authors. All Rights Reserved. 2 * Copyright (c) 2016 The WebRTC project authors. All Rights Reserved.
3 * 3 *
4 * Use of this source code is governed by a BSD-style license 4 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source 5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found 6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may 7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree. 8 * be found in the AUTHORS file in the root of the source tree.
9 */ 9 */
10 10
11 #include "webrtc/modules/desktop_capture/win/dxgi_duplicator_controller.h" 11 #include "webrtc/modules/desktop_capture/win/dxgi_duplicator_controller.h"
12 12
13 #include <windows.h> 13 #include <windows.h>
14 14
15 #include <algorithm> 15 #include <algorithm>
16 #include <string>
16 17
17 #include "webrtc/base/checks.h" 18 #include "webrtc/base/checks.h"
19 #include "webrtc/modules/desktop_capture/desktop_capture_types.h"
20 #include "webrtc/modules/desktop_capture/win/screen_capture_utils.h"
18 21
19 namespace webrtc { 22 namespace webrtc {
20 23
21 DxgiDuplicatorController::Context::Context() {} 24 DxgiDuplicatorController::Context::Context() = default;
22 25
23 DxgiDuplicatorController::Context::~Context() { 26 DxgiDuplicatorController::Context::~Context() {
24 DxgiDuplicatorController::Instance()->Unregister(this); 27 DxgiDuplicatorController::Instance()->Unregister(this);
25 } 28 }
26 29
30 void DxgiDuplicatorController::Context::Reset() {
31 identity_ = 0;
32 }
33
27 // static 34 // static
28 DxgiDuplicatorController* DxgiDuplicatorController::Instance() { 35 DxgiDuplicatorController* DxgiDuplicatorController::Instance() {
29 // The static instance won't be deleted to ensure it can be used by other 36 // The static instance won't be deleted to ensure it can be used by other
30 // threads even during program exiting. 37 // threads even during program exiting.
31 static DxgiDuplicatorController* instance = new DxgiDuplicatorController(); 38 static DxgiDuplicatorController* instance = new DxgiDuplicatorController();
32 return instance; 39 return instance;
33 } 40 }
34 41
35 DxgiDuplicatorController::DxgiDuplicatorController() = default; 42 DxgiDuplicatorController::DxgiDuplicatorController() = default;
36 43
37 DxgiDuplicatorController::~DxgiDuplicatorController() { 44 DxgiDuplicatorController::~DxgiDuplicatorController() {
38 rtc::CritScope lock(&lock_); 45 rtc::CritScope lock(&lock_);
39 Deinitialize(); 46 Deinitialize();
40 } 47 }
41 48
42 bool DxgiDuplicatorController::IsSupported() { 49 bool DxgiDuplicatorController::IsSupported() {
43 rtc::CritScope lock(&lock_); 50 rtc::CritScope lock(&lock_);
44 return Initialize(); 51 return Initialize();
45 } 52 }
46 53
54 void DxgiDuplicatorController::Reset() {
55 rtc::CritScope lock(&lock_);
56 Deinitialize();
57 }
58
47 bool DxgiDuplicatorController::RetrieveD3dInfo(D3dInfo* info) { 59 bool DxgiDuplicatorController::RetrieveD3dInfo(D3dInfo* info) {
48 rtc::CritScope lock(&lock_); 60 rtc::CritScope lock(&lock_);
49 if (!Initialize()) { 61 if (!Initialize()) {
50 return false; 62 return false;
51 } 63 }
52 *info = d3d_info_; 64 *info = d3d_info_;
53 return true; 65 return true;
54 } 66 }
55 67
56 DesktopVector DxgiDuplicatorController::dpi() { 68 DesktopVector DxgiDuplicatorController::dpi() {
(...skipping 118 matching lines...) Expand 10 before | Expand all | Expand 10 after
175 ReleaseDC(nullptr, hdc); 187 ReleaseDC(nullptr, hdc);
176 } 188 }
177 189
178 identity_++; 190 identity_++;
179 return true; 191 return true;
180 } 192 }
181 193
182 void DxgiDuplicatorController::Deinitialize() { 194 void DxgiDuplicatorController::Deinitialize() {
183 desktop_rect_ = DesktopRect(); 195 desktop_rect_ = DesktopRect();
184 duplicators_.clear(); 196 duplicators_.clear();
197 resolution_change_detector_.Reset();
185 } 198 }
186 199
187 bool DxgiDuplicatorController::ContextExpired( 200 bool DxgiDuplicatorController::ContextExpired(
188 const Context* const context) const { 201 const Context* const context) const {
189 return context->identity_ != identity_ || 202 return context->identity_ != identity_ ||
190 context->contexts_.size() != duplicators_.size(); 203 context->contexts_.size() != duplicators_.size();
191 } 204 }
192 205
193 void DxgiDuplicatorController::Setup(Context* context) { 206 void DxgiDuplicatorController::Setup(Context* context) {
194 if (ContextExpired(context)) { 207 if (ContextExpired(context)) {
(...skipping 17 matching lines...) Expand all
212 RTC_DCHECK_GE(monitor_id, 0); 225 RTC_DCHECK_GE(monitor_id, 0);
213 return DoDuplicate(context, monitor_id, target); 226 return DoDuplicate(context, monitor_id, target);
214 } 227 }
215 228
216 bool DxgiDuplicatorController::DoDuplicate(Context* context, 229 bool DxgiDuplicatorController::DoDuplicate(Context* context,
217 int monitor_id, 230 int monitor_id,
218 SharedDesktopFrame* target) { 231 SharedDesktopFrame* target) {
219 RTC_DCHECK(target); 232 RTC_DCHECK(target);
220 target->mutable_updated_region()->Clear(); 233 target->mutable_updated_region()->Clear();
221 rtc::CritScope lock(&lock_); 234 rtc::CritScope lock(&lock_);
235 if (DoDuplicateUnlocked(context, monitor_id, target)) {
236 return true;
237 }
238 Deinitialize();
239 return false;
240 }
241
242 bool DxgiDuplicatorController::DoDuplicateUnlocked(Context* context,
243 int monitor_id,
244 SharedDesktopFrame* target) {
222 if (!Initialize()) { 245 if (!Initialize()) {
223 // Cannot initialize COM components now, display mode may be changing. 246 // Cannot initialize COM components now, display mode may be changing.
224 return false; 247 return false;
225 } 248 }
226 249
250 if (resolution_change_detector_.IsChanged(
251 GetScreenRect(kFullDesktopScreenId, std::wstring()).size())) {
252 // Resolution of entire screen has been changed, which usually means a new
253 // monitor has been attached or one has been removed. The simplest way is to
254 // Deinitialize() and returns false to indicate downstream components.
255 return false;
256 }
257
227 Setup(context); 258 Setup(context);
228 if (monitor_id < 0) { 259 if (monitor_id < 0) {
229 // Capture entire screen. 260 // Capture entire screen.
230 for (size_t i = 0; i < duplicators_.size(); i++) { 261 for (size_t i = 0; i < duplicators_.size(); i++) {
231 if (!duplicators_[i].Duplicate(&context->contexts_[i], target)) { 262 if (!duplicators_[i].Duplicate(&context->contexts_[i], target)) {
232 Deinitialize();
233 return false; 263 return false;
234 } 264 }
235 } 265 }
236 target->set_dpi(dpi()); 266 target->set_dpi(dpi());
237 return true; 267 return true;
238 } 268 }
239 269
240 // Capture one monitor. 270 // Capture one monitor.
241 for (size_t i = 0; i < duplicators_.size() && i < context->contexts_.size(); 271 for (size_t i = 0; i < duplicators_.size() && i < context->contexts_.size();
242 i++) { 272 i++) {
243 if (monitor_id >= duplicators_[i].screen_count()) { 273 if (monitor_id >= duplicators_[i].screen_count()) {
244 monitor_id -= duplicators_[i].screen_count(); 274 monitor_id -= duplicators_[i].screen_count();
245 } else { 275 } else {
246 if (duplicators_[i].DuplicateMonitor(&context->contexts_[i], monitor_id, 276 if (duplicators_[i].DuplicateMonitor(&context->contexts_[i], monitor_id,
247 target)) { 277 target)) {
248 target->set_dpi(dpi()); 278 target->set_dpi(dpi());
249 return true; 279 return true;
250 } 280 }
251 Deinitialize();
252 return false; 281 return false;
253 } 282 }
254 } 283 }
255 // id >= ScreenCount(). This is a user error, so we do not need to 284 // id >= ScreenCount(). This is a user error, so we do not need to
256 // deinitialize. 285 // deinitialize.
257 return false; 286 return false;
258 } 287 }
259 288
260 } // namespace webrtc 289 } // namespace webrtc
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698