OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 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 "ui/views/win/hwnd_message_handler.h" | 5 #include "ui/views/win/hwnd_message_handler.h" |
6 | 6 |
7 #include <dwmapi.h> | 7 #include <dwmapi.h> |
8 #include <shellapi.h> | 8 #include <shellapi.h> |
9 | 9 |
10 #include "base/bind.h" | 10 #include "base/bind.h" |
(...skipping 281 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
292 } | 292 } |
293 | 293 |
294 return false; | 294 return false; |
295 } | 295 } |
296 | 296 |
297 #endif | 297 #endif |
298 | 298 |
299 // The thickness of an auto-hide taskbar in pixels. | 299 // The thickness of an auto-hide taskbar in pixels. |
300 const int kAutoHideTaskbarThicknessPx = 2; | 300 const int kAutoHideTaskbarThicknessPx = 2; |
301 | 301 |
| 302 bool IsTopLevelWindow(HWND window) { |
| 303 long style = ::GetWindowLong(window, GWL_STYLE); |
| 304 if (!(style & WS_CHILD)) |
| 305 return true; |
| 306 HWND parent = ::GetParent(window); |
| 307 return !parent || (parent == ::GetDesktopWindow()); |
| 308 } |
| 309 |
| 310 void AddScrollStylesToWindow(HWND window) { |
| 311 if (::IsWindow(window)) { |
| 312 long current_style = ::GetWindowLong(window, GWL_STYLE); |
| 313 ::SetWindowLong(window, GWL_STYLE, |
| 314 current_style | WS_VSCROLL | WS_HSCROLL); |
| 315 } |
| 316 } |
| 317 |
302 } // namespace | 318 } // namespace |
303 | 319 |
304 // A scoping class that prevents a window from being able to redraw in response | 320 // A scoping class that prevents a window from being able to redraw in response |
305 // to invalidations that may occur within it for the lifetime of the object. | 321 // to invalidations that may occur within it for the lifetime of the object. |
306 // | 322 // |
307 // Why would we want such a thing? Well, it turns out Windows has some | 323 // Why would we want such a thing? Well, it turns out Windows has some |
308 // "unorthodox" behavior when it comes to painting its non-client areas. | 324 // "unorthodox" behavior when it comes to painting its non-client areas. |
309 // Occasionally, Windows will paint portions of the default non-client area | 325 // Occasionally, Windows will paint portions of the default non-client area |
310 // right over the top of the custom frame. This is not simply fixed by handling | 326 // right over the top of the custom frame. This is not simply fixed by handling |
311 // WM_NCPAINT/WM_PAINT, with some investigation it turns out that this | 327 // WM_NCPAINT/WM_PAINT, with some investigation it turns out that this |
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
382 is_right_mouse_pressed_on_caption_(false), | 398 is_right_mouse_pressed_on_caption_(false), |
383 lock_updates_count_(0), | 399 lock_updates_count_(0), |
384 ignore_window_pos_changes_(false), | 400 ignore_window_pos_changes_(false), |
385 last_monitor_(NULL), | 401 last_monitor_(NULL), |
386 use_layered_buffer_(false), | 402 use_layered_buffer_(false), |
387 layered_alpha_(255), | 403 layered_alpha_(255), |
388 waiting_for_redraw_layered_window_contents_(false), | 404 waiting_for_redraw_layered_window_contents_(false), |
389 can_update_layered_window_(true), | 405 can_update_layered_window_(true), |
390 is_first_nccalc_(true), | 406 is_first_nccalc_(true), |
391 autohide_factory_(this), | 407 autohide_factory_(this), |
392 id_generator_(0) { | 408 id_generator_(0), |
| 409 scroll_styles_set_(false) { |
393 } | 410 } |
394 | 411 |
395 HWNDMessageHandler::~HWNDMessageHandler() { | 412 HWNDMessageHandler::~HWNDMessageHandler() { |
396 delegate_ = NULL; | 413 delegate_ = NULL; |
397 // Prevent calls back into this class via WNDPROC now that we've been | 414 // Prevent calls back into this class via WNDPROC now that we've been |
398 // destroyed. | 415 // destroyed. |
399 ClearUserData(); | 416 ClearUserData(); |
400 } | 417 } |
401 | 418 |
402 void HWNDMessageHandler::Init(HWND parent, const gfx::Rect& bounds) { | 419 void HWNDMessageHandler::Init(HWND parent, const gfx::Rect& bounds) { |
(...skipping 914 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1317 #if !defined(USE_AURA) | 1334 #if !defined(USE_AURA) |
1318 // We need to add ourselves as a message loop observer so that we can repaint | 1335 // We need to add ourselves as a message loop observer so that we can repaint |
1319 // aggressively if the contents of our window become invalid. Unfortunately | 1336 // aggressively if the contents of our window become invalid. Unfortunately |
1320 // WM_PAINT messages are starved and we get flickery redrawing when resizing | 1337 // WM_PAINT messages are starved and we get flickery redrawing when resizing |
1321 // if we do not do this. | 1338 // if we do not do this. |
1322 base::MessageLoopForUI::current()->AddObserver(this); | 1339 base::MessageLoopForUI::current()->AddObserver(this); |
1323 #endif | 1340 #endif |
1324 | 1341 |
1325 delegate_->HandleCreate(); | 1342 delegate_->HandleCreate(); |
1326 | 1343 |
| 1344 #if defined(USE_AURA) |
| 1345 // Certain trackpad drivers on Windows have bugs where in they don't generate |
| 1346 // WM_MOUSEWHEEL messages for the trackpoint and trackpad scrolling gestures |
| 1347 // unless there is an entry for Chrome with the class name of the Window. |
| 1348 // These drivers check if the window under the trackpoint has the WS_VSCROLL/ |
| 1349 // WS_HSCROLL style and if yes they generate the legacy WM_VSCROLL/WM_HSCROLL |
| 1350 // messages. We add these styles to ensure that trackpad/trackpoint scrolling |
| 1351 // work. |
| 1352 // TODO(ananta) |
| 1353 // Look into moving the WS_VSCROLL and WS_HSCROLL style setting logic to the |
| 1354 // CalculateWindowStylesFromInitParams function. Doing it there seems to |
| 1355 // cause some interactive tests to fail. Investigation needed. |
| 1356 if (IsTopLevelWindow(hwnd())) { |
| 1357 long current_style = ::GetWindowLong(hwnd(), GWL_STYLE); |
| 1358 ::SetWindowLong(hwnd(), GWL_STYLE, |
| 1359 current_style | WS_VSCROLL | WS_HSCROLL); |
| 1360 scroll_styles_set_ = true; |
| 1361 } |
| 1362 #endif |
1327 // TODO(beng): move more of NWW::OnCreate here. | 1363 // TODO(beng): move more of NWW::OnCreate here. |
1328 return 0; | 1364 return 0; |
1329 } | 1365 } |
1330 | 1366 |
1331 void HWNDMessageHandler::OnDestroy() { | 1367 void HWNDMessageHandler::OnDestroy() { |
1332 delegate_->HandleDestroying(); | 1368 delegate_->HandleDestroying(); |
1333 } | 1369 } |
1334 | 1370 |
1335 void HWNDMessageHandler::OnDisplayChange(UINT bits_per_pixel, | 1371 void HWNDMessageHandler::OnDisplayChange(UINT bits_per_pixel, |
1336 const CSize& screen_size) { | 1372 const CSize& screen_size) { |
(...skipping 581 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1918 EndPaint(hwnd(), &ps); | 1954 EndPaint(hwnd(), &ps); |
1919 } | 1955 } |
1920 | 1956 |
1921 LRESULT HWNDMessageHandler::OnReflectedMessage(UINT message, | 1957 LRESULT HWNDMessageHandler::OnReflectedMessage(UINT message, |
1922 WPARAM w_param, | 1958 WPARAM w_param, |
1923 LPARAM l_param) { | 1959 LPARAM l_param) { |
1924 SetMsgHandled(FALSE); | 1960 SetMsgHandled(FALSE); |
1925 return 0; | 1961 return 0; |
1926 } | 1962 } |
1927 | 1963 |
| 1964 LRESULT HWNDMessageHandler::OnScrollMessage(UINT message, |
| 1965 WPARAM w_param, |
| 1966 LPARAM l_param) { |
| 1967 MSG msg = { hwnd(), message, w_param, l_param, GetMessageTime() }; |
| 1968 ui::ScrollEvent event(msg); |
| 1969 delegate_->HandleScrollEvent(event); |
| 1970 return 0; |
| 1971 } |
| 1972 |
1928 LRESULT HWNDMessageHandler::OnSetCursor(UINT message, | 1973 LRESULT HWNDMessageHandler::OnSetCursor(UINT message, |
1929 WPARAM w_param, | 1974 WPARAM w_param, |
1930 LPARAM l_param) { | 1975 LPARAM l_param) { |
1931 // Reimplement the necessary default behavior here. Calling DefWindowProc can | 1976 // Reimplement the necessary default behavior here. Calling DefWindowProc can |
1932 // trigger weird non-client painting for non-glass windows with custom frames. | 1977 // trigger weird non-client painting for non-glass windows with custom frames. |
1933 // Using a ScopedRedrawLock to prevent caption rendering artifacts may allow | 1978 // Using a ScopedRedrawLock to prevent caption rendering artifacts may allow |
1934 // content behind this window to incorrectly paint in front of this window. | 1979 // content behind this window to incorrectly paint in front of this window. |
1935 // Invalidating the window to paint over either set of artifacts is not ideal. | 1980 // Invalidating the window to paint over either set of artifacts is not ideal. |
1936 wchar_t* cursor = IDC_ARROW; | 1981 wchar_t* cursor = IDC_ARROW; |
1937 switch (LOWORD(l_param)) { | 1982 switch (LOWORD(l_param)) { |
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1995 delegate_->HandleWorkAreaChanged(); | 2040 delegate_->HandleWorkAreaChanged(); |
1996 SetMsgHandled(FALSE); | 2041 SetMsgHandled(FALSE); |
1997 } | 2042 } |
1998 } | 2043 } |
1999 | 2044 |
2000 void HWNDMessageHandler::OnSize(UINT param, const CSize& size) { | 2045 void HWNDMessageHandler::OnSize(UINT param, const CSize& size) { |
2001 RedrawWindow(hwnd(), NULL, NULL, RDW_INVALIDATE | RDW_ALLCHILDREN); | 2046 RedrawWindow(hwnd(), NULL, NULL, RDW_INVALIDATE | RDW_ALLCHILDREN); |
2002 // ResetWindowRegion is going to trigger WM_NCPAINT. By doing it after we've | 2047 // ResetWindowRegion is going to trigger WM_NCPAINT. By doing it after we've |
2003 // invoked OnSize we ensure the RootView has been laid out. | 2048 // invoked OnSize we ensure the RootView has been laid out. |
2004 ResetWindowRegion(false, true); | 2049 ResetWindowRegion(false, true); |
| 2050 |
| 2051 #if defined(USE_AURA) |
| 2052 // We add the WS_VSCROLL and WS_HSCROLL styles to top level windows to ensure |
| 2053 // that legacy trackpad/trackpoint drivers generate the WM_VSCROLL and |
| 2054 // WM_HSCROLL messages and scrolling works. |
| 2055 // We want the style to be present on the window. However we don't want |
| 2056 // Windows to draw the scrollbars. To achieve this we hide the scroll bars |
| 2057 // and readd them to the window style in a posted task which works. |
| 2058 if (scroll_styles_set_) { |
| 2059 ShowScrollBar(hwnd(), SB_BOTH, FALSE); |
| 2060 base::MessageLoop::current()->PostTask( |
| 2061 FROM_HERE, |
| 2062 base::Bind(&AddScrollStylesToWindow, hwnd())); |
| 2063 #endif |
| 2064 } |
2005 } | 2065 } |
2006 | 2066 |
2007 void HWNDMessageHandler::OnSysCommand(UINT notification_code, | 2067 void HWNDMessageHandler::OnSysCommand(UINT notification_code, |
2008 const CPoint& point) { | 2068 const CPoint& point) { |
2009 if (!delegate_->ShouldHandleSystemCommands()) | 2069 if (!delegate_->ShouldHandleSystemCommands()) |
2010 return; | 2070 return; |
2011 | 2071 |
2012 // Windows uses the 4 lower order bits of |notification_code| for type- | 2072 // Windows uses the 4 lower order bits of |notification_code| for type- |
2013 // specific information so we must exclude this when comparing. | 2073 // specific information so we must exclude this when comparing. |
2014 static const int sc_mask = 0xFFF0; | 2074 static const int sc_mask = 0xFFF0; |
(...skipping 200 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2215 SetMsgHandled(FALSE); | 2275 SetMsgHandled(FALSE); |
2216 } | 2276 } |
2217 | 2277 |
2218 void HWNDMessageHandler::HandleTouchEvents(const TouchEvents& touch_events) { | 2278 void HWNDMessageHandler::HandleTouchEvents(const TouchEvents& touch_events) { |
2219 base::WeakPtr<HWNDMessageHandler> ref(weak_factory_.GetWeakPtr()); | 2279 base::WeakPtr<HWNDMessageHandler> ref(weak_factory_.GetWeakPtr()); |
2220 for (size_t i = 0; i < touch_events.size() && ref; ++i) | 2280 for (size_t i = 0; i < touch_events.size() && ref; ++i) |
2221 delegate_->HandleTouchEvent(touch_events[i]); | 2281 delegate_->HandleTouchEvent(touch_events[i]); |
2222 } | 2282 } |
2223 | 2283 |
2224 } // namespace views | 2284 } // namespace views |
OLD | NEW |