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

Side by Side Diff: chrome/views/window/window_win.cc

Issue 78002: Reorganize fullscreen mode handling. Now nearly everything is in WindowWin. ... (Closed) Base URL: svn://chrome-svn/chrome/trunk/src/
Patch Set: '' Created 11 years, 8 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 | Annotate | Revision Log
« no previous file with comments | « chrome/views/window/window_win.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "chrome/views/window/window_win.h" 5 #include "chrome/views/window/window_win.h"
6 6
7 #include <shellapi.h> 7 #include <shellapi.h>
8 8
9 #include "base/win_util.h" 9 #include "base/win_util.h"
10 #include "chrome/app/chrome_dll_resource.h" 10 #include "chrome/app/chrome_dll_resource.h"
11 #include "chrome/common/gfx/chrome_canvas.h" 11 #include "chrome/common/gfx/chrome_canvas.h"
12 #include "chrome/common/gfx/chrome_font.h" 12 #include "chrome/common/gfx/chrome_font.h"
13 #include "chrome/common/gfx/icon_util.h" 13 #include "chrome/common/gfx/icon_util.h"
14 #include "chrome/common/gfx/path.h" 14 #include "chrome/common/gfx/path.h"
15 #include "chrome/common/l10n_util.h" 15 #include "chrome/common/l10n_util.h"
16 #include "chrome/common/notification_service.h" 16 #include "chrome/common/notification_service.h"
17 #include "chrome/common/pref_service.h" 17 #include "chrome/common/pref_service.h"
18 #include "chrome/common/resource_bundle.h" 18 #include "chrome/common/resource_bundle.h"
19 #include "chrome/common/win_util.h" 19 #include "chrome/common/win_util.h"
20 #include "chrome/views/widget/root_view.h" 20 #include "chrome/views/widget/root_view.h"
21 #include "chrome/views/window/client_view.h" 21 #include "chrome/views/window/client_view.h"
22 #include "chrome/views/window/custom_frame_view.h" 22 #include "chrome/views/window/custom_frame_view.h"
23 #include "chrome/views/window/native_frame_view.h" 23 #include "chrome/views/window/native_frame_view.h"
24 #include "chrome/views/window/non_client_view.h" 24 #include "chrome/views/window/non_client_view.h"
25 #include "chrome/views/window/window_delegate.h" 25 #include "chrome/views/window/window_delegate.h"
26 #include "grit/generated_resources.h" 26 #include "grit/generated_resources.h"
27 27
28 namespace {
29
30 bool GetMonitorAndRects(const RECT& rect,
31 HMONITOR* monitor,
32 gfx::Rect* monitor_rect,
33 gfx::Rect* work_area) {
34 DCHECK(monitor);
35 DCHECK(monitor_rect);
36 DCHECK(work_area);
37 *monitor = MonitorFromRect(&rect, MONITOR_DEFAULTTONULL);
38 if (!*monitor)
39 return false;
40 MONITORINFO monitor_info = { 0 };
41 monitor_info.cbSize = sizeof(monitor_info);
42 GetMonitorInfo(*monitor, &monitor_info);
43 *monitor_rect = monitor_info.rcMonitor;
44 *work_area = monitor_info.rcWork;
45 return true;
46 }
47
48 } // namespace
49
28 namespace views { 50 namespace views {
29 51
30 // A scoping class that prevents a window from being able to redraw in response 52 // A scoping class that prevents a window from being able to redraw in response
31 // to invalidations that may occur within it for the lifetime of the object. 53 // to invalidations that may occur within it for the lifetime of the object.
32 // 54 //
33 // Why would we want such a thing? Well, it turns out Windows has some 55 // Why would we want such a thing? Well, it turns out Windows has some
34 // "unorthodox" behavior when it comes to painting its non-client areas. 56 // "unorthodox" behavior when it comes to painting its non-client areas.
35 // Occasionally, Windows will paint portions of the default non-client area 57 // Occasionally, Windows will paint portions of the default non-client area
36 // right over the top of the custom frame. This is not simply fixed by handling 58 // right over the top of the custom frame. This is not simply fixed by handling
37 // WM_NCPAINT/WM_PAINT, with some investigation it turns out that this 59 // WM_NCPAINT/WM_PAINT, with some investigation it turns out that this
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after
89 window->Init(parent, bounds); 111 window->Init(parent, bounds);
90 return window; 112 return window;
91 } 113 }
92 114
93 gfx::Rect WindowWin::GetBounds() const { 115 gfx::Rect WindowWin::GetBounds() const {
94 gfx::Rect bounds; 116 gfx::Rect bounds;
95 WidgetWin::GetBounds(&bounds, true); 117 WidgetWin::GetBounds(&bounds, true);
96 return bounds; 118 return bounds;
97 } 119 }
98 120
121 gfx::Rect WindowWin::GetNormalBounds() const {
122 // If we're in fullscreen mode, we've changed the normal bounds to the monitor
123 // rect, so return the saved bounds instead.
124 if (IsFullscreen())
125 return gfx::Rect(saved_window_info_.window_rect);
126
127 WINDOWPLACEMENT wp;
128 wp.length = sizeof(wp);
129 const bool ret = !!GetWindowPlacement(GetNativeView(), &wp);
130 DCHECK(ret);
131 return gfx::Rect(wp.rcNormalPosition);
132 }
133
99 void WindowWin::SetBounds(const gfx::Rect& bounds) { 134 void WindowWin::SetBounds(const gfx::Rect& bounds) {
100 SetBounds(bounds, NULL); 135 SetBounds(bounds, NULL);
101 } 136 }
102 137
103 void WindowWin::SetBounds(const gfx::Rect& bounds, 138 void WindowWin::SetBounds(const gfx::Rect& bounds,
104 gfx::NativeWindow other_window) { 139 gfx::NativeWindow other_window) {
105 win_util::SetChildBounds(GetNativeView(), GetParent(), other_window, bounds, 140 win_util::SetChildBounds(GetNativeView(), GetParent(), other_window, bounds,
106 kMonitorEdgePadding, 0); 141 kMonitorEdgePadding, 0);
107 } 142 }
108 143
(...skipping 22 matching lines...) Expand all
131 166
132 int WindowWin::GetShowState() const { 167 int WindowWin::GetShowState() const {
133 return SW_SHOWNORMAL; 168 return SW_SHOWNORMAL;
134 } 169 }
135 170
136 void WindowWin::ExecuteSystemMenuCommand(int command) { 171 void WindowWin::ExecuteSystemMenuCommand(int command) {
137 if (command) 172 if (command)
138 SendMessage(GetNativeView(), WM_SYSCOMMAND, command, 0); 173 SendMessage(GetNativeView(), WM_SYSCOMMAND, command, 0);
139 } 174 }
140 175
176 void WindowWin::PushForceHidden() {
177 if (force_hidden_count_++ == 0)
178 Hide();
179 }
180
181 void WindowWin::PopForceHidden() {
182 if (--force_hidden_count_ <= 0) {
183 force_hidden_count_ = 0;
184 ShowWindow(SW_SHOW);
185 }
186 }
187
141 // static 188 // static
142 int Window::GetLocalizedContentsWidth(int col_resource_id) { 189 int Window::GetLocalizedContentsWidth(int col_resource_id) {
143 double chars = _wtof(l10n_util::GetString(col_resource_id).c_str()); 190 double chars = _wtof(l10n_util::GetString(col_resource_id).c_str());
144 ResourceBundle& rb = ResourceBundle::GetSharedInstance(); 191 ResourceBundle& rb = ResourceBundle::GetSharedInstance();
145 ChromeFont font = rb.GetFont(ResourceBundle::BaseFont); 192 ChromeFont font = rb.GetFont(ResourceBundle::BaseFont);
146 int width = font.GetExpectedTextWidth(static_cast<int>(chars)); 193 int width = font.GetExpectedTextWidth(static_cast<int>(chars));
147 DCHECK(width > 0); 194 DCHECK(width > 0);
148 return width; 195 return width;
149 } 196 }
150 197
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after
228 } 275 }
229 276
230 bool WindowWin::IsMaximized() const { 277 bool WindowWin::IsMaximized() const {
231 return !!::IsZoomed(GetNativeView()); 278 return !!::IsZoomed(GetNativeView());
232 } 279 }
233 280
234 bool WindowWin::IsMinimized() const { 281 bool WindowWin::IsMinimized() const {
235 return !!::IsIconic(GetNativeView()); 282 return !!::IsIconic(GetNativeView());
236 } 283 }
237 284
285 void WindowWin::SetFullscreen(bool fullscreen) {
286 if (fullscreen_ == fullscreen)
287 return; // Nothing to do.
288
289 // Toggle fullscreen mode.
290 fullscreen_ = fullscreen;
291
292 // Reduce jankiness during the following position changes by hiding the window
293 // until it's in the final position.
294 PushForceHidden();
295
296 // Size/position/style window appropriately.
297 HWND hwnd = GetNativeView();
298 if (fullscreen_) {
299 // Save current window information. We force the window into restored mode
300 // before going fullscreen because Windows doesn't seem to hide the
301 // taskbar if the window is in the maximized state.
302 saved_window_info_.maximized = IsMaximized();
303 if (saved_window_info_.maximized)
304 ExecuteSystemMenuCommand(SC_RESTORE);
305 saved_window_info_.style = GetWindowLong(GWL_STYLE);
306 saved_window_info_.ex_style = GetWindowLong(GWL_EXSTYLE);
307 GetWindowRect(&saved_window_info_.window_rect);
308
309 // Set new window style and size.
310 MONITORINFO monitor_info;
311 monitor_info.cbSize = sizeof(monitor_info);
312 GetMonitorInfo(MonitorFromWindow(hwnd, MONITOR_DEFAULTTONEAREST),
313 &monitor_info);
314 gfx::Rect monitor_rect(monitor_info.rcMonitor);
315 SetWindowLong(GWL_STYLE,
316 saved_window_info_.style & ~(WS_CAPTION | WS_THICKFRAME));
317 SetWindowLong(GWL_EXSTYLE,
318 saved_window_info_.ex_style & ~(WS_EX_DLGMODALFRAME |
319 WS_EX_WINDOWEDGE | WS_EX_CLIENTEDGE | WS_EX_STATICEDGE));
320 SetWindowPos(NULL, monitor_rect.x(), monitor_rect.y(),
321 monitor_rect.width(), monitor_rect.height(),
322 SWP_NOZORDER | SWP_NOACTIVATE | SWP_FRAMECHANGED);
323 } else {
324 // Reset original window style and size. The multiple window size/moves
325 // here are ugly, but if SetWindowPos() doesn't redraw, the taskbar won't be
326 // repainted. Better-looking methods welcome.
327 gfx::Rect new_rect(saved_window_info_.window_rect);
328 SetWindowLong(GWL_STYLE, saved_window_info_.style);
329 SetWindowLong(GWL_EXSTYLE, saved_window_info_.ex_style);
330 SetWindowPos(NULL, new_rect.x(), new_rect.y(), new_rect.width(),
331 new_rect.height(),
332 SWP_NOZORDER | SWP_NOACTIVATE | SWP_FRAMECHANGED);
333 if (saved_window_info_.maximized)
334 ExecuteSystemMenuCommand(SC_MAXIMIZE);
335 }
336
337 // Undo our anti-jankiness hacks.
338 PopForceHidden();
339 }
340
341 bool WindowWin::IsFullscreen() const {
342 return fullscreen_;
343 }
344
238 void WindowWin::EnableClose(bool enable) { 345 void WindowWin::EnableClose(bool enable) {
239 // If the native frame is rendering its own close button, ask it to disable. 346 // If the native frame is rendering its own close button, ask it to disable.
240 non_client_view_->EnableClose(enable); 347 non_client_view_->EnableClose(enable);
241 348
242 // Disable the native frame's close button regardless of whether or not the 349 // Disable the native frame's close button regardless of whether or not the
243 // native frame is in use, since this also affects the system menu. 350 // native frame is in use, since this also affects the system menu.
244 EnableMenuItem(GetSystemMenu(GetNativeView(), false), 351 EnableMenuItem(GetSystemMenu(GetNativeView(), false),
245 SC_CLOSE, enable ? MF_ENABLED : MF_GRAYED); 352 SC_CLOSE, enable ? MF_ENABLED : MF_GRAYED);
246 353
247 // Let the window know the frame changed. 354 // Let the window know the frame changed.
(...skipping 93 matching lines...) Expand 10 before | Expand all | Expand 10 after
341 WindowWin::WindowWin(WindowDelegate* window_delegate) 448 WindowWin::WindowWin(WindowDelegate* window_delegate)
342 : WidgetWin(), 449 : WidgetWin(),
343 focus_on_creation_(true), 450 focus_on_creation_(true),
344 window_delegate_(window_delegate), 451 window_delegate_(window_delegate),
345 non_client_view_(new NonClientView(this)), 452 non_client_view_(new NonClientView(this)),
346 owning_hwnd_(NULL), 453 owning_hwnd_(NULL),
347 minimum_size_(100, 100), 454 minimum_size_(100, 100),
348 is_modal_(false), 455 is_modal_(false),
349 restored_enabled_(false), 456 restored_enabled_(false),
350 is_always_on_top_(false), 457 is_always_on_top_(false),
458 fullscreen_(false),
351 window_closed_(false), 459 window_closed_(false),
352 disable_inactive_rendering_(false), 460 disable_inactive_rendering_(false),
353 is_active_(false), 461 is_active_(false),
354 lock_updates_(false), 462 lock_updates_(false),
355 saved_window_style_(0), 463 saved_window_style_(0),
356 saved_maximized_state_(0), 464 saved_maximized_state_(0),
357 force_hidden_(false) { 465 ignore_window_pos_changes_(false),
466 ignore_pos_changes_factory_(this),
467 force_hidden_count_(0),
468 last_monitor_(NULL) {
358 InitClass(); 469 InitClass();
359 DCHECK(window_delegate_); 470 DCHECK(window_delegate_);
360 window_delegate_->window_.reset(this); 471 window_delegate_->window_.reset(this);
361 // Initialize these values to 0 so that subclasses can override the default 472 // Initialize these values to 0 so that subclasses can override the default
362 // behavior before calling Init. 473 // behavior before calling Init.
363 set_window_style(0); 474 set_window_style(0);
364 set_window_ex_style(0); 475 set_window_ex_style(0);
365 } 476 }
366 477
367 void WindowWin::Init(HWND parent, const gfx::Rect& bounds) { 478 void WindowWin::Init(HWND parent, const gfx::Rect& bounds) {
(...skipping 18 matching lines...) Expand all
386 // Create the ClientView, add it to the NonClientView and add the 497 // Create the ClientView, add it to the NonClientView and add the
387 // NonClientView to the RootView. This will cause everything to be parented. 498 // NonClientView to the RootView. This will cause everything to be parented.
388 non_client_view_->set_client_view(window_delegate_->CreateClientView(this)); 499 non_client_view_->set_client_view(window_delegate_->CreateClientView(this));
389 WidgetWin::SetContentsView(non_client_view_); 500 WidgetWin::SetContentsView(non_client_view_);
390 501
391 UpdateWindowTitle(); 502 UpdateWindowTitle();
392 503
393 SetInitialBounds(bounds); 504 SetInitialBounds(bounds);
394 InitAlwaysOnTopState(); 505 InitAlwaysOnTopState();
395 506
507 GetMonitorAndRects(bounds.ToRECT(), &last_monitor_, &last_monitor_rect_,
508 &last_work_area_);
509
396 if (!IsAppWindow()) { 510 if (!IsAppWindow()) {
397 notification_registrar_.Add( 511 notification_registrar_.Add(
398 this, 512 this,
399 NotificationType::ALL_APPWINDOWS_CLOSED, 513 NotificationType::ALL_APPWINDOWS_CLOSED,
400 NotificationService::AllSources()); 514 NotificationService::AllSources());
401 } 515 }
402 516
403 ResetWindowRegion(false); 517 ResetWindowRegion(false);
404 518
405 NotificationService::current()->Notify( 519 NotificationService::current()->Notify(
(...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after
490 // (now), saving off its placement so it can be properly restored once 604 // (now), saving off its placement so it can be properly restored once
491 // everything has settled down. 605 // everything has settled down.
492 WINDOWPLACEMENT saved_window_placement; 606 WINDOWPLACEMENT saved_window_placement;
493 saved_window_placement.length = sizeof(WINDOWPLACEMENT); 607 saved_window_placement.length = sizeof(WINDOWPLACEMENT);
494 GetWindowPlacement(GetNativeView(), &saved_window_placement); 608 GetWindowPlacement(GetNativeView(), &saved_window_placement);
495 Hide(); 609 Hide();
496 610
497 // Important step: restore the window first, since our hiding hack doesn't 611 // Important step: restore the window first, since our hiding hack doesn't
498 // work for maximized windows! We tell the frame not to allow itself to be 612 // work for maximized windows! We tell the frame not to allow itself to be
499 // made visible though, which removes the brief flicker. 613 // made visible though, which removes the brief flicker.
500 force_hidden_ = true; 614 ++force_hidden_count_;
501 ::ShowWindow(GetNativeView(), SW_RESTORE); 615 ::ShowWindow(GetNativeView(), SW_RESTORE);
502 force_hidden_ = false; 616 --force_hidden_count_;
503 617
504 // We respond to this in response to WM_DWMCOMPOSITIONCHANGED since that is 618 // We respond to this in response to WM_DWMCOMPOSITIONCHANGED since that is
505 // the only thing we care about - we don't actually respond to WM_THEMECHANGED 619 // the only thing we care about - we don't actually respond to WM_THEMECHANGED
506 // messages. 620 // messages.
507 non_client_view_->SetUseNativeFrame(win_util::ShouldUseVistaFrame()); 621 non_client_view_->SetUseNativeFrame(win_util::ShouldUseVistaFrame());
508 622
509 // Now that we've updated the frame, we'll want to restore our saved placement 623 // Now that we've updated the frame, we'll want to restore our saved placement
510 // since the display should have settled down and we can be properly rendered. 624 // since the display should have settled down and we can be properly rendered.
511 SetWindowPlacement(GetNativeView(), &saved_window_placement); 625 SetWindowPlacement(GetNativeView(), &saved_window_placement);
512 626
(...skipping 111 matching lines...) Expand 10 before | Expand all | Expand 10 after
624 // Make the maximized mode client rect fit the screen exactly, by 738 // Make the maximized mode client rect fit the screen exactly, by
625 // subtracting the border Windows automatically adds for maximized mode. 739 // subtracting the border Windows automatically adds for maximized mode.
626 int border_thickness = GetSystemMetrics(SM_CXSIZEFRAME); 740 int border_thickness = GetSystemMetrics(SM_CXSIZEFRAME);
627 InflateRect(client_rect, -border_thickness, -border_thickness); 741 InflateRect(client_rect, -border_thickness, -border_thickness);
628 742
629 // Find all auto-hide taskbars along the screen edges and adjust in by the 743 // Find all auto-hide taskbars along the screen edges and adjust in by the
630 // thickness of the auto-hide taskbar on each such edge, so the window isn't 744 // thickness of the auto-hide taskbar on each such edge, so the window isn't
631 // treated as a "fullscreen app", which would cause the taskbars to 745 // treated as a "fullscreen app", which would cause the taskbars to
632 // disappear. 746 // disappear.
633 HMONITOR monitor = MonitorFromWindow(GetNativeView(), 747 HMONITOR monitor = MonitorFromWindow(GetNativeView(),
634 MONITOR_DEFAULTTONEAREST); 748 MONITOR_DEFAULTTONULL);
635 if (win_util::EdgeHasTopmostAutoHideTaskbar(ABE_LEFT, monitor)) 749 if (win_util::EdgeHasTopmostAutoHideTaskbar(ABE_LEFT, monitor))
636 client_rect->left += win_util::kAutoHideTaskbarThicknessPx; 750 client_rect->left += win_util::kAutoHideTaskbarThicknessPx;
637 if (win_util::EdgeHasTopmostAutoHideTaskbar(ABE_TOP, monitor)) 751 if (win_util::EdgeHasTopmostAutoHideTaskbar(ABE_TOP, monitor))
638 client_rect->top += win_util::kAutoHideTaskbarThicknessPx; 752 client_rect->top += win_util::kAutoHideTaskbarThicknessPx;
639 if (win_util::EdgeHasTopmostAutoHideTaskbar(ABE_RIGHT, monitor)) 753 if (win_util::EdgeHasTopmostAutoHideTaskbar(ABE_RIGHT, monitor))
640 client_rect->right -= win_util::kAutoHideTaskbarThicknessPx; 754 client_rect->right -= win_util::kAutoHideTaskbarThicknessPx;
641 if (win_util::EdgeHasTopmostAutoHideTaskbar(ABE_BOTTOM, monitor)) 755 if (win_util::EdgeHasTopmostAutoHideTaskbar(ABE_BOTTOM, monitor))
642 client_rect->bottom -= win_util::kAutoHideTaskbarThicknessPx; 756 client_rect->bottom -= win_util::kAutoHideTaskbarThicknessPx;
643 757
644 // We cannot return WVR_REDRAW when there is nonclient area, or Windows 758 // We cannot return WVR_REDRAW when there is nonclient area, or Windows
(...skipping 253 matching lines...) Expand 10 before | Expand all | Expand 10 after
898 reinterpret_cast<LPARAM>(new_icon)); 1012 reinterpret_cast<LPARAM>(new_icon));
899 } 1013 }
900 1014
901 LRESULT WindowWin::OnSetText(const wchar_t* text) { 1015 LRESULT WindowWin::OnSetText(const wchar_t* text) {
902 // This shouldn't hurt even if we're using the native frame. 1016 // This shouldn't hurt even if we're using the native frame.
903 ScopedRedrawLock lock(this); 1017 ScopedRedrawLock lock(this);
904 return DefWindowProc(GetNativeView(), WM_SETTEXT, NULL, 1018 return DefWindowProc(GetNativeView(), WM_SETTEXT, NULL,
905 reinterpret_cast<LPARAM>(text)); 1019 reinterpret_cast<LPARAM>(text));
906 } 1020 }
907 1021
1022 void WindowWin::OnSettingChange(UINT flags, const wchar_t* section) {
1023 if (!GetParent() && (flags == SPI_SETWORKAREA)) {
1024 // Fire a dummy SetWindowPos() call, so we'll trip the code in
1025 // OnWindowPosChanging() below that notices work area changes.
1026 ::SetWindowPos(GetNativeView(), 0, 0, 0, 0, 0, SWP_NOSIZE | SWP_NOMOVE |
1027 SWP_NOZORDER | SWP_NOREDRAW | SWP_NOACTIVATE | SWP_NOOWNERZORDER);
1028 SetMsgHandled(TRUE);
1029 } else {
1030 WidgetWin::OnSettingChange(flags, section);
1031 }
1032 }
1033
908 void WindowWin::OnSize(UINT size_param, const CSize& new_size) { 1034 void WindowWin::OnSize(UINT size_param, const CSize& new_size) {
909 // Don't no-op if the new_size matches current size. If our normal bounds 1035 // Don't no-op if the new_size matches current size. If our normal bounds
910 // and maximized bounds are the same, then we need to layout (because we 1036 // and maximized bounds are the same, then we need to layout (because we
911 // layout differently when maximized). 1037 // layout differently when maximized).
912 SaveWindowPosition(); 1038 SaveWindowPosition();
913 ChangeSize(size_param, new_size); 1039 ChangeSize(size_param, new_size);
914 RedrawWindow(GetNativeView(), NULL, NULL, RDW_INVALIDATE | RDW_ALLCHILDREN); 1040 RedrawWindow(GetNativeView(), NULL, NULL, RDW_INVALIDATE | RDW_ALLCHILDREN);
915 1041
916 // ResetWindowRegion is going to trigger WM_NCPAINT. By doing it after we've 1042 // ResetWindowRegion is going to trigger WM_NCPAINT. By doing it after we've
917 // invoked OnSize we ensure the RootView has been laid out. 1043 // invoked OnSize we ensure the RootView has been laid out.
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after
964 // Run the system menu at the NonClientView's desired location. 1090 // Run the system menu at the NonClientView's desired location.
965 RunSystemMenu(non_client_view_->GetSystemMenuPoint()); 1091 RunSystemMenu(non_client_view_->GetSystemMenuPoint());
966 } else { 1092 } else {
967 // Use the default implementation for any other command. 1093 // Use the default implementation for any other command.
968 DefWindowProc(GetNativeView(), WM_SYSCOMMAND, notification_code, 1094 DefWindowProc(GetNativeView(), WM_SYSCOMMAND, notification_code,
969 MAKELPARAM(click.y, click.x)); 1095 MAKELPARAM(click.y, click.x));
970 } 1096 }
971 } 1097 }
972 1098
973 void WindowWin::OnWindowPosChanging(WINDOWPOS* window_pos) { 1099 void WindowWin::OnWindowPosChanging(WINDOWPOS* window_pos) {
974 if (force_hidden_) { 1100 if (force_hidden_count_) {
975 // Prevent the window from being made visible if we've been asked to do so. 1101 // Prevent the window from being made visible if we've been asked to do so.
976 // See comment in header as to why we might want this. 1102 // See comment in header as to why we might want this.
977 window_pos->flags &= ~SWP_SHOWWINDOW; 1103 window_pos->flags &= ~SWP_SHOWWINDOW;
978 } 1104 }
1105
1106 if (ignore_window_pos_changes_) {
1107 // If somebody's trying to toggle our visibility, change the nonclient area,
1108 // change our Z-order, or activate us, we should probably let it go through.
1109 if (!(window_pos->flags & ((IsVisible() ? SWP_HIDEWINDOW : SWP_SHOWWINDOW) |
1110 SWP_FRAMECHANGED)) &&
1111 (window_pos->flags & (SWP_NOZORDER | SWP_NOACTIVATE))) {
1112 // Just sizing/moving the window; ignore.
1113 window_pos->flags |= SWP_NOSIZE | SWP_NOMOVE | SWP_NOREDRAW;
1114 window_pos->flags &= ~(SWP_SHOWWINDOW | SWP_HIDEWINDOW);
1115 }
1116 } else if (!GetParent()) {
1117 CRect window_rect;
1118 HMONITOR monitor;
1119 gfx::Rect monitor_rect, work_area;
1120 if (GetWindowRect(&window_rect) &&
1121 GetMonitorAndRects(window_rect, &monitor, &monitor_rect, &work_area)) {
1122 if (monitor && (monitor == last_monitor_) &&
1123 (IsFullscreen() || ((monitor_rect == last_monitor_rect_) &&
1124 (work_area != last_work_area_)))) {
1125 // A rect for the monitor we're on changed. Normally Windows notifies
1126 // us about this (and thus we're reaching here due to the SetWindowPos()
1127 // call in OnSettingChange() above), but with some software (e.g.
1128 // nVidia's nView desktop manager) the work area can change asynchronous
1129 // to any notification, and we're just sent a SetWindowPos() call with a
1130 // new (frequently incorrect) position/size. In either case, the best
1131 // response is to throw away the existing position/size information in
1132 // |window_pos| and recalculate it based on the old window coordinates,
1133 // adjusted for the change in the work area (or, for fullscreen windows,
1134 // to just set it to the monitor rect).
1135 if (IsFullscreen()) {
1136 window_pos->x = monitor_rect.x();
1137 window_pos->y = monitor_rect.y();
1138 window_pos->cx = monitor_rect.width();
1139 window_pos->cy = monitor_rect.height();
1140 } else if (IsZoomed()) {
1141 window_pos->x =
1142 window_rect.left + work_area.x() - last_work_area_.x();
1143 window_pos->y = window_rect.top + work_area.y() - last_work_area_.y();
1144 window_pos->cx = window_rect.Width() + work_area.width() -
1145 last_work_area_.width();
1146 window_pos->cy = window_rect.Height() + work_area.height() -
1147 last_work_area_.height();
1148 } else {
1149 gfx::Rect window_gfx_rect(window_rect);
1150 gfx::Rect new_window_rect = window_gfx_rect.AdjustToFit(work_area);
1151 window_pos->x = new_window_rect.x();
1152 window_pos->y = new_window_rect.y();
1153 window_pos->cx = new_window_rect.width();
1154 window_pos->cy = new_window_rect.height();
1155 }
1156 // WARNING! Don't set SWP_FRAMECHANGED here, it breaks moving the child
1157 // HWNDs for some reason.
1158 window_pos->flags &= ~(SWP_NOSIZE | SWP_NOMOVE | SWP_NOREDRAW);
1159 window_pos->flags |= SWP_NOCOPYBITS;
1160
1161 // Now ignore all immediately-following SetWindowPos() changes. Windows
1162 // likes to (incorrectly) recalculate what our position/size should be
1163 // and send us further updates.
1164 ignore_window_pos_changes_ = true;
1165 DCHECK(ignore_pos_changes_factory_.empty());
1166 MessageLoop::current()->PostTask(FROM_HERE,
1167 ignore_pos_changes_factory_.NewRunnableMethod(
1168 &WindowWin::StopIgnoringPosChanges));
1169 }
1170 last_monitor_ = monitor;
1171 last_monitor_rect_ = monitor_rect;
1172 last_work_area_ = work_area;
1173 }
1174 }
1175
979 WidgetWin::OnWindowPosChanging(window_pos); 1176 WidgetWin::OnWindowPosChanging(window_pos);
980 } 1177 }
981 1178
982 //////////////////////////////////////////////////////////////////////////////// 1179 ////////////////////////////////////////////////////////////////////////////////
983 // WindowWin, private: 1180 // WindowWin, private:
984 1181
985 void WindowWin::BecomeModal() { 1182 void WindowWin::BecomeModal() {
986 // We implement modality by crawling up the hierarchy of windows starting 1183 // We implement modality by crawling up the hierarchy of windows starting
987 // at the owner, disabling all of them so that they don't receive input 1184 // at the owner, disabling all of them so that they don't receive input
988 // messages. 1185 // messages.
(...skipping 171 matching lines...) Expand 10 before | Expand all | Expand 10 after
1160 DCHECK(r); 1357 DCHECK(r);
1161 1358
1162 bool maximized = (win_placement.showCmd == SW_SHOWMAXIMIZED); 1359 bool maximized = (win_placement.showCmd == SW_SHOWMAXIMIZED);
1163 CRect window_bounds(win_placement.rcNormalPosition); 1360 CRect window_bounds(win_placement.rcNormalPosition);
1164 window_delegate_->SaveWindowPlacement( 1361 window_delegate_->SaveWindowPlacement(
1165 gfx::Rect(win_placement.rcNormalPosition), maximized, is_always_on_top_); 1362 gfx::Rect(win_placement.rcNormalPosition), maximized, is_always_on_top_);
1166 } 1363 }
1167 1364
1168 void WindowWin::LockUpdates() { 1365 void WindowWin::LockUpdates() {
1169 lock_updates_ = true; 1366 lock_updates_ = true;
1170 saved_window_style_ = GetWindowLong(GetNativeView(), GWL_STYLE); 1367 saved_window_style_ = GetWindowLong(GWL_STYLE);
1171 SetWindowLong(GetNativeView(), GWL_STYLE, saved_window_style_ & ~WS_VISIBLE); 1368 SetWindowLong(GWL_STYLE, saved_window_style_ & ~WS_VISIBLE);
1172 } 1369 }
1173 1370
1174 void WindowWin::UnlockUpdates() { 1371 void WindowWin::UnlockUpdates() {
1175 SetWindowLong(GetNativeView(), GWL_STYLE, saved_window_style_); 1372 SetWindowLong(GWL_STYLE, saved_window_style_);
1176 lock_updates_ = false; 1373 lock_updates_ = false;
1177 } 1374 }
1178 1375
1179 void WindowWin::ResetWindowRegion(bool force) { 1376 void WindowWin::ResetWindowRegion(bool force) {
1180 // A native frame uses the native window region, and we don't want to mess 1377 // A native frame uses the native window region, and we don't want to mess
1181 // with it. 1378 // with it.
1182 if (non_client_view_->UseNativeFrame()) { 1379 if (non_client_view_->UseNativeFrame()) {
1183 if (force) 1380 if (force)
1184 SetWindowRgn(NULL, TRUE); 1381 SetWindowRgn(NULL, TRUE);
1185 return; 1382 return;
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after
1234 resize_cursors_[RC_NORMAL] = LoadCursor(NULL, IDC_ARROW); 1431 resize_cursors_[RC_NORMAL] = LoadCursor(NULL, IDC_ARROW);
1235 resize_cursors_[RC_VERTICAL] = LoadCursor(NULL, IDC_SIZENS); 1432 resize_cursors_[RC_VERTICAL] = LoadCursor(NULL, IDC_SIZENS);
1236 resize_cursors_[RC_HORIZONTAL] = LoadCursor(NULL, IDC_SIZEWE); 1433 resize_cursors_[RC_HORIZONTAL] = LoadCursor(NULL, IDC_SIZEWE);
1237 resize_cursors_[RC_NESW] = LoadCursor(NULL, IDC_SIZENESW); 1434 resize_cursors_[RC_NESW] = LoadCursor(NULL, IDC_SIZENESW);
1238 resize_cursors_[RC_NWSE] = LoadCursor(NULL, IDC_SIZENWSE); 1435 resize_cursors_[RC_NWSE] = LoadCursor(NULL, IDC_SIZENWSE);
1239 initialized = true; 1436 initialized = true;
1240 } 1437 }
1241 } 1438 }
1242 1439
1243 } // namespace views 1440 } // namespace views
OLDNEW
« no previous file with comments | « chrome/views/window/window_win.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698