1ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen// Copyright (c) 2011 The Chromium Authors. All rights reserved. 2c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// Use of this source code is governed by a BSD-style license that can be 3c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// found in the LICENSE file. 4c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 5c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "chrome/browser/renderer_host/render_widget_host_view_win.h" 6c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 721d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen#include <algorithm> 821d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen 9c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "base/command_line.h" 10c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "base/i18n/rtl.h" 11731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick#include "base/metrics/histogram.h" 12c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "base/process_util.h" 133f50c38dc070f4bb515c1b64450dae14f316474eKristian Monsen#include "base/threading/thread.h" 14ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen#include "base/win/scoped_comptr.h" 1521d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen#include "base/win/scoped_gdi_object.h" 16ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen#include "base/win/wrapped_window_proc.h" 17731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick#include "chrome/browser/accessibility/browser_accessibility_manager.h" 18731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick#include "chrome/browser/accessibility/browser_accessibility_state.h" 19ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen#include "chrome/browser/accessibility/browser_accessibility_win.h" 20c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "chrome/browser/browser_trial.h" 21c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "chrome/common/chrome_constants.h" 22c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "chrome/common/chrome_switches.h" 23c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "chrome/common/render_messages.h" 24dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen#include "content/browser/browser_thread.h" 25dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen#include "content/browser/plugin_process_host.h" 26dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen#include "content/browser/renderer_host/backing_store.h" 27dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen#include "content/browser/renderer_host/backing_store_win.h" 28dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen#include "content/browser/renderer_host/render_process_host.h" 29dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen#include "content/browser/renderer_host/render_widget_host.h" 30ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen#include "content/common/native_web_keyboard_event.h" 31ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen#include "content/common/notification_service.h" 32ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen#include "content/common/plugin_messages.h" 33ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen#include "content/common/view_messages.h" 34c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "grit/webkit_resources.h" 35c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "skia/ext/skia_utils_win.h" 36ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen#include "third_party/WebKit/Source/WebKit/chromium/public/WebCompositionUnderline.h" 3772a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen#include "third_party/WebKit/Source/WebKit/chromium/public/WebInputEvent.h" 3872a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen#include "third_party/WebKit/Source/WebKit/chromium/public/win/WebInputEventFactory.h" 39ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen#include "ui/base/ime/composition_text.h" 4072a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen#include "ui/base/l10n/l10n_util.h" 4172a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen#include "ui/base/l10n/l10n_util_win.h" 4272a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen#include "ui/base/resource/resource_bundle.h" 4372a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen#include "ui/base/view_prop.h" 4472a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen#include "ui/base/win/hwnd_util.h" 4572a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen#include "ui/gfx/canvas.h" 4672a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen#include "ui/gfx/canvas_skia.h" 4772a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen#include "ui/gfx/gdi_util.h" 4872a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen#include "ui/gfx/rect.h" 49ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen#include "views/accessibility/native_view_accessibility_win.h" 50c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "views/focus/focus_manager.h" 51c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "views/focus/focus_util_win.h" 52c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// Included for views::kReflectedMessage - TODO(beng): move this to win_util.h! 53c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "views/widget/widget_win.h" 543345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick#include "webkit/glue/webaccessibility.h" 55c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "webkit/glue/webcursor.h" 5621d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen#include "webkit/plugins/npapi/plugin_constants_win.h" 5721d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen#include "webkit/plugins/npapi/webplugin.h" 58ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen#include "webkit/plugins/npapi/webplugin_delegate_impl.h" 59c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 60c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochusing base::TimeDelta; 61c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochusing base::TimeTicks; 6272a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsenusing ui::ViewProp; 63c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochusing WebKit::WebInputEvent; 64c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochusing WebKit::WebInputEventFactory; 65c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochusing WebKit::WebMouseEvent; 66c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochusing WebKit::WebTextDirection; 6721d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsenusing webkit::npapi::WebPluginGeometry; 68c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 69634420e363ef646c3b50a37b10d86a424b06ee49Ben Murdochconst wchar_t kRenderWidgetHostHWNDClass[] = L"Chrome_RenderWidgetHostHWND"; 70634420e363ef646c3b50a37b10d86a424b06ee49Ben Murdoch 71c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochnamespace { 72c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 73c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// Tooltips will wrap after this width. Yes, wrap. Imagine that! 74c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochconst int kTooltipMaxWidthPixels = 300; 75c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 76c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// Maximum number of characters we allow in a tooltip. 77c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochconst int kMaxTooltipLength = 1024; 78c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 79731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick// A custom MSAA object id used to determine if a screen reader is actively 80731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick// listening for MSAA events. 81731df977c0511bca2206b5f333555b1205ff1f43Iain Merrickconst int kIdCustom = 1; 82731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick 83ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen// The delay before the compositor host window is destroyed. This gives the GPU 84ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen// process a grace period to stop referencing it. 85ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsenconst int kDestroyCompositorHostWindowDelay = 10000; 86ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 87201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdochconst char* const kRenderWidgetHostViewKey = "__RENDER_WIDGET_HOST_VIEW__"; 88c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 89c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// A callback function for EnumThreadWindows to enumerate and dismiss 90c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// any owned popop windows 91c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochBOOL CALLBACK DismissOwnedPopups(HWND window, LPARAM arg) { 92c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch const HWND toplevel_hwnd = reinterpret_cast<HWND>(arg); 93c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 94c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (::IsWindowVisible(window)) { 95c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch const HWND owner = ::GetWindow(window, GW_OWNER); 96c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (toplevel_hwnd == owner) { 97c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ::PostMessage(window, WM_CANCELMODE, 0, 0); 98c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 99c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 100c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 101c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return TRUE; 102c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 103c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 104c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochclass NotifyPluginProcessHostTask : public Task { 105c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch public: 106c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch NotifyPluginProcessHostTask(HWND window, HWND parent) 107c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch : window_(window), parent_(parent), tries_(kMaxTries) { } 108c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 109c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch private: 110c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch void Run() { 111c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DWORD plugin_process_id; 112c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch bool found_starting_plugin_process = false; 113c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch GetWindowThreadProcessId(window_, &plugin_process_id); 114c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch for (BrowserChildProcessHost::Iterator iter( 115c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ChildProcessInfo::PLUGIN_PROCESS); 116c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch !iter.Done(); ++iter) { 117c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch PluginProcessHost* plugin = static_cast<PluginProcessHost*>(*iter); 118c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!plugin->handle()) { 119c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch found_starting_plugin_process = true; 120c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch continue; 121c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 122c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (base::GetProcId(plugin->handle()) == plugin_process_id) { 123c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch plugin->AddWindow(parent_); 124c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 125c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 126c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 127c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 128c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (found_starting_plugin_process) { 129c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // A plugin process has started but we don't have its handle yet. Since 130c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // it's most likely the one for this plugin, try a few more times after a 131c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // delay. 132c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (tries_--) { 133c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch MessageLoop::current()->PostDelayedTask(FROM_HERE, this, kTryDelayMs); 134c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 135c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 136c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 137c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 138c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // The plugin process might have died in the time to execute the task, don't 139c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // leak the HWND. 140c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch PostMessage(parent_, WM_CLOSE, 0, 0); 141c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 142c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 143c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HWND window_; // Plugin HWND, created and destroyed in the plugin process. 144c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HWND parent_; // Parent HWND, created and destroyed on the browser UI thread. 145c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 146c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch int tries_; 147c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 148c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // How many times we try to find a PluginProcessHost whose process matches 149c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // the HWND. 150c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch static const int kMaxTries = 5; 151c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // How long to wait between each try. 152c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch static const int kTryDelayMs = 200; 153c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch}; 154c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 155c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// Windows callback for OnDestroy to detach the plugin windows. 156c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochBOOL CALLBACK DetachPluginWindowsCallback(HWND window, LPARAM param) { 15721d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen if (webkit::npapi::WebPluginDelegateImpl::IsPluginDelegateWindow(window) && 158c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch !IsHungAppWindow(window)) { 159c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ::ShowWindow(window, SW_HIDE); 160c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SetParent(window, NULL); 161c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 162c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return TRUE; 163c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 164c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 165c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// Draw the contents of |backing_store_dc| onto |paint_rect| with a 70% grey 166c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// filter. 167201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdochvoid DrawDeemphasized(const SkColor& color, 168201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch const gfx::Rect& paint_rect, 169c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HDC backing_store_dc, 170c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HDC paint_dc) { 171c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch gfx::CanvasSkia canvas(paint_rect.width(), paint_rect.height(), true); 172c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HDC dc = canvas.beginPlatformPaint(); 173c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch BitBlt(dc, 174c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 0, 175c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 0, 176c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch paint_rect.width(), 177c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch paint_rect.height(), 178c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch backing_store_dc, 179c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch paint_rect.x(), 180c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch paint_rect.y(), 181c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SRCCOPY); 182c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch canvas.endPlatformPaint(); 183201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch canvas.FillRectInt(color, 0, 0, paint_rect.width(), paint_rect.height()); 184c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch canvas.getTopPlatformDevice().drawToHDC(paint_dc, paint_rect.x(), 185c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch paint_rect.y(), NULL); 186c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 187c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 188dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen// The plugin wrapper window which lives in the browser process has this proc 189dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen// as its window procedure. We only handle the WM_PARENTNOTIFY message sent by 190dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen// windowed plugins for mouse input. This is forwarded off to the wrappers 191dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen// parent which is typically the RVH window which turns on user gesture. 192dc0f95d653279beabeb9817299e2902918ba123eKristian MonsenLRESULT CALLBACK PluginWrapperWindowProc(HWND window, unsigned int message, 193dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen WPARAM wparam, LPARAM lparam) { 194dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen if (message == WM_PARENTNOTIFY) { 195dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen switch (LOWORD(wparam)) { 196dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen case WM_LBUTTONDOWN: 197dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen case WM_RBUTTONDOWN: 198dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen case WM_MBUTTONDOWN: 199dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen ::SendMessage(GetParent(window), message, wparam, lparam); 200dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen return 0; 201dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen default: 202dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen break; 203dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen } 204dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen } 205dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen return ::DefWindowProc(window, message, wparam, lparam); 206dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen} 207dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen 208c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} // namespace 209c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 210c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// RenderWidgetHostView -------------------------------------------------------- 211c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 212c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// static 213c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochRenderWidgetHostView* RenderWidgetHostView::CreateViewForWidget( 214c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch RenderWidgetHost* widget) { 215c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return new RenderWidgetHostViewWin(widget); 216c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 217c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 218c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch/////////////////////////////////////////////////////////////////////////////// 219c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// RenderWidgetHostViewWin, public: 220c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 221c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochRenderWidgetHostViewWin::RenderWidgetHostViewWin(RenderWidgetHost* widget) 222c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch : render_widget_host_(widget), 223201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch compositor_host_window_(NULL), 224ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen hide_compositor_window_at_next_paint_(false), 225c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch track_mouse_leave_(false), 226c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ime_notification_(false), 227c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch capture_enter_key_(false), 228c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch is_hidden_(false), 229c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch about_to_validate_and_paint_(false), 230c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch close_on_deactivate_(false), 231c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch being_destroyed_(false), 232c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tooltip_hwnd_(NULL), 233c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tooltip_showing_(false), 234c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch shutdown_factory_(this), 235c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch parent_hwnd_(NULL), 236c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch is_loading_(false), 237201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch overlay_color_(0), 238c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch text_input_type_(WebKit::WebTextInputTypeNone) { 239c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->set_view(this); 240c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch registrar_.Add(this, 241c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch NotificationType::RENDERER_PROCESS_TERMINATED, 242c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch NotificationService::AllSources()); 243c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 244c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 245c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochRenderWidgetHostViewWin::~RenderWidgetHostViewWin() { 246c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ResetTooltip(); 247c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 248c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 249c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::CreateWnd(HWND parent) { 250c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch Create(parent); // ATL function to create the window. 251c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 252c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 253c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch/////////////////////////////////////////////////////////////////////////////// 254c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// RenderWidgetHostViewWin, RenderWidgetHostView implementation: 255c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 256c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::InitAsPopup( 257c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch RenderWidgetHostView* parent_host_view, const gfx::Rect& pos) { 258c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch parent_hwnd_ = parent_host_view->GetNativeView(); 259c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch close_on_deactivate_ = true; 260c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch Create(parent_hwnd_, NULL, NULL, WS_POPUP, WS_EX_TOOLWINDOW); 261c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch MoveWindow(pos.x(), pos.y(), pos.width(), pos.height(), TRUE); 262c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Popups are not activated. 263c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ShowWindow(IsActivatable() ? SW_SHOW : SW_SHOWNA); 264c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 265c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 26672a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsenvoid RenderWidgetHostViewWin::InitAsFullscreen() { 2673345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick NOTIMPLEMENTED() << "Fullscreen not implemented on Win"; 2683345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick} 2693345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick 270c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochRenderWidgetHost* RenderWidgetHostViewWin::GetRenderWidgetHost() const { 271c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return render_widget_host_; 272c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 273c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 274c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::DidBecomeSelected() { 275c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!is_hidden_) 276c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 277c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 278c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (tab_switch_paint_time_.is_null()) 279c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tab_switch_paint_time_ = TimeTicks::Now(); 280c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch is_hidden_ = false; 281c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch EnsureTooltip(); 282c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->WasRestored(); 283c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 284c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 285c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::WasHidden() { 286c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (is_hidden_) 287c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 288c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 289c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // If we receive any more paint messages while we are hidden, we want to 290c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // ignore them so we don't re-allocate the backing store. We will paint 291c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // everything again when we become selected again. 292c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch is_hidden_ = true; 293c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 294c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ResetTooltip(); 295c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 296c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // If we have a renderer, then inform it that we are being hidden so it can 297c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // reduce its resource utilization. 298c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->WasHidden(); 299c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 300c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // TODO(darin): what about constrained windows? it doesn't look like they 301c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // see a message when their parent is hidden. maybe there is something more 302c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // generic we can do at the TabContents API level instead of relying on 303c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Windows messages. 304c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 305c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 306c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::SetSize(const gfx::Size& size) { 307ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen SetBounds(gfx::Rect(GetViewBounds().origin(), size)); 308ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen} 309ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 310ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsenvoid RenderWidgetHostViewWin::SetBounds(const gfx::Rect& rect) { 311c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (is_hidden_) 312c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 313c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 314ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // No SWP_NOREDRAW as autofill popups can move and the underneath window 315c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // should redraw in that case. 316c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch UINT swp_flags = SWP_NOSENDCHANGING | SWP_NOOWNERZORDER | SWP_NOCOPYBITS | 317ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen SWP_NOZORDER | SWP_NOACTIVATE | SWP_DEFERERASE; 318ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 319ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // If the style is not popup, you have to convert the point to client 320ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // coordinate. 321ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen POINT point = { rect.x(), rect.y() }; 322ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen if (GetStyle() & WS_CHILD) 323ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen ScreenToClient(&point); 324ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 325ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen SetWindowPos(NULL, point.x, point.y, rect.width(), rect.height(), swp_flags); 326c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->WasResized(); 327c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch EnsureTooltip(); 328c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 329c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 330c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochgfx::NativeView RenderWidgetHostViewWin::GetNativeView() { 331c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return m_hWnd; 332c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 333c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 334c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::MovePluginWindows( 335c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch const std::vector<WebPluginGeometry>& plugin_window_moves) { 336c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (plugin_window_moves.empty()) 337c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 338c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 339c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch bool oop_plugins = 340c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch !CommandLine::ForCurrentProcess()->HasSwitch(switches::kSingleProcess) && 341c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch !CommandLine::ForCurrentProcess()->HasSwitch(switches::kInProcessPlugins); 342c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 343c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HDWP defer_window_pos_info = 344c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ::BeginDeferWindowPos(static_cast<int>(plugin_window_moves.size())); 345c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 346c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!defer_window_pos_info) { 347c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch NOTREACHED(); 348c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 349c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 350c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 351c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch for (size_t i = 0; i < plugin_window_moves.size(); ++i) { 352c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch unsigned long flags = 0; 353c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch const WebPluginGeometry& move = plugin_window_moves[i]; 354c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HWND window = move.window; 355c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 356c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // As the plugin parent window which lives on the browser UI thread is 357c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // destroyed asynchronously, it is possible that we have a stale window 358c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // sent in by the renderer for moving around. 359c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Note: get the parent before checking if the window is valid, to avoid a 360c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // race condition where the window is destroyed after the check but before 361c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // the GetParent call. 362c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HWND parent = ::GetParent(window); 363c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!::IsWindow(window)) 364c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch continue; 365c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 366c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (oop_plugins) { 367c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (parent == m_hWnd) { 368c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // The plugin window is a direct child of this window, add an 369c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // intermediate window that lives on this thread to speed up scrolling. 370c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Note this only works with out of process plugins since we depend on 371c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // PluginProcessHost to destroy the intermediate HWNDs. 372c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch parent = ReparentWindow(window); 373c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ::ShowWindow(window, SW_SHOW); // Window was created hidden. 374c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } else if (::GetParent(parent) != m_hWnd) { 375c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // The renderer should only be trying to move windows that are children 376c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // of its render widget window. However, this may happen as a result of 377c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // a race condition, so we ignore it and not kill the plugin process. 378c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch continue; 379c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 380c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 381c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // We move the intermediate parent window which doesn't result in cross- 382c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // process synchronous Windows messages. 383c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch window = parent; 384c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 385c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 386c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (move.visible) 387c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch flags |= SWP_SHOWWINDOW; 388c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch else 389c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch flags |= SWP_HIDEWINDOW; 390c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 391c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (move.rects_valid) { 392c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HRGN hrgn = ::CreateRectRgn(move.clip_rect.x(), 393c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch move.clip_rect.y(), 394c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch move.clip_rect.right(), 395c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch move.clip_rect.bottom()); 396c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch gfx::SubtractRectanglesFromRegion(hrgn, move.cutout_rects); 397c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 398c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Note: System will own the hrgn after we call SetWindowRgn, 399c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // so we don't need to call DeleteObject(hrgn) 400c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ::SetWindowRgn(window, hrgn, !move.clip_rect.IsEmpty()); 401c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } else { 402c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch flags |= SWP_NOMOVE; 403c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch flags |= SWP_NOSIZE; 404c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 405c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 406c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch defer_window_pos_info = ::DeferWindowPos(defer_window_pos_info, 407c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch window, NULL, 408c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch move.window_rect.x(), 409c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch move.window_rect.y(), 410c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch move.window_rect.width(), 411c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch move.window_rect.height(), flags); 412c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!defer_window_pos_info) { 413c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DCHECK(false) << "DeferWindowPos failed, so all plugin moves ignored."; 414c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 415c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 416c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 417c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 418c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ::EndDeferWindowPos(defer_window_pos_info); 419c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 420c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 421c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochHWND RenderWidgetHostViewWin::ReparentWindow(HWND window) { 422c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch static ATOM window_class = 0; 423c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!window_class) { 424c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch WNDCLASSEX wcex; 425c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch wcex.cbSize = sizeof(WNDCLASSEX); 426c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch wcex.style = CS_DBLCLKS; 427ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen wcex.lpfnWndProc = base::win::WrappedWindowProc<PluginWrapperWindowProc>; 428c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch wcex.cbClsExtra = 0; 429c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch wcex.cbWndExtra = 0; 430c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch wcex.hInstance = GetModuleHandle(NULL); 431c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch wcex.hIcon = 0; 432c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch wcex.hCursor = 0; 433c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch wcex.hbrBackground = reinterpret_cast<HBRUSH>(COLOR_WINDOW+1); 434c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch wcex.lpszMenuName = 0; 43521d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen wcex.lpszClassName = webkit::npapi::kWrapperNativeWindowClassName; 436c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch wcex.hIconSm = 0; 437c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch window_class = RegisterClassEx(&wcex); 438c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 439c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DCHECK(window_class); 440c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 441c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HWND parent = CreateWindowEx( 442c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch WS_EX_LEFT | WS_EX_LTRREADING | WS_EX_RIGHTSCROLLBAR, 443c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch MAKEINTATOM(window_class), 0, 444ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen WS_CHILD | WS_CLIPCHILDREN | WS_CLIPSIBLINGS, 445c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 0, 0, 0, 0, ::GetParent(window), 0, GetModuleHandle(NULL), 0); 446ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen ui::CheckWindowCreated(parent); 447c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ::SetParent(window, parent); 448731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick BrowserThread::PostTask( 449731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick BrowserThread::IO, FROM_HERE, 450c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch new NotifyPluginProcessHostTask(window, parent)); 451c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return parent; 452c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 453c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 454201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdochstatic BOOL CALLBACK AddChildWindowToVector(HWND hwnd, LPARAM lparam) { 455201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch std::vector<HWND>* vector = reinterpret_cast<std::vector<HWND>*>(lparam); 456201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch vector->push_back(hwnd); 457201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch return TRUE; 458201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch} 459201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 460201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdochvoid RenderWidgetHostViewWin::CleanupCompositorWindow() { 461201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch if (!compositor_host_window_) 462201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch return; 463201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 464ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // Hide the compositor and parent it to the desktop rather than destroying 465ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // it immediately. The GPU process has a grace period to stop accessing the 466ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // window. TODO(apatrick): the GPU process should acknowledge that it has 467ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // finished with the window handle and the browser process should destroy it 468ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // at that point. 469ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen ::ShowWindow(compositor_host_window_, SW_HIDE); 470ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen ::SetParent(compositor_host_window_, NULL); 471ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 472ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen BrowserThread::PostDelayedTask( 473ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen BrowserThread::UI, 474ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen FROM_HERE, 475ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen NewRunnableFunction(::DestroyWindow, compositor_host_window_), 476ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen kDestroyCompositorHostWindowDelay); 477ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 478201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch compositor_host_window_ = NULL; 479201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch} 480201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 481c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochbool RenderWidgetHostViewWin::IsActivatable() const { 482c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Popups should not be activated. 483c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return popup_type_ == WebKit::WebPopupTypeNone; 484c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 485c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 486c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::Focus() { 487c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (IsWindow()) 488c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SetFocus(); 489c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 490c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 491c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::Blur() { 492c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch views::FocusManager* focus_manager = 493c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch views::FocusManager::GetFocusManagerForNativeView(m_hWnd); 494c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // We don't have a FocusManager if we are hidden. 495c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (focus_manager) 496c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch focus_manager->ClearFocus(); 497c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 498c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 499c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochbool RenderWidgetHostViewWin::HasFocus() { 500c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return ::GetFocus() == m_hWnd; 501c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 502c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 503c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::Show() { 504c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DCHECK(parent_hwnd_); 505c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DCHECK(parent_hwnd_ != GetDesktopWindow()); 506c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SetParent(parent_hwnd_); 507c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ShowWindow(SW_SHOW); 508c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 50972a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen // Save away our HWND in the parent window as a property so that the 51072a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen // accessibility code can find it. 511ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen accessibility_prop_.reset(new ViewProp( 512ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen GetParent(), 513ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen views::kViewsNativeHostPropForAccessibility, 514ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen m_hWnd)); 51572a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen 516c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DidBecomeSelected(); 517c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 518c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 519c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::Hide() { 520c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (GetParent() == GetDesktopWindow()) { 521c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch LOG(WARNING) << "Hide() called twice in a row: " << this << ":" << 522c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch parent_hwnd_ << ":" << GetParent(); 523c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 524c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 525c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 52672a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen accessibility_prop_.reset(); 52772a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen 528c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (::GetFocus() == m_hWnd) 529c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ::SetFocus(NULL); 530c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ShowWindow(SW_HIDE); 531c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 532c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Cache the old parent, then orphan the window so we stop receiving messages 533c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch parent_hwnd_ = GetParent(); 534c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SetParent(NULL); 535c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 536c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch WasHidden(); 537c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 538c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 539c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochbool RenderWidgetHostViewWin::IsShowing() { 540c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return !!IsWindowVisible(); 541c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 542c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 543c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochgfx::Rect RenderWidgetHostViewWin::GetViewBounds() const { 544c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch CRect window_rect; 545c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch GetWindowRect(&window_rect); 546c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return gfx::Rect(window_rect); 547c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 548c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 549c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::UpdateCursor(const WebCursor& cursor) { 550c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch current_cursor_ = cursor; 551c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch UpdateCursorIfOverSelf(); 552c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 553c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 554c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::UpdateCursorIfOverSelf() { 555c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch static HCURSOR kCursorArrow = LoadCursor(NULL, IDC_ARROW); 556c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch static HCURSOR kCursorAppStarting = LoadCursor(NULL, IDC_APPSTARTING); 557c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch static HINSTANCE module_handle = 558c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch GetModuleHandle(chrome::kBrowserResourcesDll); 559c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 560c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // If the mouse is over our HWND, then update the cursor state immediately. 561c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch CPoint pt; 562c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch GetCursorPos(&pt); 563c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (WindowFromPoint(pt) == m_hWnd) { 564c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch BOOL result = ::ScreenToClient(m_hWnd, &pt); 565c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DCHECK(result); 5664a5e2dc747d50c653511c68ccb2cfbfb740bd5a7Ben Murdoch // We cannot pass in NULL as the module handle as this would only work for 5674a5e2dc747d50c653511c68ccb2cfbfb740bd5a7Ben Murdoch // standard win32 cursors. We can also receive cursor types which are 5684a5e2dc747d50c653511c68ccb2cfbfb740bd5a7Ben Murdoch // defined as webkit resources. We need to specify the module handle of 5694a5e2dc747d50c653511c68ccb2cfbfb740bd5a7Ben Murdoch // chrome.dll while loading these cursors. 5704a5e2dc747d50c653511c68ccb2cfbfb740bd5a7Ben Murdoch HCURSOR display_cursor = current_cursor_.GetCursor(module_handle); 5714a5e2dc747d50c653511c68ccb2cfbfb740bd5a7Ben Murdoch 5724a5e2dc747d50c653511c68ccb2cfbfb740bd5a7Ben Murdoch // If a page is in the loading state, we want to show the Arrow+Hourglass 5734a5e2dc747d50c653511c68ccb2cfbfb740bd5a7Ben Murdoch // cursor only when the current cursor is the ARROW cursor. In all other 5744a5e2dc747d50c653511c68ccb2cfbfb740bd5a7Ben Murdoch // cases we should continue to display the current cursor. 5754a5e2dc747d50c653511c68ccb2cfbfb740bd5a7Ben Murdoch if (is_loading_ && display_cursor == kCursorArrow) 5764a5e2dc747d50c653511c68ccb2cfbfb740bd5a7Ben Murdoch display_cursor = kCursorAppStarting; 5774a5e2dc747d50c653511c68ccb2cfbfb740bd5a7Ben Murdoch 5784a5e2dc747d50c653511c68ccb2cfbfb740bd5a7Ben Murdoch SetCursor(display_cursor); 579c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 580c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 581c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 582c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::SetIsLoading(bool is_loading) { 583c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch is_loading_ = is_loading; 584c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch UpdateCursorIfOverSelf(); 585c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 586c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 587c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::ImeUpdateTextInputState( 588c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch WebKit::WebTextInputType type, 589c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch const gfx::Rect& caret_rect) { 590c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (text_input_type_ != type) { 591c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch text_input_type_ = type; 592c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (type == WebKit::WebTextInputTypeText) 593c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ime_input_.EnableIME(m_hWnd); 594c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch else 595c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ime_input_.DisableIME(m_hWnd); 596c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 597c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 598c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Only update caret position if the input method is enabled. 599c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (type == WebKit::WebTextInputTypeText) 600c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ime_input_.UpdateCaretRect(m_hWnd, caret_rect); 601c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 602c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 603c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::ImeCancelComposition() { 604c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ime_input_.CancelIME(m_hWnd); 605c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 606c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 607c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochBOOL CALLBACK EnumChildProc(HWND hwnd, LPARAM lparam) { 60821d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen if (!webkit::npapi::WebPluginDelegateImpl::IsPluginDelegateWindow(hwnd)) 609c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return TRUE; 610c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 611c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch gfx::Rect* rect = reinterpret_cast<gfx::Rect*>(lparam); 61221d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen static UINT msg = RegisterWindowMessage(webkit::npapi::kPaintMessageName); 613c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch WPARAM wparam = rect->x() << 16 | rect->y(); 614c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch lparam = rect->width() << 16 | rect->height(); 615c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 616c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // SendMessage gets the message across much quicker than PostMessage, since it 617c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // doesn't get queued. When the plugin thread calls PeekMessage or other 618c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Win32 APIs, sent messages are dispatched automatically. 619c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SendNotifyMessage(hwnd, msg, wparam, lparam); 620c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 621c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return TRUE; 622c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 623c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 624c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::Redraw() { 625c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch RECT damage_bounds; 626c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch GetUpdateRect(&damage_bounds, FALSE); 627c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 62821d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen base::win::ScopedGDIObject<HRGN> damage_region(CreateRectRgn(0, 0, 0, 0)); 629c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch GetUpdateRgn(damage_region, FALSE); 630c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 631c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Paint the invalid region synchronously. Our caller will not paint again 632c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // until we return, so by painting to the screen here, we ensure effective 633c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // rate-limiting of backing store updates. This helps a lot on pages that 634c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // have animations or fairly expensive layout (e.g., google maps). 635c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // 636c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // We paint this window synchronously, however child windows (i.e. plugins) 637c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // are painted asynchronously. By avoiding synchronous cross-process window 638c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // message dispatching we allow scrolling to be smooth, and also avoid the 639c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // browser process locking up if the plugin process is hung. 640c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // 641c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch RedrawWindow(NULL, damage_region, RDW_UPDATENOW | RDW_NOCHILDREN); 642c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 643c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Send the invalid rect in screen coordinates. 644c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch gfx::Rect screen_rect = GetViewBounds(); 645c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch gfx::Rect invalid_screen_rect(damage_bounds); 646c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch invalid_screen_rect.Offset(screen_rect.x(), screen_rect.y()); 647c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 648c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch LPARAM lparam = reinterpret_cast<LPARAM>(&invalid_screen_rect); 649c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch EnumChildWindows(m_hWnd, EnumChildProc, lparam); 650c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 651c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 652c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::DidUpdateBackingStore( 653c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch const gfx::Rect& scroll_rect, int scroll_dx, int scroll_dy, 654c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch const std::vector<gfx::Rect>& copy_rects) { 655c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (is_hidden_) 656c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 657c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 658c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Schedule invalidations first so that the ScrollWindowEx call is closer to 659c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Redraw. That minimizes chances of "flicker" resulting if the screen 660c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // refreshes before we have a chance to paint the exposed area. Somewhat 661c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // surprisingly, this ordering matters. 662c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 663c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch for (size_t i = 0; i < copy_rects.size(); ++i) 664c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch InvalidateRect(©_rects[i].ToRECT(), false); 665c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 666c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!scroll_rect.IsEmpty()) { 667c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch RECT clip_rect = scroll_rect.ToRECT(); 668c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ScrollWindowEx(scroll_dx, scroll_dy, NULL, &clip_rect, NULL, NULL, 669c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SW_INVALIDATE); 670c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 671c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 672c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!about_to_validate_and_paint_) 673c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch Redraw(); 674c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 675c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 67621d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsenvoid RenderWidgetHostViewWin::RenderViewGone(base::TerminationStatus status, 67721d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen int error_code) { 678c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // TODO(darin): keep this around, and draw sad-tab into it. 679c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch UpdateCursorIfOverSelf(); 680c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch being_destroyed_ = true; 681201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch CleanupCompositorWindow(); 682c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DestroyWindow(); 683c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 684c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 685201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdochvoid RenderWidgetHostViewWin::WillWmDestroy() { 686201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch CleanupCompositorWindow(); 687201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch} 688201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 689c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::WillDestroyRenderWidget(RenderWidgetHost* rwh) { 690c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (rwh == render_widget_host_) 691c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_ = NULL; 692c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 693c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 694c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::Destroy() { 695c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // We've been told to destroy. 696c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // By clearing close_on_deactivate_, we prevent further deactivations 697c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // (caused by windows messages resulting from the DestroyWindow) from 698c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // triggering further destructions. The deletion of this is handled by 699c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // OnFinalMessage(); 700c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch close_on_deactivate_ = false; 701c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch being_destroyed_ = true; 702201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch CleanupCompositorWindow(); 703c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DestroyWindow(); 704c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 705c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 706c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::SetTooltipText(const std::wstring& tooltip_text) { 707c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Clamp the tooltip length to kMaxTooltipLength so that we don't 708c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // accidentally DOS the user with a mega tooltip (since Windows doesn't seem 709c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // to do this itself). 710c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch const std::wstring& new_tooltip_text = 711c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch l10n_util::TruncateString(tooltip_text, kMaxTooltipLength); 712c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 713c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (new_tooltip_text != tooltip_text_) { 714c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tooltip_text_ = new_tooltip_text; 715c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 716c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Need to check if the tooltip is already showing so that we don't 717c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // immediately show the tooltip with no delay when we move the mouse from 718c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // a region with no tooltip to a region with a tooltip. 719c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (::IsWindow(tooltip_hwnd_) && tooltip_showing_) { 720c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ::SendMessage(tooltip_hwnd_, TTM_POP, 0, 0); 721c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ::SendMessage(tooltip_hwnd_, TTM_POPUP, 0, 0); 722c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 723c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } else { 724c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Make sure the tooltip gets closed after TTN_POP gets sent. For some 725c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // reason this doesn't happen automatically, so moving the mouse around 726c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // within the same link/image/etc doesn't cause the tooltip to re-appear. 727c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!tooltip_showing_) { 728c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (::IsWindow(tooltip_hwnd_)) 729c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ::SendMessage(tooltip_hwnd_, TTM_POP, 0, 0); 730c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 731c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 732c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 733c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 734c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochBackingStore* RenderWidgetHostViewWin::AllocBackingStore( 735c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch const gfx::Size& size) { 736c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return new BackingStoreWin(render_widget_host_, size); 737c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 738c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 739c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::SetBackground(const SkBitmap& background) { 740c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch RenderWidgetHostView::SetBackground(background); 741c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch Send(new ViewMsg_SetBackground(render_widget_host_->routing_id(), 742c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch background)); 743c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 744c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 745c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochbool RenderWidgetHostViewWin::ContainsNativeView( 746c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch gfx::NativeView native_view) const { 747c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (m_hWnd == native_view) 748c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return true; 749c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 750c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Traverse the set of parents of the given view to determine if native_view 751c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // is a descendant of this window. 752c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HWND parent_window = ::GetParent(native_view); 753c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch while (parent_window) { 754c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (parent_window == m_hWnd) 755c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return true; 756c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch parent_window = ::GetParent(parent_window); 757c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 758c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 759c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return false; 760c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 761c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 762201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdochvoid RenderWidgetHostViewWin::SetVisuallyDeemphasized(const SkColor* color, 763201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch bool animate) { 764201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch // |animate| is not yet implemented, and currently isn't used. 765201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch CHECK(!animate); 766201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 767201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch SkColor overlay_color = color ? *color : 0; 768201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch if (overlay_color_ == overlay_color) 769c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 770201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch overlay_color_ = overlay_color; 771c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 772c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch InvalidateRect(NULL, FALSE); 773c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 774c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 775c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch/////////////////////////////////////////////////////////////////////////////// 776c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// RenderWidgetHostViewWin, private: 777c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 778c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochLRESULT RenderWidgetHostViewWin::OnCreate(CREATESTRUCT* create_struct) { 779c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Call the WM_INPUTLANGCHANGE message handler to initialize the input locale 780c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // of a browser process. 781c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch OnInputLangChange(0, 0); 782c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Marks that window as supporting mouse-wheel messages rerouting so it is 783c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // scrolled when under the mouse pointer even if inactive. 784513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch props_.push_back(views::SetWindowSupportsRerouteMouseWheel(m_hWnd)); 785201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch props_.push_back(new ViewProp(m_hWnd, kRenderWidgetHostViewKey, 786201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch static_cast<RenderWidgetHostView*>(this))); 787dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen // Save away our HWND in the parent window as a property so that the 788dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen // accessibility code can find it. 789ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen accessibility_prop_.reset(new ViewProp( 790ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen GetParent(), 791ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen views::kViewsNativeHostPropForAccessibility, 792ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen m_hWnd)); 793dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen 794c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 0; 795c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 796c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 797c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::OnActivate(UINT action, BOOL minimized, 798c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HWND window) { 799c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // If the container is a popup, clicking elsewhere on screen should close the 800c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // popup. 801c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (close_on_deactivate_ && action == WA_INACTIVE) { 802c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Send a windows message so that any derived classes 803c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // will get a change to override the default handling 804c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SendMessage(WM_CANCELMODE); 805c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 806c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 807c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 808c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::OnDestroy() { 809c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // When a tab is closed all its child plugin windows are destroyed 810c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // automatically. This happens before plugins get any notification that its 811c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // instances are tearing down. 812c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // 813c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Plugins like Quicktime assume that their windows will remain valid as long 814c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // as they have plugin instances active. Quicktime crashes in this case 815c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // because its windowing code cleans up an internal data structure that the 816c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // handler for NPP_DestroyStream relies on. 817c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // 818c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // The fix is to detach plugin windows from web contents when it is going 819c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // away. This will prevent the plugin windows from getting destroyed 820c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // automatically. The detached plugin windows will get cleaned up in proper 821c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // sequence as part of the usual cleanup when the plugin instance goes away. 822c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch EnumChildWindows(m_hWnd, DetachPluginWindowsCallback, NULL); 823c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 824513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch props_.reset(); 825c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 826201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch CleanupCompositorWindow(); 827201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 828c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ResetTooltip(); 829c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch TrackMouseLeave(false); 830c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 831c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 832c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::OnPaint(HDC unused_dc) { 833c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DCHECK(render_widget_host_->process()->HasConnection()); 834c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 835731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick // If the GPU process is rendering directly into the View, 836731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick // call the compositor directly. 837c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch RenderWidgetHost* render_widget_host = GetRenderWidgetHost(); 838201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch if (render_widget_host->is_accelerated_compositing_active()) { 839c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // We initialize paint_dc here so that BeginPaint()/EndPaint() 840c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // get called to validate the region. 841c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch CPaintDC paint_dc(m_hWnd); 842731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick render_widget_host_->ScheduleComposite(); 843c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 844c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 845c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 846c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch about_to_validate_and_paint_ = true; 847c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch BackingStoreWin* backing_store = static_cast<BackingStoreWin*>( 848c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->GetBackingStore(true)); 849c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 850c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // We initialize |paint_dc| (and thus call BeginPaint()) after calling 851c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // GetBackingStore(), so that if it updates the invalid rect we'll catch the 852c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // changes and repaint them. 853c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch about_to_validate_and_paint_ = false; 854c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 855c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Grab the region to paint before creation of paint_dc since it clears the 856c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // damage region. 85721d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen base::win::ScopedGDIObject<HRGN> damage_region(CreateRectRgn(0, 0, 0, 0)); 858c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch GetUpdateRgn(damage_region, FALSE); 859c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 860ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen if (hide_compositor_window_at_next_paint_) { 861ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen ::ShowWindow(compositor_host_window_, SW_HIDE); 862ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen hide_compositor_window_at_next_paint_ = false; 863ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen } 864ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 865c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch CPaintDC paint_dc(m_hWnd); 866c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 867c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch gfx::Rect damaged_rect(paint_dc.m_ps.rcPaint); 868c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (damaged_rect.IsEmpty()) 869c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 870c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 871c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (backing_store) { 872c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch gfx::Rect bitmap_rect(gfx::Point(), backing_store->size()); 873c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 874c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch bool manage_colors = BackingStoreWin::ColorManagementEnabled(); 875c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (manage_colors) 876c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SetICMMode(paint_dc.m_hDC, ICM_ON); 877c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 878c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Blit only the damaged regions from the backing store. 879c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DWORD data_size = GetRegionData(damage_region, 0, NULL); 880c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch scoped_array<char> region_data_buf(new char[data_size]); 881c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch RGNDATA* region_data = reinterpret_cast<RGNDATA*>(region_data_buf.get()); 882c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch GetRegionData(damage_region, data_size, region_data); 883c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 884c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch RECT* region_rects = reinterpret_cast<RECT*>(region_data->Buffer); 885c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch for (DWORD i = 0; i < region_data->rdh.nCount; ++i) { 886c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch gfx::Rect paint_rect = bitmap_rect.Intersect(gfx::Rect(region_rects[i])); 887c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!paint_rect.IsEmpty()) { 888201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch if (SkColorGetA(overlay_color_) > 0) { 889201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch DrawDeemphasized(overlay_color_, 890201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch paint_rect, 891201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch backing_store->hdc(), 892201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch paint_dc.m_hDC); 893c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } else { 894c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch BitBlt(paint_dc.m_hDC, 895c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch paint_rect.x(), 896c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch paint_rect.y(), 897c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch paint_rect.width(), 898c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch paint_rect.height(), 899c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch backing_store->hdc(), 900c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch paint_rect.x(), 901c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch paint_rect.y(), 902c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SRCCOPY); 903c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 904c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 905c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 906c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 907c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (manage_colors) 908c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SetICMMode(paint_dc.m_hDC, ICM_OFF); 909c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 910c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Fill the remaining portion of the damaged_rect with the background 911c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (damaged_rect.right() > bitmap_rect.right()) { 912c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch RECT r; 913c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch r.left = std::max(bitmap_rect.right(), damaged_rect.x()); 914c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch r.right = damaged_rect.right(); 915c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch r.top = damaged_rect.y(); 916c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch r.bottom = std::min(bitmap_rect.bottom(), damaged_rect.bottom()); 917c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DrawBackground(r, &paint_dc); 918c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 919c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (damaged_rect.bottom() > bitmap_rect.bottom()) { 920c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch RECT r; 921c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch r.left = damaged_rect.x(); 922c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch r.right = damaged_rect.right(); 923c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch r.top = std::max(bitmap_rect.bottom(), damaged_rect.y()); 924c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch r.bottom = damaged_rect.bottom(); 925c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DrawBackground(r, &paint_dc); 926c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 927c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!whiteout_start_time_.is_null()) { 928c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch TimeDelta whiteout_duration = TimeTicks::Now() - whiteout_start_time_; 929c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch UMA_HISTOGRAM_TIMES("MPArch.RWHH_WhiteoutDuration", whiteout_duration); 930c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 931c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Reset the start time to 0 so that we start recording again the next 932c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // time the backing store is NULL... 933c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch whiteout_start_time_ = TimeTicks(); 934c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 935c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!tab_switch_paint_time_.is_null()) { 936c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch TimeDelta tab_switch_paint_duration = TimeTicks::Now() - 937c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tab_switch_paint_time_; 938c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch UMA_HISTOGRAM_TIMES("MPArch.RWH_TabSwitchPaintDuration", 939c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tab_switch_paint_duration); 940c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Reset tab_switch_paint_time_ to 0 so future tab selections are 941c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // recorded. 942c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tab_switch_paint_time_ = TimeTicks(); 943c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 944c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } else { 945c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DrawBackground(paint_dc.m_ps.rcPaint, &paint_dc); 946c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (whiteout_start_time_.is_null()) 947c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch whiteout_start_time_ = TimeTicks::Now(); 948c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 949c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 950c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 951c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::DrawBackground(const RECT& dirty_rect, 952c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch CPaintDC* dc) { 953c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!background_.empty()) { 954c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch gfx::CanvasSkia canvas(dirty_rect.right - dirty_rect.left, 955c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch dirty_rect.bottom - dirty_rect.top, 956c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch true); // opaque 957c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch canvas.TranslateInt(-dirty_rect.left, -dirty_rect.top); 958c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 959c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch const RECT& dc_rect = dc->m_ps.rcPaint; 960c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch canvas.TileImageInt(background_, 0, 0, 961c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch dc_rect.right - dc_rect.left, 962c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch dc_rect.bottom - dc_rect.top); 963c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 964c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch canvas.getTopPlatformDevice().drawToHDC(*dc, dirty_rect.left, 965c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch dirty_rect.top, NULL); 966c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } else { 967c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HBRUSH white_brush = reinterpret_cast<HBRUSH>(GetStockObject(WHITE_BRUSH)); 968c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch dc->FillRect(&dirty_rect, white_brush); 969c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 970c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 971c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 972c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::OnNCPaint(HRGN update_region) { 973c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Do nothing. This suppresses the resize corner that Windows would 974c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // otherwise draw for us. 975c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 976c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 977c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochLRESULT RenderWidgetHostViewWin::OnEraseBkgnd(HDC dc) { 978c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 1; 979c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 980c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 981c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochLRESULT RenderWidgetHostViewWin::OnSetCursor(HWND window, UINT hittest_code, 982c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch UINT mouse_message_id) { 983c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch UpdateCursorIfOverSelf(); 984c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 0; 985c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 986c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 987c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::OnSetFocus(HWND window) { 988c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch views::FocusManager::GetWidgetFocusManager()->OnWidgetFocusEvent(window, 989c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch m_hWnd); 990731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick if (browser_accessibility_manager_.get()) 991731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick browser_accessibility_manager_->GotFocus(); 992c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (render_widget_host_) 993c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->GotFocus(); 994c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 995c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 996c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::OnKillFocus(HWND window) { 997c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch views::FocusManager::GetWidgetFocusManager()->OnWidgetFocusEvent(m_hWnd, 998c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch window); 999c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1000c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (render_widget_host_) 1001c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->Blur(); 1002c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1003c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1004c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::OnCaptureChanged(HWND window) { 1005c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (render_widget_host_) 1006c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->LostCapture(); 1007c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1008c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1009c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::OnCancelMode() { 1010c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (render_widget_host_) 1011c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->LostCapture(); 1012c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1013c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (close_on_deactivate_ && shutdown_factory_.empty()) { 1014c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Dismiss popups and menus. We do this asynchronously to avoid changing 1015c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // activation within this callstack, which may interfere with another window 1016c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // being activated. We can synchronously hide the window, but we need to 1017c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // not change activation while doing so. 1018c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SetWindowPos(NULL, 0, 0, 0, 0, 1019c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SWP_HIDEWINDOW | SWP_NOACTIVATE | SWP_NOMOVE | 1020c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SWP_NOREPOSITION | SWP_NOSIZE | SWP_NOZORDER); 1021c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch MessageLoop::current()->PostTask(FROM_HERE, 1022c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch shutdown_factory_.NewRunnableMethod( 1023c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch &RenderWidgetHostViewWin::ShutdownHost)); 1024c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1025c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1026c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1027c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::OnInputLangChange(DWORD character_set, 1028c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HKL input_language_id) { 1029c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Send the given Locale ID to the ImeInput object and retrieves whether 1030c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // or not the current input context has IMEs. 1031c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // If the current input context has IMEs, a browser process has to send a 1032c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // request to a renderer process that it needs status messages about 1033c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // the focused edit control from the renderer process. 1034c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // On the other hand, if the current input context does not have IMEs, the 1035c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // browser process also has to send a request to the renderer process that 1036c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // it does not need the status messages any longer. 1037c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // To minimize the number of this notification request, we should check if 1038c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // the browser process is actually retrieving the status messages (this 1039c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // state is stored in ime_notification_) and send a request only if the 1040c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // browser process has to update this status, its details are listed below: 1041c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // * If a browser process is not retrieving the status messages, 1042c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // (i.e. ime_notification_ == false), 1043c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // send this request only if the input context does have IMEs, 1044c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // (i.e. ime_status == true); 1045c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // When it successfully sends the request, toggle its notification status, 1046c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // (i.e.ime_notification_ = !ime_notification_ = true). 1047c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // * If a browser process is retrieving the status messages 1048c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // (i.e. ime_notification_ == true), 1049c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // send this request only if the input context does not have IMEs, 1050c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // (i.e. ime_status == false). 1051c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // When it successfully sends the request, toggle its notification status, 1052c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // (i.e.ime_notification_ = !ime_notification_ = false). 1053c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // To analyze the above actions, we can optimize them into the ones 1054c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // listed below: 1055c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // 1 Sending a request only if ime_status_ != ime_notification_, and; 1056c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // 2 Copying ime_status to ime_notification_ if it sends the request 1057c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // successfully (because Action 1 shows ime_status = !ime_notification_.) 1058c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch bool ime_status = ime_input_.SetInputLanguage(); 1059c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (ime_status != ime_notification_) { 1060c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (render_widget_host_) { 1061c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->SetInputMethodActive(ime_status); 1062c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ime_notification_ = ime_status; 1063c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1064c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1065c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1066c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1067c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::OnThemeChanged() { 1068c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (render_widget_host_) 1069c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->SystemThemeChanged(); 1070c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1071c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1072c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochLRESULT RenderWidgetHostViewWin::OnNotify(int w_param, NMHDR* header) { 1073c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (tooltip_hwnd_ == NULL) 1074c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 0; 1075c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1076c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch switch (header->code) { 1077c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch case TTN_GETDISPINFO: { 1078c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch NMTTDISPINFOW* tooltip_info = reinterpret_cast<NMTTDISPINFOW*>(header); 1079c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tooltip_info->szText[0] = L'\0'; 1080c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tooltip_info->lpszText = const_cast<wchar_t*>(tooltip_text_.c_str()); 1081c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ::SendMessage( 1082c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tooltip_hwnd_, TTM_SETMAXTIPWIDTH, 0, kTooltipMaxWidthPixels); 1083c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SetMsgHandled(TRUE); 1084c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch break; 1085c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1086c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch case TTN_POP: 1087c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tooltip_showing_ = false; 1088c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SetMsgHandled(TRUE); 1089c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch break; 1090c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch case TTN_SHOW: 1091c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tooltip_showing_ = true; 1092c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SetMsgHandled(TRUE); 1093c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch break; 1094c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1095c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 0; 1096c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1097c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1098c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochLRESULT RenderWidgetHostViewWin::OnImeSetContext( 1099c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch UINT message, WPARAM wparam, LPARAM lparam, BOOL& handled) { 1100c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!render_widget_host_) 1101c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 0; 1102c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1103c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // We need status messages about the focused input control from a 1104c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // renderer process when: 1105c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // * the current input context has IMEs, and; 1106c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // * an application is activated. 1107c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // This seems to tell we should also check if the current input context has 1108c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // IMEs before sending a request, however, this WM_IME_SETCONTEXT is 1109c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // fortunately sent to an application only while the input context has IMEs. 1110c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Therefore, we just start/stop status messages according to the activation 1111c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // status of this application without checks. 1112c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch bool activated = (wparam == TRUE); 1113c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (render_widget_host_) { 1114c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->SetInputMethodActive(activated); 1115c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ime_notification_ = activated; 1116c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1117c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1118c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (ime_notification_) 1119c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ime_input_.CreateImeWindow(m_hWnd); 1120c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1121c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ime_input_.CleanupComposition(m_hWnd); 1122ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen return ime_input_.SetImeWindowStyle( 1123ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen m_hWnd, message, wparam, lparam, &handled); 1124c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1125c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1126c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochLRESULT RenderWidgetHostViewWin::OnImeStartComposition( 1127c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch UINT message, WPARAM wparam, LPARAM lparam, BOOL& handled) { 1128c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!render_widget_host_) 1129c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 0; 1130c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1131c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Reset the composition status and create IME windows. 1132c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ime_input_.CreateImeWindow(m_hWnd); 1133c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ime_input_.ResetComposition(m_hWnd); 1134c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // We have to prevent WTL from calling ::DefWindowProc() because the function 1135c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // calls ::ImmSetCompositionWindow() and ::ImmSetCandidateWindow() to 1136c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // over-write the position of IME windows. 1137c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch handled = TRUE; 1138c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 0; 1139c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1140c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1141c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochLRESULT RenderWidgetHostViewWin::OnImeComposition( 1142c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch UINT message, WPARAM wparam, LPARAM lparam, BOOL& handled) { 1143c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!render_widget_host_) 1144c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 0; 1145c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1146c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // At first, update the position of the IME window. 1147c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ime_input_.UpdateImeWindow(m_hWnd); 1148c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1149ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // ui::CompositionUnderline should be identical to 1150ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // WebKit::WebCompositionUnderline, so that we can do reinterpret_cast safely. 1151ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen COMPILE_ASSERT(sizeof(ui::CompositionUnderline) == 1152ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen sizeof(WebKit::WebCompositionUnderline), 1153ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen ui_CompositionUnderline__WebKit_WebCompositionUnderline_diff); 1154ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 1155c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Retrieve the result string and its attributes of the ongoing composition 1156c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // and send it to a renderer process. 1157ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen ui::CompositionText composition; 1158ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen if (ime_input_.GetResult(m_hWnd, lparam, &composition.text)) { 1159ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen render_widget_host_->ImeConfirmComposition(composition.text); 1160c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ime_input_.ResetComposition(m_hWnd); 1161c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Fall though and try reading the composition string. 1162c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Japanese IMEs send a message containing both GCS_RESULTSTR and 1163c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // GCS_COMPSTR, which means an ongoing composition has been finished 1164c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // by the start of another composition. 1165c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1166c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Retrieve the composition string and its attributes of the ongoing 1167c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // composition and send it to a renderer process. 1168c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (ime_input_.GetComposition(m_hWnd, lparam, &composition)) { 1169ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // TODO(suzhe): due to a bug of webkit, we can't use selection range with 1170ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // composition string. See: https://bugs.webkit.org/show_bug.cgi?id=37788 1171ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen composition.selection = ui::Range(composition.selection.end()); 1172ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen 1173ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // TODO(suzhe): convert both renderer_host and renderer to use 1174ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen // ui::CompositionText. 1175ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen const std::vector<WebKit::WebCompositionUnderline>& underlines = 1176ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen reinterpret_cast<const std::vector<WebKit::WebCompositionUnderline>&>( 1177ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen composition.underlines); 1178c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->ImeSetComposition( 1179ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen composition.text, underlines, 1180ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen composition.selection.start(), composition.selection.end()); 1181c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1182c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // We have to prevent WTL from calling ::DefWindowProc() because we do not 1183c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // want for the IMM (Input Method Manager) to send WM_IME_CHAR messages. 1184c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch handled = TRUE; 1185c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 0; 1186c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1187c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1188c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochLRESULT RenderWidgetHostViewWin::OnImeEndComposition( 1189c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch UINT message, WPARAM wparam, LPARAM lparam, BOOL& handled) { 1190c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!render_widget_host_) 1191c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 0; 1192c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1193c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (ime_input_.is_composing()) { 1194c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // A composition has been ended while there is an ongoing composition, 1195c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // i.e. the ongoing composition has been canceled. 1196c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // We need to reset the composition status both of the ImeInput object and 1197c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // of the renderer process. 1198c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->ImeCancelComposition(); 1199c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ime_input_.ResetComposition(m_hWnd); 1200c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1201c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ime_input_.DestroyImeWindow(m_hWnd); 1202c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Let WTL call ::DefWindowProc() and release its resources. 1203c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch handled = FALSE; 1204c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 0; 1205c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1206c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1207c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochLRESULT RenderWidgetHostViewWin::OnMouseEvent(UINT message, WPARAM wparam, 1208c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch LPARAM lparam, BOOL& handled) { 1209c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch handled = TRUE; 1210c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1211c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (::IsWindow(tooltip_hwnd_)) { 1212c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Forward mouse events through to the tooltip window 1213c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch MSG msg; 1214c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch msg.hwnd = m_hWnd; 1215c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch msg.message = message; 1216c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch msg.wParam = wparam; 1217c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch msg.lParam = lparam; 1218c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SendMessage(tooltip_hwnd_, TTM_RELAYEVENT, NULL, 1219c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch reinterpret_cast<LPARAM>(&msg)); 1220c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1221c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1222c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // TODO(jcampan): I am not sure if we should forward the message to the 1223c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // TabContents first in the case of popups. If we do, we would need to 1224c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // convert the click from the popup window coordinates to the TabContents' 1225c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // window coordinates. For now we don't forward the message in that case to 1226c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // address bug #907474. 1227c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Note: GetParent() on popup windows returns the top window and not the 1228c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // parent the window was created with (the parent and the owner of the popup 1229c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // is the first non-child view of the view that was specified to the create 1230c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // call). So the TabContents window would have to be specified to the 1231c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // RenderViewHostHWND as there is no way to retrieve it from the HWND. 1232c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!close_on_deactivate_) { // Don't forward if the container is a popup. 1233c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch switch (message) { 1234c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch case WM_LBUTTONDOWN: 1235c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch case WM_MBUTTONDOWN: 1236c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch case WM_RBUTTONDOWN: 1237c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Finish the ongoing composition whenever a mouse click happens. 1238c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // It matches IE's behavior. 1239c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ime_input_.CleanupComposition(m_hWnd); 1240c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Fall through. 1241c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch case WM_MOUSEMOVE: 1242c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch case WM_MOUSELEAVE: { 1243c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Give the TabContents first crack at the message. It may want to 1244c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // prevent forwarding to the renderer if some higher level browser 1245c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // functionality is invoked. 1246c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch LPARAM parent_msg_lparam = lparam; 1247c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (message != WM_MOUSELEAVE) { 1248c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // For the messages except WM_MOUSELEAVE, before forwarding them to 1249c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // parent window, we should adjust cursor position from client 1250c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // coordinates in current window to client coordinates in its parent 1251c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // window. 1252c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch CPoint cursor_pos(GET_X_LPARAM(lparam), GET_Y_LPARAM(lparam)); 1253c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ClientToScreen(&cursor_pos); 1254c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch GetParent().ScreenToClient(&cursor_pos); 1255c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch parent_msg_lparam = MAKELPARAM(cursor_pos.x, cursor_pos.y); 1256c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1257c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (SendMessage(GetParent(), message, wparam, parent_msg_lparam) != 0) 1258c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 1; 1259c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1260c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1261c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1262c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1263c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ForwardMouseEventToRenderer(message, wparam, lparam); 1264c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 0; 1265c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1266c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1267c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochLRESULT RenderWidgetHostViewWin::OnKeyEvent(UINT message, WPARAM wparam, 1268c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch LPARAM lparam, BOOL& handled) { 1269c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch handled = TRUE; 1270c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1271c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // If we are a pop-up, forward tab related messages to our parent HWND, so 1272c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // that we are dismissed appropriately and so that the focus advance in our 1273c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // parent. 1274c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // TODO(jcampan): http://b/issue?id=1192881 Could be abstracted in the 1275c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // FocusManager. 1276c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (close_on_deactivate_ && 1277c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch (((message == WM_KEYDOWN || message == WM_KEYUP) && (wparam == VK_TAB)) || 1278c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch (message == WM_CHAR && wparam == L'\t'))) { 1279c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DCHECK(parent_hwnd_); 1280c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // First close the pop-up. 1281c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SendMessage(WM_CANCELMODE); 1282c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Then move the focus by forwarding the tab key to the parent. 1283c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return ::SendMessage(parent_hwnd_, message, wparam, lparam); 1284c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1285c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1286c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!render_widget_host_) 1287c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 0; 1288c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1289c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Bug 1845: we need to update the text direction when a user releases 1290c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // either a right-shift key or a right-control key after pressing both of 1291c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // them. So, we just update the text direction while a user is pressing the 1292c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // keys, and we notify the text direction when a user releases either of them. 1293c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Bug 9718: http://crbug.com/9718 To investigate IE and notepad, this 1294c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // shortcut is enabled only on a PC having RTL keyboard layouts installed. 1295c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // We should emulate them. 1296ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen if (ui::ImeInput::IsRTLKeyboardLayoutInstalled()) { 1297c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (message == WM_KEYDOWN) { 1298c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (wparam == VK_SHIFT) { 1299ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen base::i18n::TextDirection dir; 1300ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen if (ui::ImeInput::IsCtrlShiftPressed(&dir)) { 1301ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen render_widget_host_->UpdateTextDirection( 1302ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen dir == base::i18n::RIGHT_TO_LEFT ? 1303ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen WebKit::WebTextDirectionRightToLeft : 1304ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen WebKit::WebTextDirectionLeftToRight); 1305ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen } 1306c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } else if (wparam != VK_CONTROL) { 1307c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Bug 9762: http://crbug.com/9762 A user pressed a key except shift 1308c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // and control keys. 1309c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // When a user presses a key while he/she holds control and shift keys, 1310c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // we cancel sending an IPC message in NotifyTextDirection() below and 1311c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // ignore succeeding UpdateTextDirection() calls while we call 1312c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // NotifyTextDirection(). 1313c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // To cancel it, this call set a flag that prevents sending an IPC 1314c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // message in NotifyTextDirection() only if we are going to send it. 1315c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // It is harmless to call this function if we aren't going to send it. 1316c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->CancelUpdateTextDirection(); 1317c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1318c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } else if (message == WM_KEYUP && 1319c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch (wparam == VK_SHIFT || wparam == VK_CONTROL)) { 1320c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // We send an IPC message only if we need to update the text direction. 1321c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->NotifyTextDirection(); 1322c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1323c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1324c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1325c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Special processing for enter key: When user hits enter in omnibox 1326c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // we change focus to render host after the navigation, so repeat WM_KEYDOWNs 1327c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // and WM_KEYUP are going to render host, despite being initiated in other 1328c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // window. This code filters out these messages. 1329c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch bool ignore_keyboard_event = false; 1330c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (wparam == VK_RETURN) { 1331c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (message == WM_KEYDOWN || message == WM_SYSKEYDOWN) { 1332c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (KF_REPEAT & HIWORD(lparam)) { 1333c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // this is a repeated key 1334c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!capture_enter_key_) 1335c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ignore_keyboard_event = true; 1336c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } else { 1337c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch capture_enter_key_ = true; 1338c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1339c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } else if (message == WM_KEYUP || message == WM_SYSKEYUP) { 1340c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!capture_enter_key_) 1341c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ignore_keyboard_event = true; 1342c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch capture_enter_key_ = false; 1343c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } else { 1344c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Ignore all other keyboard events for the enter key if not captured. 1345c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!capture_enter_key_) 1346c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ignore_keyboard_event = true; 1347c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1348c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1349c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1350c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (render_widget_host_ && !ignore_keyboard_event) { 1351c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->ForwardKeyboardEvent( 1352c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch NativeWebKeyboardEvent(m_hWnd, message, wparam, lparam)); 1353c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1354c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 0; 1355c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1356c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1357c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochLRESULT RenderWidgetHostViewWin::OnWheelEvent(UINT message, WPARAM wparam, 1358c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch LPARAM lparam, BOOL& handled) { 1359c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Forward the mouse-wheel message to the window under the mouse if it belongs 1360c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // to us. 1361c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (message == WM_MOUSEWHEEL && 1362c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch views::RerouteMouseWheel(m_hWnd, wparam, lparam)) { 1363c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch handled = TRUE; 1364c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 0; 1365c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1366c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1367c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Workaround for Thinkpad mousewheel driver. We get mouse wheel/scroll 1368c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // messages even if we are not in the foreground. So here we check if 1369c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // we have any owned popup windows in the foreground and dismiss them. 1370c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (m_hWnd != GetForegroundWindow()) { 1371c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HWND toplevel_hwnd = ::GetAncestor(m_hWnd, GA_ROOT); 1372c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch EnumThreadWindows( 1373c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch GetCurrentThreadId(), 1374c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DismissOwnedPopups, 1375c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch reinterpret_cast<LPARAM>(toplevel_hwnd)); 1376c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1377c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1378c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // This is a bit of a hack, but will work for now since we don't want to 1379c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // pollute this object with TabContents-specific functionality... 1380c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch bool handled_by_TabContents = false; 1381c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (GetParent()) { 1382c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Use a special reflected message to break recursion. If we send 1383c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // WM_MOUSEWHEEL, the focus manager subclass of web contents will 1384c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // route it back here. 1385c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch MSG new_message = {0}; 1386c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch new_message.hwnd = m_hWnd; 1387c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch new_message.message = message; 1388c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch new_message.wParam = wparam; 1389c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch new_message.lParam = lparam; 1390c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1391c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch handled_by_TabContents = 1392c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch !!::SendMessage(GetParent(), views::kReflectedMessage, 0, 1393c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch reinterpret_cast<LPARAM>(&new_message)); 1394c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1395c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1396c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!handled_by_TabContents && render_widget_host_) { 1397c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->ForwardWheelEvent( 1398c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch WebInputEventFactory::mouseWheelEvent(m_hWnd, message, wparam, 1399c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch lparam)); 1400c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1401c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch handled = TRUE; 1402c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return 0; 1403c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1404c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 14053345a6884c488ff3a535c2c9acdd33d74b37e311Iain MerrickLRESULT RenderWidgetHostViewWin::OnMouseActivate(UINT message, 14063345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick WPARAM wparam, 14073345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick LPARAM lparam, 1408c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch BOOL& handled) { 1409c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!IsActivatable()) 1410c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return MA_NOACTIVATE; 1411c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1412c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HWND focus_window = GetFocus(); 1413c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!::IsWindow(focus_window) || !IsChild(focus_window)) { 1414c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // We handle WM_MOUSEACTIVATE to set focus to the underlying plugin 1415c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // child window. This is to ensure that keyboard events are received 1416c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // by the plugin. The correct way to fix this would be send over 1417c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // an event to the renderer which would then eventually send over 1418c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // a setFocus call to the plugin widget. This would ensure that 1419c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // the renderer (webkit) knows about the plugin widget receiving 1420c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // focus. 1421c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // TODO(iyengar) Do the right thing as per the above comment. 1422c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch POINT cursor_pos = {0}; 1423c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ::GetCursorPos(&cursor_pos); 1424c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ::ScreenToClient(m_hWnd, &cursor_pos); 1425c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HWND child_window = ::RealChildWindowFromPoint(m_hWnd, cursor_pos); 14263345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick if (::IsWindow(child_window) && child_window != m_hWnd) { 142772a454cd3513ac24fbdd0e0cb9ad70b86a99b801Kristian Monsen if (ui::GetClassName(child_window) == 142821d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen webkit::npapi::kWrapperNativeWindowClassName) 1429c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch child_window = ::GetWindow(child_window, GW_CHILD); 1430c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1431c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ::SetFocus(child_window); 1432c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return MA_NOACTIVATE; 1433c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1434c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1435c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch handled = FALSE; 14363345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick render_widget_host_->OnMouseActivate(); 1437c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return MA_ACTIVATE; 1438c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1439c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 14403345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrickvoid RenderWidgetHostViewWin::OnAccessibilityNotifications( 14413345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick const std::vector<ViewHostMsg_AccessibilityNotification_Params>& params) { 14423345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick if (!browser_accessibility_manager_.get()) { 14433345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick // Use empty document to process notifications 14443345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick webkit_glue::WebAccessibility empty_document; 14453345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick empty_document.role = WebAccessibility::ROLE_DOCUMENT; 14463345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick empty_document.state = 0; 14473345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick browser_accessibility_manager_.reset( 1448731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick BrowserAccessibilityManager::Create(m_hWnd, empty_document, this)); 1449c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1450c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 14513345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick browser_accessibility_manager_->OnAccessibilityNotifications(params); 1452c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1453c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1454c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::Observe(NotificationType type, 1455c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch const NotificationSource& source, 1456c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch const NotificationDetails& details) { 1457c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DCHECK(type == NotificationType::RENDERER_PROCESS_TERMINATED); 1458c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1459c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Get the RenderProcessHost that posted this notification, and exit 1460c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // if it's not the one associated with this host view. 1461c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch RenderProcessHost* render_process_host = 1462c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch Source<RenderProcessHost>(source).ptr(); 1463c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DCHECK(render_process_host); 1464c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!render_widget_host_ || 1465c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_process_host != render_widget_host_->process()) 1466c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 1467c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1468c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // If it was our RenderProcessHost that posted the notification, 1469c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // clear the BrowserAccessibilityManager, because the renderer is 1470c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // dead and any accessibility information we have is now stale. 1471c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch browser_accessibility_manager_.reset(NULL); 1472c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1473c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1474201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdochstatic void PaintCompositorHostWindow(HWND hWnd) { 1475201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch PAINTSTRUCT paint; 1476201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch BeginPaint(hWnd, &paint); 1477201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 1478201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch EndPaint(hWnd, &paint); 1479201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch} 1480201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 1481201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch// WndProc for the compositor host window. We use this instead of Default so 1482201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch// we can drop WM_PAINT and WM_ERASEBKGD messages on the floor. 1483201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdochstatic LRESULT CALLBACK CompositorHostWindowProc(HWND hWnd, UINT message, 1484201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch WPARAM wParam, LPARAM lParam) { 1485201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch switch (message) { 1486201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch case WM_ERASEBKGND: 1487201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch return 0; 1488201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch case WM_DESTROY: 1489201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch return 0; 1490201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch case WM_PAINT: 1491201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch PaintCompositorHostWindow(hWnd); 1492201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch return 0; 1493201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch default: 1494201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch return DefWindowProc(hWnd, message, wParam, lParam); 1495201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch } 1496201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch} 1497201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 1498201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch// Creates a HWND within the RenderWidgetHostView that will serve as a host 1499201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch// for a HWND that the GPU process will create. The host window is used 1500201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch// to Z-position the GPU's window relative to other plugin windows. 1501ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsengfx::PluginWindowHandle RenderWidgetHostViewWin::GetCompositingSurface() { 1502201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch // If the window has been created, don't recreate it a second time 1503201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch if (compositor_host_window_) 1504201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch return compositor_host_window_; 1505201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 1506201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch static ATOM window_class = 0; 1507201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch if (!window_class) { 1508201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch WNDCLASSEX wcex; 1509201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch wcex.cbSize = sizeof(WNDCLASSEX); 1510201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch wcex.style = 0; 1511ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen wcex.lpfnWndProc = 1512ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen base::win::WrappedWindowProc<CompositorHostWindowProc>; 1513201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch wcex.cbClsExtra = 0; 1514201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch wcex.cbWndExtra = 0; 1515201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch wcex.hInstance = GetModuleHandle(NULL); 1516201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch wcex.hIcon = 0; 1517201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch wcex.hCursor = 0; 1518201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch wcex.hbrBackground = NULL; 1519201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch wcex.lpszMenuName = 0; 1520201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch wcex.lpszClassName = L"CompositorHostWindowClass"; 1521201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch wcex.hIconSm = 0; 1522201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch window_class = RegisterClassEx(&wcex); 1523201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch DCHECK(window_class); 1524201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch } 1525201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 1526201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch RECT currentRect; 1527201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch GetClientRect(¤tRect); 1528201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch int width = currentRect.right - currentRect.left; 1529201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch int height = currentRect.bottom - currentRect.top; 1530201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 1531201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch compositor_host_window_ = CreateWindowEx( 1532201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch WS_EX_LEFT | WS_EX_LTRREADING | WS_EX_RIGHTSCROLLBAR, 1533201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch MAKEINTATOM(window_class), 0, 1534201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch WS_CHILD | WS_CLIPCHILDREN | WS_CLIPSIBLINGS | WS_DISABLED, 1535201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 0, 0, width, height, m_hWnd, 0, GetModuleHandle(NULL), 0); 1536ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen ui::CheckWindowCreated(compositor_host_window_); 1537201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 1538201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch return static_cast<gfx::PluginWindowHandle>(compositor_host_window_); 1539201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch} 1540201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 1541201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdochvoid RenderWidgetHostViewWin::ShowCompositorHostWindow(bool show) { 1542201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch // When we first create the compositor, we will get a show request from 1543201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch // the renderer before we have gotten the create request from the GPU. In this 1544201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch // case, simply ignore the show request. 1545201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch if (compositor_host_window_ == NULL) 1546201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch return; 1547201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 1548201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch if (show) { 1549ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen ::ShowWindow(compositor_host_window_, SW_SHOW); 1550201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 1551201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch // Get all the child windows of this view, including the compositor window. 1552201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch std::vector<HWND> all_child_windows; 1553201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch ::EnumChildWindows(m_hWnd, AddChildWindowToVector, 1554201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch reinterpret_cast<LPARAM>(&all_child_windows)); 1555201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 1556201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch // Build a list of just the plugin window handles 1557201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch std::vector<HWND> plugin_windows; 1558201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch bool compositor_host_window_found = false; 1559201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch for (size_t i = 0; i < all_child_windows.size(); ++i) { 1560201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch if (all_child_windows[i] != compositor_host_window_) 1561201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch plugin_windows.push_back(all_child_windows[i]); 1562201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch else 1563201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch compositor_host_window_found = true; 1564201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch } 1565201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch DCHECK(compositor_host_window_found); 1566201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 1567201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch // Set all the plugin windows to be "after" the compositor window. 1568201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch // When the compositor window is created, gets placed above plugins. 1569201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch for (size_t i = 0; i < plugin_windows.size(); ++i) { 1570201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch HWND next; 1571201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch if (i + 1 < plugin_windows.size()) 1572201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch next = plugin_windows[i+1]; 1573201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch else 1574201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch next = compositor_host_window_; 1575201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch ::SetWindowPos(plugin_windows[i], next, 0, 0, 0, 0, 1576201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch SWP_NOSIZE | SWP_NOMOVE | SWP_NOACTIVATE); 1577201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch } 1578201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch } else { 1579ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen hide_compositor_window_at_next_paint_ = true; 1580201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch } 1581201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch} 1582201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch 1583c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::SetAccessibilityFocus(int acc_obj_id) { 1584c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!browser_accessibility_manager_.get() || 1585c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch !render_widget_host_ || 1586c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch !render_widget_host_->process() || 1587c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch !render_widget_host_->process()->HasConnection()) { 1588c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 1589c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1590c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1591c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->SetAccessibilityFocus(acc_obj_id); 1592c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1593c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1594c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::AccessibilityDoDefaultAction(int acc_obj_id) { 1595c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!browser_accessibility_manager_.get() || 1596c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch !render_widget_host_ || 1597c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch !render_widget_host_->process() || 1598c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch !render_widget_host_->process()->HasConnection()) { 1599c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 1600c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1601c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1602c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->AccessibilityDoDefaultAction(acc_obj_id); 1603c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1604c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1605c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochLRESULT RenderWidgetHostViewWin::OnGetObject(UINT message, WPARAM wparam, 1606c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch LPARAM lparam, BOOL& handled) { 1607731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick if (kIdCustom == lparam) { 1608731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick // An MSAA client requestes our custom id. Assume that we have detected an 1609731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick // active windows screen reader. 161021d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen BrowserAccessibilityState::GetInstance()->OnScreenReaderDetected(); 1611731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick render_widget_host_->EnableRendererAccessibility(); 1612731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick 1613731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick // Return with failure. 1614731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick return static_cast<LRESULT>(0L); 1615731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick } 1616731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick 1617c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (lparam != OBJID_CLIENT) { 1618c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch handled = false; 1619c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return static_cast<LRESULT>(0L); 1620c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1621c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1622731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick if (render_widget_host_ && !render_widget_host_->renderer_accessible()) { 1623731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick // Attempt to detect screen readers by sending an event with our custom id. 1624731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick NotifyWinEvent(EVENT_SYSTEM_ALERT, m_hWnd, kIdCustom, CHILDID_SELF); 1625731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick } 1626c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1627731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick if (!browser_accessibility_manager_.get()) { 16283345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick // Return busy document tree while renderer accessibility tree loads. 16293345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick webkit_glue::WebAccessibility loading_tree; 16303345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick loading_tree.role = WebAccessibility::ROLE_DOCUMENT; 16313345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick loading_tree.state = (1 << WebAccessibility::STATE_BUSY); 16323345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick browser_accessibility_manager_.reset( 1633731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick BrowserAccessibilityManager::Create(m_hWnd, loading_tree, this)); 16343345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick } 1635c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1636ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen base::win::ScopedComPtr<IAccessible> root( 1637731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick browser_accessibility_manager_->GetRoot()->toBrowserAccessibilityWin()); 1638731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick if (root.get()) 1639731df977c0511bca2206b5f333555b1205ff1f43Iain Merrick return LresultFromObject(IID_IAccessible, wparam, root.Detach()); 1640c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1641c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch handled = false; 1642c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return static_cast<LRESULT>(0L); 1643c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1644c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1645dc0f95d653279beabeb9817299e2902918ba123eKristian MonsenLRESULT RenderWidgetHostViewWin::OnParentNotify(UINT message, WPARAM wparam, 1646dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen LPARAM lparam, BOOL& handled) { 1647dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen handled = FALSE; 1648dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen 1649dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen if (!render_widget_host_) 1650dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen return 0; 1651dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen 1652dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen switch (LOWORD(wparam)) { 1653dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen case WM_LBUTTONDOWN: 1654dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen case WM_RBUTTONDOWN: 1655dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen case WM_MBUTTONDOWN: 1656dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen render_widget_host_->StartUserGesture(); 1657dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen break; 1658dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen default: 1659dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen break; 1660dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen } 1661dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen return 0; 1662dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen} 1663dc0f95d653279beabeb9817299e2902918ba123eKristian Monsen 1664c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::OnFinalMessage(HWND window) { 1665c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // When the render widget host is being destroyed, it ends up calling 1666c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // WillDestroyRenderWidget (through the RENDER_WIDGET_HOST_DESTROYED 1667c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // notification) which NULLs render_widget_host_. 1668c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Note: the following bug http://crbug.com/24248 seems to report that 1669c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // OnFinalMessage is called with a deleted |render_widget_host_|. It is not 1670c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // clear how this could happen, hence the NULLing of render_widget_host_ 1671c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // above. 1672c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!render_widget_host_ && !being_destroyed_) { 1673c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // If you hit this NOTREACHED, please add a comment to report it on 1674c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // http://crbug.com/24248, including what you did when it happened and if 1675c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // you can repro. 1676c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch NOTREACHED(); 1677c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1678c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (render_widget_host_) 1679c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->ViewDestroyed(); 1680c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch delete this; 1681c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1682c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1683c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::TrackMouseLeave(bool track) { 1684c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (track == track_mouse_leave_) 1685c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 1686c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch track_mouse_leave_ = track; 1687c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1688c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DCHECK(m_hWnd); 1689c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1690c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch TRACKMOUSEEVENT tme; 1691c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tme.cbSize = sizeof(TRACKMOUSEEVENT); 1692c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tme.dwFlags = TME_LEAVE; 1693c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!track_mouse_leave_) 1694c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tme.dwFlags |= TME_CANCEL; 1695c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tme.hwndTrack = m_hWnd; 1696c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1697c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch TrackMouseEvent(&tme); 1698c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1699c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1700c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochbool RenderWidgetHostViewWin::Send(IPC::Message* message) { 1701c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!render_widget_host_) 1702c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return false; 1703c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return render_widget_host_->Send(message); 1704c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1705c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1706c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::EnsureTooltip() { 1707c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch UINT message = TTM_NEWTOOLRECT; 1708c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1709c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch TOOLINFO ti; 1710c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ti.cbSize = sizeof(ti); 1711c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ti.hwnd = m_hWnd; 1712c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ti.uId = 0; 1713c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!::IsWindow(tooltip_hwnd_)) { 1714c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch message = TTM_ADDTOOL; 1715c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tooltip_hwnd_ = CreateWindowEx( 1716c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch WS_EX_TRANSPARENT | l10n_util::GetExtendedTooltipStyles(), 1717c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch TOOLTIPS_CLASS, NULL, TTS_NOPREFIX, 0, 0, 0, 0, m_hWnd, NULL, 1718c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch NULL, NULL); 1719ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen ui::CheckWindowCreated(tooltip_hwnd_); 1720c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ti.uFlags = TTF_TRANSPARENT; 1721c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ti.lpszText = LPSTR_TEXTCALLBACK; 1722c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1723c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1724c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch CRect cr; 1725c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch GetClientRect(&ti.rect); 1726c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SendMessage(tooltip_hwnd_, message, NULL, reinterpret_cast<LPARAM>(&ti)); 1727c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1728c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1729c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::ResetTooltip() { 1730c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (::IsWindow(tooltip_hwnd_)) 1731c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ::DestroyWindow(tooltip_hwnd_); 1732c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch tooltip_hwnd_ = NULL; 1733c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1734c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1735c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::ForwardMouseEventToRenderer(UINT message, 1736c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch WPARAM wparam, 1737c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch LPARAM lparam) { 1738c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (!render_widget_host_) 1739c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return; 1740c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1741c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch WebMouseEvent event( 1742c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch WebInputEventFactory::mouseEvent(m_hWnd, message, wparam, lparam)); 1743c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1744c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Send the event to the renderer before changing mouse capture, so that the 1745c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // capturelost event arrives after mouseup. 1746c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->ForwardMouseEvent(event); 1747c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1748c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch switch (event.type) { 1749c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch case WebInputEvent::MouseMove: 1750c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch TrackMouseLeave(true); 1751c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch break; 1752c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch case WebInputEvent::MouseLeave: 1753c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch TrackMouseLeave(false); 1754c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch break; 1755c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch case WebInputEvent::MouseDown: 1756c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SetCapture(); 1757c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch break; 1758c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch case WebInputEvent::MouseUp: 1759c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (GetCapture() == m_hWnd) 1760c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ReleaseCapture(); 1761c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch break; 1762c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1763c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1764c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (IsActivatable() && event.type == WebInputEvent::MouseDown) { 1765c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // This is a temporary workaround for bug 765011 to get focus when the 1766c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // mouse is clicked. This happens after the mouse down event is sent to 1767c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // the renderer because normally Windows does a WM_SETFOCUS after 1768c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // WM_LBUTTONDOWN. 1769c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch SetFocus(); 1770c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 1771c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1772c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1773c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochvoid RenderWidgetHostViewWin::ShutdownHost() { 1774c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch shutdown_factory_.RevokeAll(); 1775c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch if (render_widget_host_) 1776c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch render_widget_host_->Shutdown(); 1777c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Do not touch any members at this point, |this| has been deleted. 1778c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1779c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 1780c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// static 1781c407dc5cd9bdc5668497f21b26b09d988ab439deBen MurdochRenderWidgetHostView* 1782c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch RenderWidgetHostView::GetRenderWidgetHostViewFromNativeView( 1783c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch gfx::NativeView native_view) { 1784201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch return ::IsWindow(native_view) ? 1785201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch reinterpret_cast<RenderWidgetHostView*>( 1786201ade2fbba22bfb27ae029f4d23fca6ded109a0Ben Murdoch ViewProp::GetValue(native_view, kRenderWidgetHostViewKey)) : NULL; 1787c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch} 1788