blob: e3780ec0e09f100e001a3005992ad76a819d77da [file] [log] [blame]
[email protected]60a50072012-01-11 02:05:351// Copyright (c) 2012 The Chromium Authors. All rights reserved.
license.botbf09a502008-08-24 00:55:552// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
initial.commit09911bf2008-07-26 23:55:294
[email protected]2cff0052011-03-18 16:51:445#include "content/renderer/render_widget.h"
initial.commit09911bf2008-07-26 23:55:296
dcheng07945f632015-12-26 07:59:327#include <utility>
8
[email protected]c27dd4f2014-05-22 18:05:199#include "base/auto_reset.h"
[email protected]32876ae2011-11-15 22:25:2110#include "base/bind.h"
[email protected]4fb66842009-12-04 21:41:0011#include "base/command_line.h"
initial.commit09911bf2008-07-26 23:55:2912#include "base/logging.h"
avi1023d012015-12-25 02:39:1413#include "base/macros.h"
[email protected]3b63f8f42011-03-28 01:54:1514#include "base/memory/scoped_ptr.h"
[email protected]b256eca2013-07-11 10:57:4015#include "base/memory/singleton.h"
[email protected]aaf68892013-07-18 00:11:3016#include "base/message_loop/message_loop.h"
[email protected]835d7c82010-10-14 04:38:3817#include "base/metrics/histogram.h"
[email protected]aa4117f2011-12-09 22:19:2118#include "base/stl_util.h"
[email protected]74ebfb12013-06-07 20:48:0019#include "base/strings/utf_string_conversions.h"
[email protected]35b4f0c2014-06-26 16:55:2720#include "base/sys_info.h"
primiano9e38d552015-01-28 04:18:0121#include "base/trace_event/trace_event.h"
22#include "base/trace_event/trace_event_synthetic_delay.h"
[email protected]661eb9d2009-02-03 02:11:4823#include "build/build_config.h"
[email protected]681ccff2013-03-18 06:13:5224#include "cc/base/switches.h"
[email protected]adbe30f2013-10-11 21:12:3325#include "cc/debug/benchmark_instrumentation.h"
[email protected]7f0d825f2013-03-18 07:24:3026#include "cc/output/output_surface.h"
fsamuel78f86e42016-01-20 04:10:2327#include "cc/scheduler/begin_frame_source.h"
[email protected]556fd292013-03-18 08:03:0428#include "cc/trees/layer_tree_host.h"
alexclarke7fa93942015-10-21 15:37:1129#include "components/scheduler/renderer/render_widget_scheduling_state.h"
alexclarke7819e2552015-06-03 11:17:2130#include "components/scheduler/renderer/renderer_scheduler.h"
[email protected]29e2fb42013-07-19 01:13:4731#include "content/child/npapi/webplugin.h"
oshima750cb4342015-10-31 00:59:0132#include "content/common/content_switches_internal.h"
[email protected]0634cdd42013-08-16 00:46:0933#include "content/common/gpu/client/context_provider_command_buffer.h"
[email protected]ed7defa2013-03-12 21:29:5934#include "content/common/gpu/client/webgraphicscontext3d_command_buffer_impl.h"
[email protected]96ab016c2013-10-23 00:50:2935#include "content/common/gpu/gpu_process_launch_causes.h"
[email protected]9017d7852013-11-21 17:47:3536#include "content/common/input/synthetic_gesture_packet.h"
[email protected]8e299aa2013-10-16 18:17:4437#include "content/common/input/web_input_event_traits.h"
[email protected]c084330e02013-04-27 01:08:1538#include "content/common/input_messages.h"
[email protected]992db4c2011-05-12 15:37:1539#include "content/common/swapped_out_messages.h"
[email protected]778574e2011-03-21 22:03:5040#include "content/common/view_messages.h"
[email protected]c08950d22011-10-13 22:20:2941#include "content/public/common/content_switches.h"
[email protected]a09d53ce2014-01-31 00:46:4242#include "content/public/common/context_menu_params.h"
[email protected]953bd0062013-08-01 00:58:4043#include "content/renderer/cursor_utils.h"
mfomitchev2600fd7c2016-02-17 20:53:3944#include "content/renderer/devtools/render_widget_screen_metrics_emulator.h"
[email protected]b2e4c70132013-10-03 02:07:5145#include "content/renderer/external_popup_menu.h"
[email protected]ed7defa2013-03-12 21:29:5946#include "content/renderer/gpu/compositor_output_surface.h"
[email protected]36e5ff12013-06-11 12:19:2947#include "content/renderer/gpu/delegated_compositor_output_surface.h"
[email protected]586871b2014-07-22 17:05:1148#include "content/renderer/gpu/frame_swap_message_queue.h"
[email protected]ed7defa2013-03-12 21:29:5949#include "content/renderer/gpu/mailbox_output_surface.h"
[email protected]586871b2014-07-22 17:05:1150#include "content/renderer/gpu/queue_message_swap_promise.h"
[email protected]ba91a792013-02-06 09:48:2851#include "content/renderer/gpu/render_widget_compositor.h"
[email protected]66fca5bc2013-05-23 06:58:2952#include "content/renderer/ime_event_guard.h"
[email protected]7a72d452013-12-13 10:01:1353#include "content/renderer/input/input_handler_manager.h"
[email protected]adab2332013-07-25 18:04:3254#include "content/renderer/pepper/pepper_plugin_instance_impl.h"
[email protected]bffc8302014-01-23 20:52:1655#include "content/renderer/render_frame_impl.h"
[email protected]e3244ed2014-06-20 20:04:2756#include "content/renderer/render_frame_proxy.h"
[email protected]8704f89b2011-04-15 00:30:0557#include "content/renderer/render_process.h"
[email protected]f1a29a02011-10-06 23:08:4458#include "content/renderer/render_thread_impl.h"
dcheng3ce04b62015-10-26 23:30:5559#include "content/renderer/render_view_impl.h"
tfarina556a7232014-10-05 01:02:0960#include "content/renderer/renderer_blink_platform_impl.h"
[email protected]5b45ad42013-10-25 00:42:0461#include "content/renderer/resizing_mode_selector.h"
[email protected]484955942010-08-19 16:13:1862#include "ipc/ipc_sync_message.h"
[email protected]661eb9d2009-02-03 02:11:4863#include "skia/ext/platform_canvas.h"
[email protected]ec173b522013-11-14 11:01:1864#include "third_party/WebKit/public/platform/WebCursorInfo.h"
[email protected]aaf68892013-07-18 00:11:3065#include "third_party/WebKit/public/platform/WebGraphicsContext3D.h"
donnda070f3c2015-01-16 19:54:1166#include "third_party/WebKit/public/platform/WebPoint.h"
[email protected]aaf68892013-07-18 00:11:3067#include "third_party/WebKit/public/platform/WebRect.h"
[email protected]ec173b522013-11-14 11:01:1868#include "third_party/WebKit/public/platform/WebScreenInfo.h"
[email protected]aaf68892013-07-18 00:11:3069#include "third_party/WebKit/public/platform/WebSize.h"
70#include "third_party/WebKit/public/platform/WebString.h"
[email protected]19193682014-04-03 15:01:4371#include "third_party/WebKit/public/web/WebDeviceEmulationParams.h"
kenrba7199832015-01-22 23:44:5972#include "third_party/WebKit/public/web/WebFrameWidget.h"
73#include "third_party/WebKit/public/web/WebLocalFrame.h"
donnda070f3c2015-01-16 19:54:1174#include "third_party/WebKit/public/web/WebNode.h"
[email protected]2255a9332013-06-17 05:12:3175#include "third_party/WebKit/public/web/WebPagePopup.h"
[email protected]2255a9332013-06-17 05:12:3176#include "third_party/WebKit/public/web/WebPopupMenuInfo.h"
77#include "third_party/WebKit/public/web/WebRange.h"
jddukeacf809e2014-09-23 20:38:3878#include "third_party/WebKit/public/web/WebRuntimeFeatures.h"
kenrba7199832015-01-22 23:44:5979#include "third_party/WebKit/public/web/WebView.h"
[email protected]d353541f2012-05-03 22:45:4180#include "third_party/skia/include/core/SkShader.h"
[email protected]faec7b12012-06-19 14:42:1381#include "ui/base/ui_base_switches.h"
tfarina655f81d2014-12-23 02:38:5082#include "ui/gfx/geometry/point_conversions.h"
tfarina3b0452d2014-12-31 15:20:0983#include "ui/gfx/geometry/rect_conversions.h"
tfarinaebe974f02015-01-03 04:25:3284#include "ui/gfx/geometry/size_conversions.h"
[email protected]1835b9e2012-02-28 13:12:4885#include "ui/gfx/skia_util.h"
[email protected]c9e2cbbb2012-05-12 21:17:2786#include "ui/gl/gl_switches.h"
[email protected]d353541f2012-05-03 22:45:4187#include "ui/surface/transport_dib.h"
[email protected]661eb9d2009-02-03 02:11:4888
[email protected]eeb93112013-05-01 19:41:1089#if defined(OS_ANDROID)
[email protected]cefe9b152014-03-27 18:16:1590#include <android/keycodes.h>
[email protected]913d99a2013-05-31 07:16:0791#include "content/renderer/android/synchronous_compositor_factory.h"
boliubee541f42015-11-05 00:52:5392#include "content/renderer/android/synchronous_compositor_filter.h"
93#include "content/renderer/android/synchronous_compositor_output_surface.h"
[email protected]eeb93112013-05-01 19:41:1094#endif
95
[email protected]661eb9d2009-02-03 02:11:4896#if defined(OS_POSIX)
[email protected]6b889fb2010-03-23 20:09:4997#include "ipc/ipc_channel_posix.h"
[email protected]d5282e72009-05-13 13:16:5298#include "third_party/skia/include/core/SkMallocPixelRef.h"
[email protected]d353541f2012-05-03 22:45:4199#include "third_party/skia/include/core/SkPixelRef.h"
[email protected]661eb9d2009-02-03 02:11:48100#endif // defined(OS_POSIX)
[email protected]8085dbc82008-09-26 22:53:44101
penghuang28a5fa22015-12-02 17:58:19102#if defined(MOJO_SHELL_CLIENT)
103#include "content/public/common/mojo_shell_connection.h"
fsamuel2545ecc2015-12-05 00:44:46104#include "content/renderer/mus/render_widget_mus_connection.h"
penghuang28a5fa22015-12-02 17:58:19105#endif
106
[email protected]2255a9332013-06-17 05:12:31107#include "third_party/WebKit/public/web/WebWidget.h"
initial.commit09911bf2008-07-26 23:55:29108
[email protected]180ef242013-11-07 06:50:46109using blink::WebCompositionUnderline;
110using blink::WebCursorInfo;
[email protected]19193682014-04-03 15:01:43111using blink::WebDeviceEmulationParams;
[email protected]180ef242013-11-07 06:50:46112using blink::WebGestureEvent;
113using blink::WebInputEvent;
dtapuska5d2e9c32015-12-03 16:39:49114using blink::WebInputEventResult;
[email protected]180ef242013-11-07 06:50:46115using blink::WebKeyboardEvent;
116using blink::WebMouseEvent;
117using blink::WebMouseWheelEvent;
118using blink::WebNavigationPolicy;
donnda070f3c2015-01-16 19:54:11119using blink::WebNode;
[email protected]180ef242013-11-07 06:50:46120using blink::WebPagePopup;
donnda070f3c2015-01-16 19:54:11121using blink::WebPoint;
[email protected]180ef242013-11-07 06:50:46122using blink::WebPopupType;
123using blink::WebRange;
124using blink::WebRect;
125using blink::WebScreenInfo;
126using blink::WebSize;
127using blink::WebTextDirection;
128using blink::WebTouchEvent;
[email protected]f8ed4722013-12-03 03:27:25129using blink::WebTouchPoint;
[email protected]180ef242013-11-07 06:50:46130using blink::WebVector;
131using blink::WebWidget;
[email protected]e9ff79c2012-10-19 21:31:26132
danakj365175c2016-02-06 00:37:37133#define STATIC_ASSERT_ENUM(a, b) \
134 static_assert(static_cast<int>(a) == static_cast<int>(b), \
135 "mismatching enums: " #a)
136
[email protected]6a4d7f62013-01-07 21:32:13137namespace {
[email protected]b256eca2013-07-11 10:57:40138
139typedef std::map<std::string, ui::TextInputMode> TextInputModeMap;
140
141class TextInputModeMapSingleton {
142 public:
143 static TextInputModeMapSingleton* GetInstance() {
olli.raula36aa8be2015-09-10 11:14:22144 return base::Singleton<TextInputModeMapSingleton>::get();
[email protected]b256eca2013-07-11 10:57:40145 }
[email protected]dd705d4d2013-11-27 08:14:41146 TextInputModeMapSingleton() {
147 map_["verbatim"] = ui::TEXT_INPUT_MODE_VERBATIM;
148 map_["latin"] = ui::TEXT_INPUT_MODE_LATIN;
149 map_["latin-name"] = ui::TEXT_INPUT_MODE_LATIN_NAME;
150 map_["latin-prose"] = ui::TEXT_INPUT_MODE_LATIN_PROSE;
151 map_["full-width-latin"] = ui::TEXT_INPUT_MODE_FULL_WIDTH_LATIN;
152 map_["kana"] = ui::TEXT_INPUT_MODE_KANA;
153 map_["katakana"] = ui::TEXT_INPUT_MODE_KATAKANA;
154 map_["numeric"] = ui::TEXT_INPUT_MODE_NUMERIC;
155 map_["tel"] = ui::TEXT_INPUT_MODE_TEL;
156 map_["email"] = ui::TEXT_INPUT_MODE_EMAIL;
157 map_["url"] = ui::TEXT_INPUT_MODE_URL;
[email protected]b256eca2013-07-11 10:57:40158 }
[email protected]dd705d4d2013-11-27 08:14:41159 const TextInputModeMap& map() const { return map_; }
[email protected]b256eca2013-07-11 10:57:40160 private:
[email protected]dd705d4d2013-11-27 08:14:41161 TextInputModeMap map_;
[email protected]b256eca2013-07-11 10:57:40162
olli.raula36aa8be2015-09-10 11:14:22163 friend struct base::DefaultSingletonTraits<TextInputModeMapSingleton>;
[email protected]b256eca2013-07-11 10:57:40164
165 DISALLOW_COPY_AND_ASSIGN(TextInputModeMapSingleton);
166};
167
[email protected]dd705d4d2013-11-27 08:14:41168ui::TextInputMode ConvertInputMode(const blink::WebString& input_mode) {
[email protected]b256eca2013-07-11 10:57:40169 static TextInputModeMapSingleton* singleton =
170 TextInputModeMapSingleton::GetInstance();
[email protected]dd705d4d2013-11-27 08:14:41171 TextInputModeMap::const_iterator it =
172 singleton->map().find(input_mode.utf8());
173 if (it == singleton->map().end())
[email protected]b256eca2013-07-11 10:57:40174 return ui::TEXT_INPUT_MODE_DEFAULT;
175 return it->second;
[email protected]6a4d7f62013-01-07 21:32:13176}
[email protected]b256eca2013-07-11 10:57:40177
fsamuel72464894f2015-12-15 06:59:31178bool IsDateTimeInput(ui::TextInputType type) {
179 return type == ui::TEXT_INPUT_TYPE_DATE ||
180 type == ui::TEXT_INPUT_TYPE_DATE_TIME ||
181 type == ui::TEXT_INPUT_TYPE_DATE_TIME_LOCAL ||
182 type == ui::TEXT_INPUT_TYPE_MONTH ||
183 type == ui::TEXT_INPUT_TYPE_TIME || type == ui::TEXT_INPUT_TYPE_WEEK;
dtapuskae7473612015-12-04 14:23:06184}
185
fsamuele8326c742016-01-12 00:49:39186content::RenderWidgetInputHandlerDelegate* GetRenderWidgetInputHandlerDelegate(
187 content::RenderWidget* widget) {
188#if defined(MOJO_SHELL_CLIENT)
penghuang639a1042016-01-14 21:25:29189 const base::CommandLine& cmdline = *base::CommandLine::ForCurrentProcess();
190 if (content::MojoShellConnection::Get() &&
191 cmdline.HasSwitch(switches::kUseMusInRenderer)) {
fsamuele8326c742016-01-12 00:49:39192 return content::RenderWidgetMusConnection::GetOrCreate(
193 widget->routing_id());
194 }
195#endif
196 // If we don't have a connection to the Mojo shell, then we want to route IPCs
197 // back to the browser process rather than Mus so we use the |widget| as the
198 // RenderWidgetInputHandlerDelegate.
199 return widget;
200}
201
[email protected]b256eca2013-07-11 10:57:40202} // namespace
203
[email protected]e9ff79c2012-10-19 21:31:26204namespace content {
[email protected]62cb33cae2009-03-27 23:30:22205
[email protected]b2e4c70132013-10-03 02:07:51206// RenderWidget ---------------------------------------------------------------
207
dcheng35d31c112015-07-22 00:17:36208RenderWidget::RenderWidget(CompositorDependencies* compositor_deps,
209 blink::WebPopupType popup_type,
[email protected]180ef242013-11-07 06:50:46210 const blink::WebScreenInfo& screen_info,
[email protected]1ac10dca2013-08-20 20:47:04211 bool swapped_out,
[email protected]7912e822014-04-16 02:37:03212 bool hidden,
213 bool never_visible)
initial.commit09911bf2008-07-26 23:55:29214 : routing_id_(MSG_ROUTING_NONE),
dcheng35d31c112015-07-22 00:17:36215 compositor_deps_(compositor_deps),
danakj6e3bf8012014-12-16 18:27:53216 webwidget_(nullptr),
initial.commit09911bf2008-07-26 23:55:29217 opener_id_(MSG_ROUTING_NONE),
dtrainorcb7779b82014-12-04 01:08:02218 top_controls_shrink_blink_size_(false),
219 top_controls_height_(0.f),
initial.commit09911bf2008-07-26 23:55:29220 next_paint_flags_(0),
[email protected]847a2582013-03-09 02:29:51221 auto_resize_mode_(false),
[email protected]ea3ee0a2012-05-15 03:43:09222 need_update_rect_for_auto_resize_(false),
initial.commit09911bf2008-07-26 23:55:29223 did_show_(false),
[email protected]1ac10dca2013-08-20 20:47:04224 is_hidden_(hidden),
sievers71c62dd52015-10-07 01:44:39225 compositor_never_visible_(never_visible),
mikhail.pozdnyakovf2c902a2015-04-14 08:09:12226 is_fullscreen_granted_(false),
mikhail.pozdnyakovc0e251b2015-04-15 06:51:12227 display_mode_(blink::WebDisplayModeUndefined),
changwanf2a707b2015-10-30 08:22:16228 ime_event_guard_(nullptr),
[email protected]661eb9d2009-02-03 02:11:48229 closing_(false),
[email protected]aeeedad2014-08-22 18:16:22230 host_closing_(false),
[email protected]14392a52012-05-02 20:28:44231 is_swapped_out_(swapped_out),
simonhong628f9812015-04-27 23:13:20232 for_oopif_(false),
[email protected]ad26ef42011-06-17 07:59:45233 text_input_type_(ui::TEXT_INPUT_TYPE_NONE),
[email protected]b256eca2013-07-11 10:57:40234 text_input_mode_(ui::TEXT_INPUT_MODE_DEFAULT),
shuchen82ce8c52014-10-23 01:55:20235 text_input_flags_(0),
[email protected]86ba5fcb2013-09-04 00:36:53236 can_compose_inline_(true),
[email protected]3e2b375b2010-04-07 17:03:12237 popup_type_(popup_type),
[email protected]867125a02009-12-10 06:01:48238 pending_window_rect_count_(0),
[email protected]842f10652012-06-06 01:54:04239 screen_info_(screen_info),
[email protected]3d779472012-11-15 20:49:52240 device_scale_factor_(screen_info_.deviceScaleFactor),
[email protected]53b4cc12013-07-18 23:02:30241 next_output_surface_id_(0),
[email protected]0d1ebed12013-08-05 22:01:13242#if defined(OS_ANDROID)
[email protected]90f24152014-04-09 12:41:36243 text_field_is_dirty_(false),
[email protected]0d1ebed12013-08-05 22:01:13244#endif
[email protected]b2e4c70132013-10-03 02:07:51245 popup_origin_scale_for_emulation_(0.f),
[email protected]586871b2014-07-22 17:05:11246 frame_swap_message_queue_(new FrameSwapMessageQueue()),
[email protected]a09d53ce2014-01-31 00:46:42247 resizing_mode_selector_(new ResizingModeSelector()),
[email protected]be1af0662014-07-29 19:55:51248 has_host_context_menu_location_(false) {
[email protected]8b3f0eb2012-05-03 19:15:05249 if (!swapped_out)
250 RenderProcess::current()->AddRefProcess();
[email protected]380244092011-10-07 17:26:27251 DCHECK(RenderThread::Get());
[email protected]3079c28a2014-06-24 03:38:53252 device_color_profile_.push_back('0');
changwan3a841162015-08-11 02:53:37253#if defined(OS_ANDROID)
254 text_input_info_history_.push_back(blink::WebTextInputInfo());
255#endif
alexclarke7fa93942015-10-21 15:37:11256
257 // In tests there may not be a RenderThreadImpl.
258 if (RenderThreadImpl::current()) {
259 render_widget_scheduling_state_ = RenderThreadImpl::current()
260 ->GetRendererScheduler()
dcheng07945f632015-12-26 07:59:32261 ->NewRenderWidgetSchedulingState();
alexclarke7fa93942015-10-21 15:37:11262 render_widget_scheduling_state_->SetHidden(is_hidden_);
263 }
initial.commit09911bf2008-07-26 23:55:29264}
265
266RenderWidget::~RenderWidget() {
[email protected]c5b3b5e2009-02-13 06:41:11267 DCHECK(!webwidget_) << "Leaking our WebWidget!";
[email protected]bffc8302014-01-23 20:52:16268
[email protected]992db4c2011-05-12 15:37:15269 // If we are swapped out, we have released already.
[email protected]d2e2f9ee2013-08-21 11:02:02270 if (!is_swapped_out_ && RenderProcess::current())
[email protected]992db4c2011-05-12 15:37:15271 RenderProcess::current()->ReleaseProcess();
initial.commit09911bf2008-07-26 23:55:29272}
273
[email protected]484955942010-08-19 16:13:18274// static
avi1023d012015-12-25 02:39:14275RenderWidget* RenderWidget::Create(int32_t opener_id,
danakj6e3bf8012014-12-16 18:27:53276 CompositorDependencies* compositor_deps,
[email protected]180ef242013-11-07 06:50:46277 blink::WebPopupType popup_type,
278 const blink::WebScreenInfo& screen_info) {
initial.commit09911bf2008-07-26 23:55:29279 DCHECK(opener_id != MSG_ROUTING_NONE);
dcheng35d31c112015-07-22 00:17:36280 scoped_refptr<RenderWidget> widget(new RenderWidget(
281 compositor_deps, popup_type, screen_info, false, false, false));
282 if (widget->Init(opener_id)) { // adds reference on success.
[email protected]fc72bb12013-06-02 21:13:46283 return widget.get();
[email protected]a635f942012-12-07 10:34:29284 }
285 return NULL;
initial.commit09911bf2008-07-26 23:55:29286}
287
[email protected]484955942010-08-19 16:13:18288// static
kenrba7199832015-01-22 23:44:59289RenderWidget* RenderWidget::CreateForFrame(
290 int routing_id,
kenrba7199832015-01-22 23:44:59291 bool hidden,
292 const blink::WebScreenInfo& screen_info,
293 CompositorDependencies* compositor_deps,
294 blink::WebLocalFrame* frame) {
295 CHECK_NE(routing_id, MSG_ROUTING_NONE);
dcheng3ce04b62015-10-26 23:30:55296 // TODO(avi): Before RenderViewImpl has-a RenderWidget, the browser passes the
297 // same routing ID for both the view routing ID and the main frame widget
298 // routing ID. https://crbug.com/545684
299 RenderViewImpl* view = RenderViewImpl::FromRoutingID(routing_id);
300 if (view) {
avi8a45c1092016-03-01 16:12:34301 view->AttachWebFrameWidget(
302 RenderWidget::CreateWebFrameWidget(view->GetWidget(), frame));
303 return view->GetWidget();
dcheng3ce04b62015-10-26 23:30:55304 }
dcheng35d31c112015-07-22 00:17:36305 scoped_refptr<RenderWidget> widget(
306 new RenderWidget(compositor_deps, blink::WebPopupTypeNone, screen_info,
307 false, hidden, false));
fsamuele8326c742016-01-12 00:49:39308 widget->SetRoutingID(routing_id);
simonhong628f9812015-04-27 23:13:20309 widget->for_oopif_ = true;
kenrba7199832015-01-22 23:44:59310 // DoInit increments the reference count on |widget|, keeping it alive after
311 // this function returns.
dcheng35d31c112015-07-22 00:17:36312 if (widget->DoInit(MSG_ROUTING_NONE,
kenrba7199832015-01-22 23:44:59313 RenderWidget::CreateWebFrameWidget(widget.get(), frame),
314 nullptr)) {
kenrba7199832015-01-22 23:44:59315 return widget.get();
316 }
317 return nullptr;
318}
319
320// static
lfgcaab5142016-02-26 19:06:52321blink::WebFrameWidget* RenderWidget::CreateWebFrameWidget(
dchengda9b4bb2015-07-20 20:58:08322 RenderWidget* render_widget,
323 blink::WebLocalFrame* frame) {
dcheng3ce04b62015-10-26 23:30:55324 if (!frame->parent()) {
325 // TODO(dcheng): The main frame widget currently has a special case.
326 // Eliminate this once WebView is no longer a WebWidget.
327 return blink::WebFrameWidget::create(render_widget, frame->view(), frame);
328 }
dchengda9b4bb2015-07-20 20:58:08329 return blink::WebFrameWidget::create(render_widget, frame);
330}
331
332// static
kenrba7199832015-01-22 23:44:59333blink::WebWidget* RenderWidget::CreateWebWidget(RenderWidget* render_widget) {
[email protected]484955942010-08-19 16:13:18334 switch (render_widget->popup_type_) {
[email protected]180ef242013-11-07 06:50:46335 case blink::WebPopupTypeNone: // Nothing to create.
[email protected]484955942010-08-19 16:13:18336 break;
[email protected]180ef242013-11-07 06:50:46337 case blink::WebPopupTypePage:
[email protected]a7547fb2012-03-08 04:43:44338 return WebPagePopup::create(render_widget);
[email protected]484955942010-08-19 16:13:18339 default:
340 NOTREACHED();
341 }
342 return NULL;
343}
344
dchengda9b4bb2015-07-20 20:58:08345void RenderWidget::CloseForFrame() {
dchengd96a27a2015-07-24 20:17:32346 OnClose();
kenrba7199832015-01-22 23:44:59347}
348
fsamuele8326c742016-01-12 00:49:39349void RenderWidget::SetRoutingID(int32_t routing_id) {
350 routing_id_ = routing_id;
351 input_handler_.reset(new RenderWidgetInputHandler(
352 GetRenderWidgetInputHandlerDelegate(this), this));
353}
354
avi1023d012015-12-25 02:39:14355bool RenderWidget::Init(int32_t opener_id) {
fsamuele8326c742016-01-12 00:49:39356 bool success = DoInit(
piman5d36dae2015-09-24 22:47:05357 opener_id, RenderWidget::CreateWebWidget(this),
358 new ViewHostMsg_CreateWidget(opener_id, popup_type_, &routing_id_));
fsamuele8326c742016-01-12 00:49:39359 if (success) {
360 SetRoutingID(routing_id_);
361 return true;
362 }
363 return false;
[email protected]484955942010-08-19 16:13:18364}
365
avi1023d012015-12-25 02:39:14366bool RenderWidget::DoInit(int32_t opener_id,
[email protected]6a8ddba52010-09-05 04:38:06367 WebWidget* web_widget,
[email protected]484955942010-08-19 16:13:18368 IPC::SyncMessage* create_widget_message) {
initial.commit09911bf2008-07-26 23:55:29369 DCHECK(!webwidget_);
370
371 if (opener_id != MSG_ROUTING_NONE)
372 opener_id_ = opener_id;
373
[email protected]484955942010-08-19 16:13:18374 webwidget_ = web_widget;
initial.commit09911bf2008-07-26 23:55:29375
kenrba7199832015-01-22 23:44:59376 bool result = true;
377 if (create_widget_message)
378 result = RenderThread::Get()->Send(create_widget_message);
379
initial.commit09911bf2008-07-26 23:55:29380 if (result) {
[email protected]380244092011-10-07 17:26:27381 RenderThread::Get()->AddRoute(routing_id_, this);
initial.commit09911bf2008-07-26 23:55:29382 // Take a reference on behalf of the RenderThread. This will be balanced
383 // when we receive ViewMsg_Close.
384 AddRef();
[email protected]b2db9272014-01-10 17:42:00385 if (RenderThreadImpl::current()) {
386 RenderThreadImpl::current()->WidgetCreated();
387 if (is_hidden_)
388 RenderThreadImpl::current()->WidgetHidden();
389 }
fsamuele8326c742016-01-12 00:49:39390
[email protected]a635f942012-12-07 10:34:29391 return true;
initial.commit09911bf2008-07-26 23:55:29392 } else {
[email protected]a635f942012-12-07 10:34:29393 // The above Send can fail when the tab is closing.
394 return false;
initial.commit09911bf2008-07-26 23:55:29395 }
396}
397
[email protected]992db4c2011-05-12 15:37:15398void RenderWidget::SetSwappedOut(bool is_swapped_out) {
399 // We should only toggle between states.
400 DCHECK(is_swapped_out_ != is_swapped_out);
401 is_swapped_out_ = is_swapped_out;
402
403 // If we are swapping out, we will call ReleaseProcess, allowing the process
404 // to exit if all of its RenderViews are swapped out. We wait until the
[email protected]949b6592014-08-20 13:17:52405 // WasSwappedOut call to do this, to allow the unload handler to finish.
[email protected]992db4c2011-05-12 15:37:15406 // If we are swapping in, we call AddRefProcess to prevent the process from
407 // exiting.
[email protected]949b6592014-08-20 13:17:52408 if (!is_swapped_out_)
[email protected]992db4c2011-05-12 15:37:15409 RenderProcess::current()->AddRefProcess();
410}
411
[email protected]949b6592014-08-20 13:17:52412void RenderWidget::WasSwappedOut() {
413 // If we have been swapped out and no one else is using this process,
414 // it's safe to exit now.
415 CHECK(is_swapped_out_);
416 RenderProcess::current()->ReleaseProcess();
417}
418
[email protected]b2e4c70132013-10-03 02:07:51419void RenderWidget::SetPopupOriginAdjustmentsForEmulation(
mfomitchev2600fd7c2016-02-17 20:53:39420 RenderWidgetScreenMetricsEmulator* emulator) {
[email protected]b2e4c70132013-10-03 02:07:51421 popup_origin_scale_for_emulation_ = emulator->scale();
[email protected]19193682014-04-03 15:01:43422 popup_view_origin_for_emulation_ = emulator->applied_widget_rect().origin();
[email protected]9a2d7ee32013-12-05 12:15:49423 popup_screen_origin_for_emulation_ = gfx::Point(
424 emulator->original_screen_rect().origin().x() + emulator->offset().x(),
425 emulator->original_screen_rect().origin().y() + emulator->offset().y());
[email protected]5f75aa42014-04-01 23:00:56426 screen_info_ = emulator->original_screen_info();
427 device_scale_factor_ = screen_info_.deviceScaleFactor;
[email protected]b2e4c70132013-10-03 02:07:51428}
429
[email protected]2d6836f42014-07-02 17:25:31430gfx::Rect RenderWidget::AdjustValidationMessageAnchor(const gfx::Rect& anchor) {
431 if (screen_metrics_emulator_)
432 return screen_metrics_emulator_->AdjustValidationMessageAnchor(anchor);
433 return anchor;
434}
435
[email protected]53907862014-03-25 15:42:40436#if defined(OS_MACOSX) || defined(OS_ANDROID)
[email protected]b2e4c70132013-10-03 02:07:51437void RenderWidget::SetExternalPopupOriginAdjustmentsForEmulation(
mfomitchev2600fd7c2016-02-17 20:53:39438 ExternalPopupMenu* popup,
439 RenderWidgetScreenMetricsEmulator* emulator) {
[email protected]9a2d7ee32013-12-05 12:15:49440 popup->SetOriginScaleAndOffsetForEmulation(
441 emulator->scale(), emulator->offset());
[email protected]b2e4c70132013-10-03 02:07:51442}
[email protected]53907862014-03-25 15:42:40443#endif
[email protected]b2e4c70132013-10-03 02:07:51444
445void RenderWidget::OnShowHostContextMenu(ContextMenuParams* params) {
446 if (screen_metrics_emulator_)
447 screen_metrics_emulator_->OnShowContextMenu(params);
448}
449
[email protected]a95986a82010-12-24 06:19:28450bool RenderWidget::OnMessageReceived(const IPC::Message& message) {
451 bool handled = true;
452 IPC_BEGIN_MESSAGE_MAP(RenderWidget, message)
[email protected]c084330e02013-04-27 01:08:15453 IPC_MESSAGE_HANDLER(InputMsg_HandleInputEvent, OnHandleInputEvent)
[email protected]34202de2013-05-06 23:36:22454 IPC_MESSAGE_HANDLER(InputMsg_CursorVisibilityChange,
455 OnCursorVisibilityChange)
[email protected]a2214eb2014-06-23 18:31:22456 IPC_MESSAGE_HANDLER(InputMsg_ImeSetComposition, OnImeSetComposition)
457 IPC_MESSAGE_HANDLER(InputMsg_ImeConfirmComposition, OnImeConfirmComposition)
[email protected]c084330e02013-04-27 01:08:15458 IPC_MESSAGE_HANDLER(InputMsg_MouseCaptureLost, OnMouseCaptureLost)
459 IPC_MESSAGE_HANDLER(InputMsg_SetFocus, OnSetFocus)
[email protected]9017d7852013-11-21 17:47:35460 IPC_MESSAGE_HANDLER(InputMsg_SyntheticGestureCompleted,
461 OnSyntheticGestureCompleted)
[email protected]a95986a82010-12-24 06:19:28462 IPC_MESSAGE_HANDLER(ViewMsg_Close, OnClose)
[email protected]a95986a82010-12-24 06:19:28463 IPC_MESSAGE_HANDLER(ViewMsg_Resize, OnResize)
dgozman9260b0a12015-03-16 13:45:20464 IPC_MESSAGE_HANDLER(ViewMsg_EnableDeviceEmulation,
465 OnEnableDeviceEmulation)
466 IPC_MESSAGE_HANDLER(ViewMsg_DisableDeviceEmulation,
467 OnDisableDeviceEmulation)
noel89949e62014-09-30 01:12:41468 IPC_MESSAGE_HANDLER(ViewMsg_ColorProfile, OnColorProfile)
[email protected]b5913d72012-02-07 22:26:54469 IPC_MESSAGE_HANDLER(ViewMsg_ChangeResizeRect, OnChangeResizeRect)
[email protected]a95986a82010-12-24 06:19:28470 IPC_MESSAGE_HANDLER(ViewMsg_WasHidden, OnWasHidden)
[email protected]9e2e4632012-07-27 16:38:41471 IPC_MESSAGE_HANDLER(ViewMsg_WasShown, OnWasShown)
[email protected]3d9ec5052013-01-02 22:05:25472 IPC_MESSAGE_HANDLER(ViewMsg_Repaint, OnRepaint)
[email protected]a95986a82010-12-24 06:19:28473 IPC_MESSAGE_HANDLER(ViewMsg_SetTextDirection, OnSetTextDirection)
474 IPC_MESSAGE_HANDLER(ViewMsg_Move_ACK, OnRequestMoveAck)
[email protected]80ad8622012-11-07 16:33:03475 IPC_MESSAGE_HANDLER(ViewMsg_UpdateScreenRects, OnUpdateScreenRects)
kenrbb4e2a3b2015-05-14 15:05:05476 IPC_MESSAGE_HANDLER(ViewMsg_SetSurfaceIdNamespace, OnSetSurfaceIdNamespace)
lfg43e08e62016-02-03 18:51:37477 IPC_MESSAGE_HANDLER(ViewMsg_WaitForNextFrameForTests,
478 OnWaitNextFrameForTests)
[email protected]105dffb42013-02-20 03:46:21479#if defined(OS_ANDROID)
changwan3a841162015-08-11 02:53:37480 IPC_MESSAGE_HANDLER(InputMsg_ImeEventAck, OnImeEventAck)
changwan8c342742016-02-26 00:53:39481 IPC_MESSAGE_HANDLER(InputMsg_RequestTextInputStateUpdate,
482 OnRequestTextInputStateUpdate)
[email protected]2384b6c2013-02-28 23:58:51483 IPC_MESSAGE_HANDLER(ViewMsg_ShowImeIfNeeded, OnShowImeIfNeeded)
[email protected]105dffb42013-02-20 03:46:21484#endif
dtrainor5ef644e2015-11-19 00:12:47485 IPC_MESSAGE_HANDLER(ViewMsg_HandleCompositorProto, OnHandleCompositorProto)
[email protected]a95986a82010-12-24 06:19:28486 IPC_MESSAGE_UNHANDLED(handled = false)
487 IPC_END_MESSAGE_MAP()
488 return handled;
489}
initial.commit09911bf2008-07-26 23:55:29490
491bool RenderWidget::Send(IPC::Message* message) {
[email protected]992db4c2011-05-12 15:37:15492 // Don't send any messages after the browser has told us to close, and filter
493 // most outgoing messages while swapped out.
494 if ((is_swapped_out_ &&
[email protected]e9ff79c2012-10-19 21:31:26495 !SwappedOutMessages::CanSendWhileSwappedOut(message)) ||
[email protected]c6c921e92012-05-10 23:31:11496 closing_) {
initial.commit09911bf2008-07-26 23:55:29497 delete message;
498 return false;
499 }
500
501 // If given a messsage without a routing ID, then assign our routing ID.
502 if (message->routing_id() == MSG_ROUTING_NONE)
503 message->set_routing_id(routing_id_);
504
[email protected]380244092011-10-07 17:26:27505 return RenderThread::Get()->Send(message);
[email protected]8085dbc82008-09-26 22:53:44506}
507
bokanc007c3a2015-02-03 07:15:56508void RenderWidget::SetWindowRectSynchronously(
509 const gfx::Rect& new_window_rect) {
mfomitchev2600fd7c2016-02-17 20:53:39510 ResizeParams params;
511 params.screen_info = screen_info_;
512 params.new_size = new_window_rect.size();
513 params.physical_backing_size =
514 gfx::ScaleToCeiledSize(new_window_rect.size(), device_scale_factor_);
515 params.top_controls_shrink_blink_size = top_controls_shrink_blink_size_;
516 params.top_controls_height = top_controls_height_;
517 params.visible_viewport_size = new_window_rect.size();
518 params.resizer_rect = gfx::Rect();
519 params.is_fullscreen_granted = is_fullscreen_granted_;
520 params.display_mode = display_mode_;
521 params.needs_resize_ack = false;
522 Resize(params);
523
bokanc007c3a2015-02-03 07:15:56524 view_screen_rect_ = new_window_rect;
525 window_screen_rect_ = new_window_rect;
[email protected]92650162013-10-30 03:31:02526 if (!did_show_)
bokanc007c3a2015-02-03 07:15:56527 initial_rect_ = new_window_rect;
[email protected]92650162013-10-30 03:31:02528}
529
initial.commit09911bf2008-07-26 23:55:29530void RenderWidget::OnClose() {
dchengd96a27a2015-07-24 20:17:32531 DCHECK(content::RenderThread::Get());
532 if (closing_)
533 return;
534 NotifyOnClose();
535 closing_ = true;
536
537 // Browser correspondence is no longer needed at this point.
538 if (routing_id_ != MSG_ROUTING_NONE) {
539 RenderThread::Get()->RemoveRoute(routing_id_);
540 SetHidden(false);
541 if (RenderThreadImpl::current())
542 RenderThreadImpl::current()->WidgetDestroyed();
543 }
544
545 if (for_oopif_) {
546 // Widgets for frames may be created and closed at any time while the frame
547 // is alive. However, the closing process must happen synchronously. Frame
548 // widget and frames hold pointers to each other. If Close() is deferred to
549 // the message loop like in the non-frame widget case, WebWidget::close()
550 // can end up accessing members of an already-deleted frame.
551 Close();
552 } else {
553 // If there is a Send call on the stack, then it could be dangerous to close
554 // now. Post a task that only gets invoked when there are no nested message
555 // loops.
556 base::ThreadTaskRunnerHandle::Get()->PostNonNestableTask(
557 FROM_HERE, base::Bind(&RenderWidget::Close, this));
558 }
559
560 // Balances the AddRef taken when we called AddRoute.
561 Release();
initial.commit09911bf2008-07-26 23:55:29562}
563
fsamuel664e8b62016-01-20 19:54:01564void RenderWidget::OnResize(const ResizeParams& params) {
[email protected]5b45ad42013-10-25 00:42:04565 if (resizing_mode_selector_->ShouldAbortOnResize(this, params))
[email protected]03e88672013-10-22 21:31:32566 return;
567
[email protected]b2e4c70132013-10-03 02:07:51568 if (screen_metrics_emulator_) {
mfomitchev2600fd7c2016-02-17 20:53:39569 screen_metrics_emulator_->OnResize(params);
[email protected]b2e4c70132013-10-03 02:07:51570 return;
571 }
572
mfomitchev2600fd7c2016-02-17 20:53:39573 Resize(params);
initial.commit09911bf2008-07-26 23:55:29574}
575
dgozman9260b0a12015-03-16 13:45:20576void RenderWidget::OnEnableDeviceEmulation(
577 const blink::WebDeviceEmulationParams& params) {
mfomitchev2600fd7c2016-02-17 20:53:39578 if (!screen_metrics_emulator_) {
579 ResizeParams resize_params;
580 resize_params.screen_info = screen_info_;
581 resize_params.new_size = size_;
582 resize_params.physical_backing_size = physical_backing_size_;
583 resize_params.visible_viewport_size = visible_viewport_size_;
584 resize_params.top_controls_shrink_blink_size =
585 top_controls_shrink_blink_size_;
586 resize_params.top_controls_height = top_controls_height_;
587 resize_params.resizer_rect = resizer_rect_;
588 resize_params.is_fullscreen_granted = is_fullscreen_granted_;
589 resize_params.display_mode = display_mode_;
590 screen_metrics_emulator_.reset(new RenderWidgetScreenMetricsEmulator(
591 this, params, resize_params, view_screen_rect_, window_screen_rect_));
592 } else {
dgozman9260b0a12015-03-16 13:45:20593 screen_metrics_emulator_->ChangeEmulationParams(params);
mfomitchev2600fd7c2016-02-17 20:53:39594 }
dgozman9260b0a12015-03-16 13:45:20595}
596
597void RenderWidget::OnDisableDeviceEmulation() {
598 screen_metrics_emulator_.reset();
599}
600
noel89949e62014-09-30 01:12:41601void RenderWidget::OnColorProfile(const std::vector<char>& color_profile) {
602 SetDeviceColorProfile(color_profile);
603}
604
[email protected]b5913d72012-02-07 22:26:54605void RenderWidget::OnChangeResizeRect(const gfx::Rect& resizer_rect) {
[email protected]721e2302014-04-30 23:42:01606 if (resizer_rect_ == resizer_rect)
607 return;
608 resizer_rect_ = resizer_rect;
609 if (webwidget_)
610 webwidget_->didChangeWindowResizerRect();
[email protected]b5913d72012-02-07 22:26:54611}
612
initial.commit09911bf2008-07-26 23:55:29613void RenderWidget::OnWasHidden() {
[email protected]9c3085f2011-06-09 02:10:31614 TRACE_EVENT0("renderer", "RenderWidget::OnWasHidden");
initial.commit09911bf2008-07-26 23:55:29615 // Go into a mode where we stop generating paint and scrolling events.
[email protected]bee16aab2009-08-26 15:55:03616 SetHidden(true);
[email protected]de3c5d82014-05-28 22:12:59617 FOR_EACH_OBSERVER(RenderFrameImpl, render_frames_,
618 WasHidden());
initial.commit09911bf2008-07-26 23:55:29619}
620
[email protected]3399dd822014-08-09 11:14:24621void RenderWidget::OnWasShown(bool needs_repainting,
622 const ui::LatencyInfo& latency_info) {
[email protected]9e2e4632012-07-27 16:38:41623 TRACE_EVENT0("renderer", "RenderWidget::OnWasShown");
initial.commit09911bf2008-07-26 23:55:29624 // During shutdown we can just ignore this message.
625 if (!webwidget_)
626 return;
627
628 // See OnWasHidden
[email protected]bee16aab2009-08-26 15:55:03629 SetHidden(false);
[email protected]de3c5d82014-05-28 22:12:59630 FOR_EACH_OBSERVER(RenderFrameImpl, render_frames_,
631 WasShown());
initial.commit09911bf2008-07-26 23:55:29632
[email protected]8a23afb32014-04-30 22:40:23633 if (!needs_repainting)
initial.commit09911bf2008-07-26 23:55:29634 return;
initial.commit09911bf2008-07-26 23:55:29635
636 // Generate a full repaint.
[email protected]3399dd822014-08-09 11:14:24637 if (compositor_) {
638 ui::LatencyInfo swap_latency_info(latency_info);
639 scoped_ptr<cc::SwapPromiseMonitor> latency_info_swap_promise_monitor(
640 compositor_->CreateLatencyInfoSwapPromiseMonitor(&swap_latency_info));
[email protected]aca33f4f2014-05-17 17:08:05641 compositor_->SetNeedsForcedRedraw();
[email protected]3399dd822014-08-09 11:14:24642 }
jdduke491a3f0c2015-06-15 23:30:26643 ScheduleComposite();
initial.commit09911bf2008-07-26 23:55:29644}
645
[email protected]53d3f302009-12-21 04:42:05646void RenderWidget::OnRequestMoveAck() {
647 DCHECK(pending_window_rect_count_);
648 pending_window_rect_count_--;
649}
650
[email protected]ed7defa2013-03-12 21:29:59651GURL RenderWidget::GetURLForGraphicsContext3D() {
652 return GURL();
[email protected]65225772011-05-12 21:10:24653}
654
fsamuel78f86e42016-01-20 04:10:23655void RenderWidget::OnHandleInputEvent(const blink::WebInputEvent* input_event,
dtapuska0bd451a2016-02-18 17:08:10656 const ui::LatencyInfo& latency_info,
657 InputEventDispatchType dispatch_type) {
fsamuel78f86e42016-01-20 04:10:23658 if (!input_event)
659 return;
dtapuska0bd451a2016-02-18 17:08:10660 input_handler_->HandleInputEvent(*input_event, latency_info, dispatch_type);
fsamuel78f86e42016-01-20 04:10:23661}
662
663void RenderWidget::OnCursorVisibilityChange(bool is_visible) {
664 if (webwidget_)
665 webwidget_->setCursorVisibilityState(is_visible);
666}
667
668void RenderWidget::OnMouseCaptureLost() {
669 if (webwidget_)
670 webwidget_->mouseCaptureLost();
671}
672
673void RenderWidget::OnSetFocus(bool enable) {
674 if (webwidget_)
675 webwidget_->setFocus(enable);
676}
677
678///////////////////////////////////////////////////////////////////////////////
679// RenderWidgetCompositorDelegate
680
681void RenderWidget::ApplyViewportDeltas(
682 const gfx::Vector2dF& inner_delta,
683 const gfx::Vector2dF& outer_delta,
684 const gfx::Vector2dF& elastic_overscroll_delta,
685 float page_scale,
686 float top_controls_delta) {
687 webwidget_->applyViewportDeltas(inner_delta, outer_delta,
688 elastic_overscroll_delta, page_scale,
689 top_controls_delta);
690}
691
692void RenderWidget::BeginMainFrame(double frame_time_sec) {
693 webwidget_->beginFrame(frame_time_sec);
694}
695
[email protected]ebc0e1df2013-08-01 02:46:22696scoped_ptr<cc::OutputSurface> RenderWidget::CreateOutputSurface(bool fallback) {
piman990d8ea2016-01-12 15:35:31697 DCHECK(webwidget_);
[email protected]7912e822014-04-16 02:37:03698 // For widgets that are never visible, we don't start the compositor, so we
699 // never get a request for a cc::OutputSurface.
sievers71c62dd52015-10-07 01:44:39700 DCHECK(!compositor_never_visible_);
[email protected]a1811b8912013-05-09 15:35:19701
avi83883c82014-12-23 00:08:49702 const base::CommandLine& command_line =
703 *base::CommandLine::ForCurrentProcess();
[email protected]e09994a2014-03-26 19:59:33704 bool use_software = fallback;
705 if (command_line.HasSwitch(switches::kDisableGpuCompositing))
706 use_software = true;
707
penghuang28a5fa22015-12-02 17:58:19708#if defined(MOJO_SHELL_CLIENT)
rockot19c030e862016-02-26 05:46:58709 if (MojoShellConnection::Get() && !use_software &&
710 command_line.HasSwitch(switches::kUseMusInRenderer)) {
penghuang28a5fa22015-12-02 17:58:19711 RenderWidgetMusConnection* connection =
712 RenderWidgetMusConnection::GetOrCreate(routing_id());
713 return connection->CreateOutputSurface();
714 }
715#endif
716
piman990d8ea2016-01-12 15:35:31717 scoped_refptr<GpuChannelHost> gpu_channel_host;
718 if (!use_software) {
719 CauseForGpuLaunch cause =
720 CAUSE_FOR_GPU_LAUNCH_WEBGRAPHICSCONTEXT3DCOMMANDBUFFERIMPL_INITIALIZE;
721 gpu_channel_host =
722 RenderThreadImpl::current()->EstablishGpuChannelSync(cause);
723 if (!gpu_channel_host.get()) {
724 // Cause the compositor to wait and try again.
725 return nullptr;
726 }
727 // We may get a valid channel, but with a software renderer. In that case,
728 // disable GPU compositing.
729 if (gpu_channel_host->gpu_info().software_rendering)
730 use_software = true;
731 }
732
[email protected]0634cdd42013-08-16 00:46:09733 scoped_refptr<ContextProviderCommandBuffer> context_provider;
vmiura78b69282015-02-14 00:01:17734 scoped_refptr<ContextProviderCommandBuffer> worker_context_provider;
[email protected]e09994a2014-03-26 19:59:33735 if (!use_software) {
[email protected]0634cdd42013-08-16 00:46:09736 context_provider = ContextProviderCommandBuffer::Create(
piman990d8ea2016-01-12 15:35:31737 CreateGraphicsContext3D(gpu_channel_host.get()),
738 RENDER_COMPOSITOR_CONTEXT);
739 DCHECK(context_provider);
revemand180dfc32015-09-24 00:19:43740 worker_context_provider =
741 RenderThreadImpl::current()->SharedWorkerContextProvider();
742 if (!worker_context_provider) {
vmiura78b69282015-02-14 00:01:17743 // Cause the compositor to wait and try again.
piman8944e1c2015-09-22 21:10:34744 return nullptr;
vmiura78b69282015-02-14 00:01:17745 }
boliu853d46052015-10-13 20:20:06746
747#if defined(OS_ANDROID)
748 if (SynchronousCompositorFactory* factory =
749 SynchronousCompositorFactory::GetInstance()) {
750 return factory->CreateOutputSurface(
751 routing_id(), frame_swap_message_queue_, context_provider,
752 worker_context_provider);
boliubee541f42015-11-05 00:52:53753 } else if (RenderThreadImpl::current()->sync_compositor_message_filter()) {
754 return make_scoped_ptr(new SynchronousCompositorOutputSurface(
755 context_provider, worker_context_provider, routing_id(),
756 content::RenderThreadImpl::current()
757 ->sync_compositor_message_filter(),
758 frame_swap_message_queue_));
boliu853d46052015-10-13 20:20:06759 }
760#endif
[email protected]0634cdd42013-08-16 00:46:09761 }
[email protected]ebc0e1df2013-08-01 02:46:22762
avi1023d012015-12-25 02:39:14763 uint32_t output_surface_id = next_output_surface_id_++;
piman8944e1c2015-09-22 21:10:34764 // Composite-to-mailbox is currently used for layout tests in order to cause
765 // them to draw inside in the renderer to do the readback there. This should
766 // no longer be the case when crbug.com/311404 is fixed.
767 if (!RenderThreadImpl::current() ||
768 !RenderThreadImpl::current()->layout_test_mode()) {
danakj6e3bf8012014-12-16 18:27:53769 DCHECK(compositor_deps_->GetCompositorImplThreadTaskRunner());
piman8944e1c2015-09-22 21:10:34770 return make_scoped_ptr(new DelegatedCompositorOutputSurface(
vmiura78b69282015-02-14 00:01:17771 routing_id(), output_surface_id, context_provider,
772 worker_context_provider, frame_swap_message_queue_));
[email protected]65a33ce2014-03-25 22:37:09773 }
piman8944e1c2015-09-22 21:10:34774
[email protected]0634cdd42013-08-16 00:46:09775 if (!context_provider.get()) {
[email protected]0634cdd42013-08-16 00:46:09776 scoped_ptr<cc::SoftwareOutputDevice> software_device(
jbauman7e15c6a2015-05-11 23:43:12777 new cc::SoftwareOutputDevice());
[email protected]0634cdd42013-08-16 00:46:09778
piman8944e1c2015-09-22 21:10:34779 return make_scoped_ptr(new CompositorOutputSurface(
caseqff9c74c2015-02-10 14:56:29780 routing_id(), output_surface_id, nullptr, nullptr,
dcheng07945f632015-12-26 07:59:32781 std::move(software_device), frame_swap_message_queue_, true));
[email protected]ebc0e1df2013-08-01 02:46:22782 }
[email protected]ed7defa2013-03-12 21:29:59783
piman8944e1c2015-09-22 21:10:34784 return make_scoped_ptr(new MailboxOutputSurface(
vmiura78b69282015-02-14 00:01:17785 routing_id(), output_surface_id, context_provider,
piman8944e1c2015-09-22 21:10:34786 worker_context_provider, frame_swap_message_queue_, cc::RGBA_8888));
[email protected]ba91a792013-02-06 09:48:28787}
788
fsamuel78f86e42016-01-20 04:10:23789scoped_ptr<cc::BeginFrameSource>
790RenderWidget::CreateExternalBeginFrameSource() {
791 return compositor_deps_->CreateExternalBeginFrameSource(routing_id_);
792}
793
794void RenderWidget::DidCommitAndDrawCompositorFrame() {
795 // NOTE: Tests may break if this event is renamed or moved. See
796 // tab_capture_performancetest.cc.
797 TRACE_EVENT0("gpu", "RenderWidget::DidCommitAndDrawCompositorFrame");
798 // Notify subclasses that we initiated the paint operation.
799 DidInitiatePaint();
800}
801
802void RenderWidget::DidCommitCompositorFrame() {
803 FOR_EACH_OBSERVER(RenderFrameImpl, render_frames_,
804 DidCommitCompositorFrame());
805 FOR_EACH_OBSERVER(RenderFrameProxy, render_frame_proxies_,
806 DidCommitCompositorFrame());
807#if defined(VIDEO_HOLE)
808 FOR_EACH_OBSERVER(RenderFrameImpl, video_hole_frames_,
809 DidCommitCompositorFrame());
810#endif // defined(VIDEO_HOLE)
811 input_handler_->FlushPendingInputEventAck();
812}
813
814void RenderWidget::DidCompletePageScaleAnimation() {}
815
816void RenderWidget::DidCompleteSwapBuffers() {
817 TRACE_EVENT0("renderer", "RenderWidget::DidCompleteSwapBuffers");
818
819 // Notify subclasses threaded composited rendering was flushed to the screen.
820 DidFlushPaint();
821
822 if (!next_paint_flags_ && !need_update_rect_for_auto_resize_ &&
823 !plugin_window_moves_.size()) {
824 return;
825 }
826
827 ViewHostMsg_UpdateRect_Params params;
828 params.view_size = size_;
829 params.plugin_window_moves.swap(plugin_window_moves_);
830 params.flags = next_paint_flags_;
831
832 Send(new ViewHostMsg_UpdateRect(routing_id_, params));
833 next_paint_flags_ = 0;
834 need_update_rect_for_auto_resize_ = false;
835}
836
837bool RenderWidget::ForOOPIF() const {
838 // TODO(simonhong): Remove this when we enable BeginFrame scheduling for
839 // OOPIF(crbug.com/471411).
840 return for_oopif_;
841}
842
843void RenderWidget::ForwardCompositorProto(const std::vector<uint8_t>& proto) {
844 Send(new ViewHostMsg_ForwardCompositorProto(routing_id_, proto));
845}
846
847bool RenderWidget::IsClosing() const {
848 return host_closing_;
849}
850
[email protected]4d7e46a2013-11-08 05:33:40851void RenderWidget::OnSwapBuffersAborted() {
[email protected]65225772011-05-12 21:10:24852 TRACE_EVENT0("renderer", "RenderWidget::OnSwapBuffersAborted");
[email protected]65225772011-05-12 21:10:24853 // Schedule another frame so the compositor learns about it.
jdduke491a3f0c2015-06-15 23:30:26854 ScheduleComposite();
[email protected]65225772011-05-12 21:10:24855}
856
[email protected]4d7e46a2013-11-08 05:33:40857void RenderWidget::OnSwapBuffersComplete() {
[email protected]65225772011-05-12 21:10:24858 TRACE_EVENT0("renderer", "RenderWidget::OnSwapBuffersComplete");
[email protected]29ed96a2012-02-04 18:12:16859
[email protected]404939f2012-06-01 04:06:18860 // Notify subclasses that composited rendering was flushed to the screen.
[email protected]29ed96a2012-02-04 18:12:16861 DidFlushPaint();
initial.commit09911bf2008-07-26 23:55:29862}
863
fsamuel78f86e42016-01-20 04:10:23864void RenderWidget::OnSwapBuffersPosted() {
865 TRACE_EVENT0("renderer", "RenderWidget::OnSwapBuffersPosted");
initial.commit09911bf2008-07-26 23:55:29866}
867
fsamuel78f86e42016-01-20 04:10:23868void RenderWidget::RecordFrameTimingEvents(
869 scoped_ptr<cc::FrameTimingTracker::CompositeTimingSet> composite_events,
870 scoped_ptr<cc::FrameTimingTracker::MainFrameTimingSet> main_frame_events) {
871 for (const auto& composite_event : *composite_events) {
872 int64_t frameId = composite_event.first;
873 const std::vector<cc::FrameTimingTracker::CompositeTimingEvent>& events =
874 composite_event.second;
875 std::vector<blink::WebFrameTimingEvent> webEvents;
876 for (size_t i = 0; i < events.size(); ++i) {
877 webEvents.push_back(blink::WebFrameTimingEvent(
878 events[i].frame_id,
879 (events[i].timestamp - base::TimeTicks()).InSecondsF()));
880 }
881 webwidget_->recordFrameTimingEvent(blink::WebWidget::CompositeEvent,
882 frameId, webEvents);
883 }
884 for (const auto& main_frame_event : *main_frame_events) {
885 int64_t frameId = main_frame_event.first;
886 const std::vector<cc::FrameTimingTracker::MainFrameTimingEvent>& events =
887 main_frame_event.second;
888 std::vector<blink::WebFrameTimingEvent> webEvents;
889 for (size_t i = 0; i < events.size(); ++i) {
890 webEvents.push_back(blink::WebFrameTimingEvent(
891 events[i].frame_id,
892 (events[i].timestamp - base::TimeTicks()).InSecondsF(),
893 (events[i].end_time - base::TimeTicks()).InSecondsF()));
894 }
895 webwidget_->recordFrameTimingEvent(blink::WebWidget::RenderEvent, frameId,
896 webEvents);
897 }
[email protected]34202de2013-05-06 23:36:22898}
899
danakj53eccbc2016-03-02 22:51:07900void RenderWidget::RequestScheduleAnimation() {
fsamuel78f86e42016-01-20 04:10:23901 scheduleAnimation();
initial.commit09911bf2008-07-26 23:55:29902}
903
fsamuel78f86e42016-01-20 04:10:23904void RenderWidget::UpdateVisualState() {
905 webwidget_->updateAllLifecyclePhases();
906}
907
908void RenderWidget::WillBeginCompositorFrame() {
909 TRACE_EVENT0("gpu", "RenderWidget::willBeginCompositorFrame");
910
911 // The UpdateTextInputState can result in further layout and possibly
912 // enable GPU acceleration so they need to be called before any painting
913 // is done.
914 UpdateTextInputState(ShowIme::HIDE_IME, ChangeSource::FROM_NON_IME);
915 UpdateSelectionBounds();
lfge6119aac2016-01-27 02:14:31916
917 FOR_EACH_OBSERVER(RenderFrameProxy, render_frame_proxies_,
918 WillBeginCompositorFrame());
initial.commit09911bf2008-07-26 23:55:29919}
920
fsamuel72464894f2015-12-15 06:59:31921///////////////////////////////////////////////////////////////////////////////
922// RenderWidgetInputHandlerDelegate
923
924void RenderWidget::FocusChangeComplete() {}
925
926bool RenderWidget::HasTouchEventHandlersAt(const gfx::Point& point) const {
927 return true;
928}
929
930void RenderWidget::ObserveWheelEventAndResult(
931 const blink::WebMouseWheelEvent& wheel_event,
932 const gfx::Vector2dF& wheel_unused_delta,
933 bool event_processed) {
934 if (!compositor_deps_->IsElasticOverscrollEnabled())
935 return;
936
937 cc::InputHandlerScrollResult scroll_result;
938 scroll_result.did_scroll = event_processed;
939 scroll_result.did_overscroll_root = !wheel_unused_delta.IsZero();
940 scroll_result.unused_scroll_delta = wheel_unused_delta;
941
942 RenderThreadImpl* render_thread = RenderThreadImpl::current();
943 InputHandlerManager* input_handler_manager =
944 render_thread ? render_thread->input_handler_manager() : NULL;
945 if (input_handler_manager) {
946 input_handler_manager->ObserveWheelEventAndResultOnMainThread(
947 routing_id_, wheel_event, scroll_result);
jddukefffb67c2015-01-07 22:32:29948 }
fsamuel72464894f2015-12-15 06:59:31949}
950
951void RenderWidget::OnDidHandleKeyEvent() {}
952
953void RenderWidget::OnDidOverscroll(const DidOverscrollParams& params) {
954 Send(new InputHostMsg_DidOverscroll(routing_id_, params));
955}
956
957void RenderWidget::OnInputEventAck(scoped_ptr<InputEventAck> input_event_ack) {
958 Send(new InputHostMsg_HandleInputEvent_ACK(routing_id_, *input_event_ack));
959}
960
dtapuska0bd451a2016-02-18 17:08:10961void RenderWidget::NonBlockingInputEventHandled(
962 blink::WebInputEvent::Type handled_type) {
963 RenderThreadImpl* render_thread = RenderThreadImpl::current();
964 InputHandlerManager* input_handler_manager =
965 render_thread ? render_thread->input_handler_manager() : NULL;
966 if (input_handler_manager) {
967 input_handler_manager->NonBlockingInputEventHandledOnMainThread(
968 routing_id_, handled_type);
969 }
970}
971
fsamuele8326c742016-01-12 00:49:39972void RenderWidget::SetInputHandler(RenderWidgetInputHandler* input_handler) {
973 // Nothing to do here. RenderWidget created the |input_handler| and will take
974 // ownership of it. We just verify here that we don't already have an input
975 // handler.
976 DCHECK(!input_handler_);
977}
978
fsamuel72464894f2015-12-15 06:59:31979void RenderWidget::UpdateTextInputState(ShowIme show_ime,
980 ChangeSource change_source) {
981 TRACE_EVENT0("renderer", "RenderWidget::UpdateTextInputState");
982 if (ime_event_guard_) {
983 // show_ime should still be effective even if it was set inside the IME
984 // event guard.
985 if (show_ime == ShowIme::IF_NEEDED) {
986 ime_event_guard_->set_show_ime(true);
987 }
988 return;
989 }
990
991 ui::TextInputType new_type = GetTextInputType();
992 if (IsDateTimeInput(new_type))
993 return; // Not considered as a text input field in WebKit/Chromium.
994
995 blink::WebTextInputInfo new_info;
996 if (webwidget_)
997 new_info = webwidget_->textInputInfo();
998 const ui::TextInputMode new_mode = ConvertInputMode(new_info.inputMode);
999
1000 bool new_can_compose_inline = CanComposeInline();
1001
1002 // Only sends text input params if they are changed or if the ime should be
1003 // shown.
1004 if (show_ime == ShowIme::IF_NEEDED ||
changwan8c342742016-02-26 00:53:391005 (IsUsingImeThread() && change_source == ChangeSource::FROM_IME) ||
fsamuel72464894f2015-12-15 06:59:311006 (text_input_type_ != new_type || text_input_mode_ != new_mode ||
1007 text_input_info_ != new_info ||
1008 can_compose_inline_ != new_can_compose_inline)
1009#if defined(OS_ANDROID)
1010 || text_field_is_dirty_
1011#endif
1012 ) {
1013 ViewHostMsg_TextInputState_Params params;
1014 params.type = new_type;
1015 params.mode = new_mode;
1016 params.flags = new_info.flags;
1017 params.value = new_info.value.utf8();
1018 params.selection_start = new_info.selectionStart;
1019 params.selection_end = new_info.selectionEnd;
1020 params.composition_start = new_info.compositionStart;
1021 params.composition_end = new_info.compositionEnd;
1022 params.can_compose_inline = new_can_compose_inline;
1023 params.show_ime_if_needed = (show_ime == ShowIme::IF_NEEDED);
1024#if defined(USE_AURA)
1025 params.is_non_ime_change = true;
1026#endif
1027#if defined(OS_ANDROID)
1028 params.is_non_ime_change =
1029 (change_source == ChangeSource::FROM_NON_IME) || text_field_is_dirty_;
1030 if (params.is_non_ime_change)
1031 OnImeEventSentForAck(new_info);
1032 text_field_is_dirty_ = false;
1033#endif
1034 Send(new ViewHostMsg_TextInputStateChanged(routing_id(), params));
1035
1036 text_input_info_ = new_info;
1037 text_input_type_ = new_type;
1038 text_input_mode_ = new_mode;
1039 can_compose_inline_ = new_can_compose_inline;
1040 text_input_flags_ = new_info.flags;
1041 }
1042}
1043
1044bool RenderWidget::WillHandleGestureEvent(const blink::WebGestureEvent& event) {
1045 return false;
1046}
1047
1048bool RenderWidget::WillHandleMouseEvent(const blink::WebMouseEvent& event) {
1049 return false;
[email protected]fd847792013-10-24 17:12:351050}
1051
initial.commit09911bf2008-07-26 23:55:291052///////////////////////////////////////////////////////////////////////////////
mfomitchev2600fd7c2016-02-17 20:53:391053// RenderWidgetScreenMetricsDelegate
1054
1055void RenderWidget::Redraw() {
1056 set_next_paint_is_resize_ack();
1057 if (compositor_)
1058 compositor_->SetNeedsRedrawRect(gfx::Rect(size_));
1059}
1060
1061void RenderWidget::Resize(const ResizeParams& params) {
engedy6cb63c92016-02-23 14:14:581062 bool orientation_changed =
1063 screen_info_.orientationAngle != params.screen_info.orientationAngle ||
1064 screen_info_.orientationType != params.screen_info.orientationType;
1065
mfomitchev2600fd7c2016-02-17 20:53:391066 screen_info_ = params.screen_info;
1067 SetDeviceScaleFactor(screen_info_.deviceScaleFactor);
1068
1069 if (resizing_mode_selector_->NeverUsesSynchronousResize()) {
1070 // A resize ack shouldn't be requested if we have not ACK'd the previous
1071 // one.
1072 DCHECK(!params.needs_resize_ack || !next_paint_is_resize_ack());
1073 }
1074
1075 // Ignore this during shutdown.
1076 if (!webwidget_)
1077 return;
1078
1079 if (compositor_)
1080 compositor_->setViewportSize(params.physical_backing_size);
1081
1082 bool resized = size_ != params.new_size ||
1083 physical_backing_size_ != params.physical_backing_size;
1084
1085 size_ = params.new_size;
1086 physical_backing_size_ = params.physical_backing_size;
1087
1088 top_controls_shrink_blink_size_ = params.top_controls_shrink_blink_size;
1089 top_controls_height_ = params.top_controls_height;
1090 visible_viewport_size_ = params.visible_viewport_size;
1091 resizer_rect_ = params.resizer_rect;
1092
1093 // NOTE: We may have entered fullscreen mode without changing our size.
1094 bool fullscreen_change =
1095 is_fullscreen_granted_ != params.is_fullscreen_granted;
1096 is_fullscreen_granted_ = params.is_fullscreen_granted;
1097 display_mode_ = params.display_mode;
1098
1099 webwidget_->setTopControlsHeight(params.top_controls_height,
1100 top_controls_shrink_blink_size_);
1101
1102 if (resized) {
1103 gfx::Size new_widget_size =
1104 IsUseZoomForDSFEnabled() ? physical_backing_size_ : size_;
1105 // When resizing, we want to wait to paint before ACK'ing the resize. This
1106 // ensures that we only resize as fast as we can paint. We only need to
1107 // send an ACK if we are resized to a non-empty rect.
1108 webwidget_->resize(new_widget_size);
1109 }
1110 WebSize visual_viewport_size;
1111
1112 if (IsUseZoomForDSFEnabled()) {
1113 visual_viewport_size = gfx::ScaleToCeiledSize(params.visible_viewport_size,
1114 device_scale_factor_);
1115 } else {
1116 visual_viewport_size = visible_viewport_size_;
1117 }
1118
1119 webwidget()->resizeVisualViewport(visual_viewport_size);
1120
1121 if (params.new_size.IsEmpty() || params.physical_backing_size.IsEmpty()) {
1122 // In this case there is no paint/composite and therefore no
1123 // ViewHostMsg_UpdateRect to send the resize ack with. We'd need to send the
1124 // ack through a fake ViewHostMsg_UpdateRect or a different message.
1125 DCHECK(!params.needs_resize_ack);
1126 }
1127
1128 // Send the Resize_ACK flag once we paint again if requested.
1129 if (params.needs_resize_ack)
1130 set_next_paint_is_resize_ack();
1131
1132 if (fullscreen_change)
1133 DidToggleFullscreen();
1134
engedy6cb63c92016-02-23 14:14:581135 if (orientation_changed)
1136 OnOrientationChange();
1137
mfomitchev2600fd7c2016-02-17 20:53:391138 // If a resize ack is requested and it isn't set-up, then no more resizes will
1139 // come in and in general things will go wrong.
1140 DCHECK(!params.needs_resize_ack || next_paint_is_resize_ack());
1141}
1142
1143void RenderWidget::SetScreenMetricsEmulationParameters(
1144 bool enabled,
1145 const blink::WebDeviceEmulationParams& params) {
1146 // This is only supported in RenderView.
1147 NOTREACHED();
1148}
1149
1150void RenderWidget::SetScreenRects(const gfx::Rect& view_screen_rect,
1151 const gfx::Rect& window_screen_rect) {
1152 view_screen_rect_ = view_screen_rect;
1153 window_screen_rect_ = window_screen_rect;
1154}
1155
1156///////////////////////////////////////////////////////////////////////////////
[email protected]f98d7e3c2010-09-13 22:30:461157// WebWidgetClient
initial.commit09911bf2008-07-26 23:55:291158
[email protected]244ac1892011-12-02 17:04:471159void RenderWidget::didAutoResize(const WebSize& new_size) {
oshima33ec97cd2015-12-14 19:40:241160 WebRect new_size_in_window(0, 0, new_size.width, new_size.height);
1161 convertViewportToWindow(&new_size_in_window);
1162 if (size_.width() != new_size_in_window.width ||
1163 size_.height() != new_size_in_window.height) {
1164 size_ = gfx::Size(new_size_in_window.width, new_size_in_window.height);
[email protected]20fbfc22013-05-08 20:50:581165
[email protected]5b45ad42013-10-25 00:42:041166 if (resizing_mode_selector_->is_synchronous_mode()) {
oshima33ec97cd2015-12-14 19:40:241167 gfx::Rect new_pos(rootWindowRect().x,
1168 rootWindowRect().y,
1169 size_.width(),
1170 size_.height());
[email protected]eac2b362013-05-22 07:01:451171 view_screen_rect_ = new_pos;
1172 window_screen_rect_ = new_pos;
[email protected]8be1c582013-03-06 00:55:031173 }
[email protected]20fbfc22013-05-08 20:50:581174
[email protected]eac2b362013-05-22 07:01:451175 AutoResizeCompositor();
[email protected]20fbfc22013-05-08 20:50:581176
[email protected]5b45ad42013-10-25 00:42:041177 if (!resizing_mode_selector_->is_synchronous_mode())
[email protected]20fbfc22013-05-08 20:50:581178 need_update_rect_for_auto_resize_ = true;
[email protected]ea3ee0a2012-05-15 03:43:091179 }
[email protected]244ac1892011-12-02 17:04:471180}
1181
[email protected]3a1c8a8032013-03-18 22:35:321182void RenderWidget::AutoResizeCompositor() {
danakjddaec912015-09-25 19:38:401183 physical_backing_size_ = gfx::ScaleToCeiledSize(size_, device_scale_factor_);
[email protected]97e1bf72013-03-06 14:06:051184 if (compositor_)
oshima750cb4342015-10-31 00:59:011185 compositor_->setViewportSize(physical_backing_size_);
[email protected]97e1bf72013-03-06 14:06:051186}
1187
[email protected]e195e582013-03-08 01:32:591188void RenderWidget::initializeLayerTreeView() {
[email protected]aeeedad2014-08-22 18:16:221189 DCHECK(!host_closing_);
1190
fsamuel78f86e42016-01-20 04:10:231191 compositor_ = RenderWidgetCompositor::Create(this, device_scale_factor_,
1192 compositor_deps_);
oshima750cb4342015-10-31 00:59:011193 compositor_->setViewportSize(physical_backing_size_);
oshimad5279032015-12-16 18:22:331194 OnDeviceScaleFactorChanged();
sievers71c62dd52015-10-07 01:44:391195 // For background pages and certain tests, we don't want to trigger
1196 // OutputSurface creation.
1197 if (compositor_never_visible_ || !RenderThreadImpl::current())
1198 compositor_->SetNeverVisible();
1199
pimanc4af3072015-10-02 03:45:591200 StartCompositor();
[email protected]e195e582013-03-08 01:32:591201}
1202
ennef3c58142014-12-09 21:44:381203void RenderWidget::WillCloseLayerTreeView() {
1204 if (host_closing_)
1205 return;
1206
1207 // Prevent new compositors or output surfaces from being created.
1208 host_closing_ = true;
1209
[email protected]aeeedad2014-08-22 18:16:221210 // Always send this notification to prevent new layer tree views from
1211 // being created, even if one hasn't been created yet.
1212 if (webwidget_)
1213 webwidget_->willCloseLayerTreeView();
[email protected]aeeedad2014-08-22 18:16:221214}
1215
[email protected]180ef242013-11-07 06:50:461216blink::WebLayerTreeView* RenderWidget::layerTreeView() {
[email protected]ba91a792013-02-06 09:48:281217 return compositor_.get();
[email protected]8926c602013-01-23 05:32:061218}
1219
dglazkovf0e1d6d2015-10-10 02:13:481220void RenderWidget::didMeaningfulLayout(blink::WebMeaningfulLayout layout_type) {
1221 if (layout_type == blink::WebMeaningfulLayout::VisuallyNonEmpty) {
1222 QueueMessage(new ViewHostMsg_DidFirstVisuallyNonEmptyPaint(routing_id_),
1223 MESSAGE_DELIVERY_POLICY_WITH_VISUAL_STATE);
1224 }
dglazkov79c426102015-08-31 21:22:431225
dglazkovf0e1d6d2015-10-10 02:13:481226 FOR_EACH_OBSERVER(RenderFrameImpl, render_frames_,
1227 DidMeaningfulLayout(layout_type));
dglazkov79c426102015-08-31 21:22:431228}
1229
jdduke491a3f0c2015-06-15 23:30:261230void RenderWidget::ScheduleComposite() {
1231 if (compositor_ &&
1232 compositor_deps_->GetCompositorImplThreadTaskRunner().get()) {
1233 compositor_->setNeedsAnimate();
1234 }
1235}
1236
1237void RenderWidget::ScheduleCompositeWithForcedRedraw() {
1238 if (compositor_) {
1239 // Regardless of whether threaded compositing is enabled, always
1240 // use this mechanism to force the compositor to redraw. However,
1241 // the invalidation code path below is still needed for the
1242 // non-threaded case.
1243 compositor_->SetNeedsForcedRedraw();
1244 }
1245 ScheduleComposite();
[email protected]6fceb912013-02-15 06:24:151246}
1247
[email protected]586871b2014-07-22 17:05:111248// static
1249scoped_ptr<cc::SwapPromise> RenderWidget::QueueMessageImpl(
1250 IPC::Message* msg,
1251 MessageDeliveryPolicy policy,
1252 FrameSwapMessageQueue* frame_swap_message_queue,
1253 scoped_refptr<IPC::SyncMessageFilter> sync_message_filter,
[email protected]586871b2014-07-22 17:05:111254 int source_frame_number) {
[email protected]586871b2014-07-22 17:05:111255 bool first_message_for_frame = false;
1256 frame_swap_message_queue->QueueMessageForFrame(policy,
1257 source_frame_number,
1258 make_scoped_ptr(msg),
1259 &first_message_for_frame);
1260 if (first_message_for_frame) {
1261 scoped_ptr<cc::SwapPromise> promise(new QueueMessageSwapPromise(
1262 sync_message_filter, frame_swap_message_queue, source_frame_number));
dcheng4b6b5ff2014-10-16 00:42:061263 return promise;
[email protected]586871b2014-07-22 17:05:111264 }
dcheng4b6b5ff2014-10-16 00:42:061265 return nullptr;
[email protected]586871b2014-07-22 17:05:111266}
1267
1268void RenderWidget::QueueMessage(IPC::Message* msg,
1269 MessageDeliveryPolicy policy) {
1270 // RenderThreadImpl::current() is NULL in some tests.
1271 if (!compositor_ || !RenderThreadImpl::current()) {
1272 Send(msg);
1273 return;
1274 }
1275
1276 scoped_ptr<cc::SwapPromise> swap_promise =
1277 QueueMessageImpl(msg,
1278 policy,
dcheng58867a92014-08-26 02:50:221279 frame_swap_message_queue_.get(),
[email protected]586871b2014-07-22 17:05:111280 RenderThreadImpl::current()->sync_message_filter(),
[email protected]586871b2014-07-22 17:05:111281 compositor_->GetSourceFrameNumber());
1282
1283 if (swap_promise) {
dcheng07945f632015-12-26 07:59:321284 compositor_->QueueSwapPromise(std::move(swap_promise));
igsollaeab34cc2015-02-20 11:33:351285 // Request a commit. This might either A) request a commit ahead of time
1286 // or B) request a commit which is not needed because there are not
1287 // pending updates. If B) then the commit will be skipped and the swap
1288 // promises will be broken (see EarlyOut_NoUpdates). To achieve that we
1289 // call SetNeedsUpdateLayers instead of SetNeedsCommit so that
1290 // can_cancel_commit is not unset.
1291 compositor_->SetNeedsUpdateLayers();
[email protected]586871b2014-07-22 17:05:111292 }
1293}
1294
[email protected]4873c7d2009-07-16 06:36:281295void RenderWidget::didChangeCursor(const WebCursorInfo& cursor_info) {
[email protected]7c51b0ee2009-07-08 21:49:301296 // TODO(darin): Eliminate this temporary.
[email protected]9ec87712013-05-24 23:23:521297 WebCursor cursor;
tfarina75a0abf2015-10-06 15:07:181298 InitializeCursorFromWebCursorInfo(&cursor, cursor_info);
initial.commit09911bf2008-07-26 23:55:291299 // Only send a SetCursor message if we need to make a change.
1300 if (!current_cursor_.IsEqual(cursor)) {
1301 current_cursor_ = cursor;
1302 Send(new ViewHostMsg_SetCursor(routing_id_, cursor));
1303 }
1304}
1305
1306// We are supposed to get a single call to Show for a newly created RenderWidget
1307// that was created via RenderWidget::CreateWebView. So, we wait until this
1308// point to dispatch the ShowWidget message.
1309//
1310// This method provides us with the information about how to display the newly
[email protected]5f9de5882011-09-30 23:36:281311// created RenderWidget (i.e., as a blocked popup or as a new tab).
initial.commit09911bf2008-07-26 23:55:291312//
[email protected]4873c7d2009-07-16 06:36:281313void RenderWidget::show(WebNavigationPolicy) {
initial.commit09911bf2008-07-26 23:55:291314 DCHECK(!did_show_) << "received extraneous Show call";
1315 DCHECK(routing_id_ != MSG_ROUTING_NONE);
1316 DCHECK(opener_id_ != MSG_ROUTING_NONE);
1317
[email protected]8de12d942010-11-17 20:42:441318 if (did_show_)
1319 return;
1320
1321 did_show_ = true;
bokanc007c3a2015-02-03 07:15:561322 // NOTE: initial_rect_ may still have its default values at this point, but
[email protected]8de12d942010-11-17 20:42:441323 // that's okay. It'll be ignored if as_popup is false, or the browser
1324 // process will impose a default position otherwise.
bokanc007c3a2015-02-03 07:15:561325 Send(new ViewHostMsg_ShowWidget(opener_id_, routing_id_, initial_rect_));
1326 SetPendingWindowRect(initial_rect_);
initial.commit09911bf2008-07-26 23:55:291327}
1328
[email protected]4873c7d2009-07-16 06:36:281329void RenderWidget::didFocus() {
initial.commit09911bf2008-07-26 23:55:291330}
1331
[email protected]2533ce12009-05-09 00:02:241332void RenderWidget::DoDeferredClose() {
ennef3c58142014-12-09 21:44:381333 WillCloseLayerTreeView();
[email protected]2533ce12009-05-09 00:02:241334 Send(new ViewHostMsg_Close(routing_id_));
1335}
1336
dgozmancf9039cd2015-04-06 12:01:311337void RenderWidget::NotifyOnClose() {
1338 FOR_EACH_OBSERVER(RenderFrameImpl, render_frames_, WidgetWillClose());
1339}
1340
[email protected]4873c7d2009-07-16 06:36:281341void RenderWidget::closeWidgetSoon() {
skyostiled8969c2015-07-20 16:57:081342 DCHECK(content::RenderThread::Get());
[email protected]e1c3a552012-05-04 20:51:321343 if (is_swapped_out_) {
1344 // This widget is currently swapped out, and the active widget is in a
1345 // different process. Have the browser route the close request to the
1346 // active widget instead, so that the correct unload handlers are run.
1347 Send(new ViewHostMsg_RouteCloseEvent(routing_id_));
1348 return;
1349 }
1350
initial.commit09911bf2008-07-26 23:55:291351 // If a page calls window.close() twice, we'll end up here twice, but that's
1352 // OK. It is safe to send multiple Close messages.
1353
[email protected]2533ce12009-05-09 00:02:241354 // Ask the RenderWidgetHost to initiate close. We could be called from deep
1355 // in Javascript. If we ask the RendwerWidgetHost to close now, the window
1356 // could be closed before the JS finishes executing. So instead, post a
1357 // message back to the message loop, which won't run until the JS is
1358 // complete, and then the Close message can be sent.
skyostiled8969c2015-07-20 16:57:081359 base::ThreadTaskRunnerHandle::Get()->PostTask(
[email protected]32876ae2011-11-15 22:25:211360 FROM_HERE, base::Bind(&RenderWidget::DoDeferredClose, this));
initial.commit09911bf2008-07-26 23:55:291361}
1362
[email protected]9017d7852013-11-21 17:47:351363void RenderWidget::QueueSyntheticGesture(
1364 scoped_ptr<SyntheticGestureParams> gesture_params,
1365 const SyntheticGestureCompletionCallback& callback) {
1366 DCHECK(!callback.is_null());
1367
1368 pending_synthetic_gesture_callbacks_.push(callback);
1369
1370 SyntheticGesturePacket gesture_packet;
dcheng07945f632015-12-26 07:59:321371 gesture_packet.set_gesture_params(std::move(gesture_params));
[email protected]9017d7852013-11-21 17:47:351372
1373 Send(new InputHostMsg_QueueSyntheticGesture(routing_id_, gesture_packet));
1374}
1375
initial.commit09911bf2008-07-26 23:55:291376void RenderWidget::Close() {
[email protected]404630b2014-07-03 19:33:031377 screen_metrics_emulator_.reset();
ennef3c58142014-12-09 21:44:381378 WillCloseLayerTreeView();
1379 compositor_.reset();
initial.commit09911bf2008-07-26 23:55:291380 if (webwidget_) {
[email protected]4873c7d2009-07-16 06:36:281381 webwidget_->close();
initial.commit09911bf2008-07-26 23:55:291382 webwidget_ = NULL;
1383 }
1384}
1385
[email protected]4873c7d2009-07-16 06:36:281386WebRect RenderWidget::windowRect() {
1387 if (pending_window_rect_count_)
1388 return pending_window_rect_;
[email protected]2533ce12009-05-09 00:02:241389
[email protected]80ad8622012-11-07 16:33:031390 return view_screen_rect_;
initial.commit09911bf2008-07-26 23:55:291391}
1392
[email protected]180ef242013-11-07 06:50:461393void RenderWidget::setToolTipText(const blink::WebString& text,
[email protected]8a9d6ca32011-06-06 20:11:301394 WebTextDirection hint) {
[email protected]5a395b72011-08-08 19:13:541395 Send(new ViewHostMsg_SetTooltipText(routing_id_, text, hint));
[email protected]8a9d6ca32011-06-06 20:11:301396}
1397
oshima33ec97cd2015-12-14 19:40:241398void RenderWidget::setWindowRect(const WebRect& rect_in_screen) {
1399 WebRect window_rect = rect_in_screen;
[email protected]b2e4c70132013-10-03 02:07:511400 if (popup_origin_scale_for_emulation_) {
1401 float scale = popup_origin_scale_for_emulation_;
bokanc007c3a2015-02-03 07:15:561402 window_rect.x = popup_screen_origin_for_emulation_.x() +
1403 (window_rect.x - popup_view_origin_for_emulation_.x()) * scale;
1404 window_rect.y = popup_screen_origin_for_emulation_.y() +
1405 (window_rect.y - popup_view_origin_for_emulation_.y()) * scale;
[email protected]b2e4c70132013-10-03 02:07:511406 }
1407
[email protected]5b45ad42013-10-25 00:42:041408 if (!resizing_mode_selector_->is_synchronous_mode()) {
[email protected]ec951b9d2013-10-20 06:21:201409 if (did_show_) {
bokanc007c3a2015-02-03 07:15:561410 Send(new ViewHostMsg_RequestMove(routing_id_, window_rect));
1411 SetPendingWindowRect(window_rect);
[email protected]8be1c582013-03-06 00:55:031412 } else {
bokanc007c3a2015-02-03 07:15:561413 initial_rect_ = window_rect;
[email protected]8be1c582013-03-06 00:55:031414 }
initial.commit09911bf2008-07-26 23:55:291415 } else {
bokanc007c3a2015-02-03 07:15:561416 SetWindowRectSynchronously(window_rect);
initial.commit09911bf2008-07-26 23:55:291417 }
1418}
1419
[email protected]2533ce12009-05-09 00:02:241420void RenderWidget::SetPendingWindowRect(const WebRect& rect) {
1421 pending_window_rect_ = rect;
1422 pending_window_rect_count_++;
1423}
1424
[email protected]4873c7d2009-07-16 06:36:281425WebRect RenderWidget::rootWindowRect() {
[email protected]2533ce12009-05-09 00:02:241426 if (pending_window_rect_count_) {
1427 // NOTE(mbelshe): If there is a pending_window_rect_, then getting
1428 // the RootWindowRect is probably going to return wrong results since the
1429 // browser may not have processed the Move yet. There isn't really anything
1430 // good to do in this case, and it shouldn't happen - since this size is
1431 // only really needed for windowToScreen, which is only used for Popups.
[email protected]4873c7d2009-07-16 06:36:281432 return pending_window_rect_;
[email protected]2533ce12009-05-09 00:02:241433 }
1434
[email protected]80ad8622012-11-07 16:33:031435 return window_screen_rect_;
[email protected]d4547452008-08-28 18:36:371436}
1437
[email protected]4873c7d2009-07-16 06:36:281438WebRect RenderWidget::windowResizerRect() {
1439 return resizer_rect_;
[email protected]c04b6362008-11-21 18:54:191440}
1441
[email protected]fa7b1dc2010-06-23 17:53:041442void RenderWidget::OnImeSetComposition(
[email protected]fcf75d42013-12-03 20:11:261443 const base::string16& text,
[email protected]fa7b1dc2010-06-23 17:53:041444 const std::vector<WebCompositionUnderline>& underlines,
chongz7eb752802016-01-27 21:28:071445 const gfx::Range& replacement_range,
[email protected]fa7b1dc2010-06-23 17:53:041446 int selection_start, int selection_end) {
[email protected]0d1ebed12013-08-05 22:01:131447 if (!ShouldHandleImeEvent())
[email protected]4873c7d2009-07-16 06:36:281448 return;
[email protected]66fca5bc2013-05-23 06:58:291449 ImeEventGuard guard(this);
[email protected]88dbe32f2013-06-20 23:31:361450 if (!webwidget_->setComposition(
[email protected]fa7b1dc2010-06-23 17:53:041451 text, WebVector<WebCompositionUnderline>(underlines),
1452 selection_start, selection_end)) {
1453 // If we failed to set the composition text, then we need to let the browser
1454 // process to cancel the input method's ongoing composition session, to make
1455 // sure we are in a consistent state.
[email protected]a2214eb2014-06-23 18:31:221456 Send(new InputHostMsg_ImeCancelComposition(routing_id()));
[email protected]7f00efa2010-04-15 05:01:261457 }
[email protected]88dbe32f2013-06-20 23:31:361458 UpdateCompositionInfo(true);
[email protected]fa7b1dc2010-06-23 17:53:041459}
1460
[email protected]fcf75d42013-12-03 20:11:261461void RenderWidget::OnImeConfirmComposition(const base::string16& text,
[email protected]db4fc1e2013-09-06 20:01:511462 const gfx::Range& replacement_range,
[email protected]0e45bd02013-07-12 20:20:021463 bool keep_selection) {
[email protected]0d1ebed12013-08-05 22:01:131464 if (!ShouldHandleImeEvent())
[email protected]d0be63772011-12-20 23:18:041465 return;
[email protected]66fca5bc2013-05-23 06:58:291466 ImeEventGuard guard(this);
fsamuele8326c742016-01-12 00:49:391467 input_handler_->set_handling_input_event(true);
[email protected]0e45bd02013-07-12 20:20:021468 if (text.length())
1469 webwidget_->confirmComposition(text);
1470 else if (keep_selection)
1471 webwidget_->confirmComposition(WebWidget::KeepSelection);
1472 else
1473 webwidget_->confirmComposition(WebWidget::DoNotKeepSelection);
fsamuele8326c742016-01-12 00:49:391474 input_handler_->set_handling_input_event(false);
[email protected]88dbe32f2013-06-20 23:31:361475 UpdateCompositionInfo(true);
initial.commit09911bf2008-07-26 23:55:291476}
1477
oshimad5279032015-12-16 18:22:331478void RenderWidget::OnDeviceScaleFactorChanged() {
1479 if (!compositor_)
1480 return;
1481
1482 if (IsUseZoomForDSFEnabled())
1483 compositor_->SetPaintedDeviceScaleFactor(device_scale_factor_);
1484 else
1485 compositor_->setDeviceScaleFactor(device_scale_factor_);
1486}
1487
[email protected]0bc1f572013-04-17 01:46:311488void RenderWidget::OnRepaint(gfx::Size size_to_paint) {
[email protected]ec7dc112008-08-06 05:30:121489 // During shutdown we can just ignore this message.
1490 if (!webwidget_)
1491 return;
1492
[email protected]0bc1f572013-04-17 01:46:311493 // Even if the browser provides an empty damage rect, it's still expecting to
1494 // receive a repaint ack so just damage the entire widget bounds.
1495 if (size_to_paint.IsEmpty()) {
1496 size_to_paint = size_;
1497 }
1498
[email protected]ec7dc112008-08-06 05:30:121499 set_next_paint_is_repaint_ack();
[email protected]aca33f4f2014-05-17 17:08:051500 if (compositor_)
[email protected]0bc1f572013-04-17 01:46:311501 compositor_->SetNeedsRedrawRect(gfx::Rect(size_to_paint));
[email protected]ec7dc112008-08-06 05:30:121502}
1503
[email protected]79fa22e2013-08-23 15:18:121504void RenderWidget::OnSyntheticGestureCompleted() {
[email protected]9017d7852013-11-21 17:47:351505 DCHECK(!pending_synthetic_gesture_callbacks_.empty());
1506
1507 pending_synthetic_gesture_callbacks_.front().Run();
1508 pending_synthetic_gesture_callbacks_.pop();
[email protected]0e241b4b2012-08-18 09:06:271509}
1510
[email protected]4873c7d2009-07-16 06:36:281511void RenderWidget::OnSetTextDirection(WebTextDirection direction) {
[email protected]07f953332009-03-25 04:31:111512 if (!webwidget_)
1513 return;
[email protected]4873c7d2009-07-16 06:36:281514 webwidget_->setTextDirection(direction);
[email protected]07f953332009-03-25 04:31:111515}
1516
[email protected]80ad8622012-11-07 16:33:031517void RenderWidget::OnUpdateScreenRects(const gfx::Rect& view_screen_rect,
1518 const gfx::Rect& window_screen_rect) {
[email protected]b2e4c70132013-10-03 02:07:511519 if (screen_metrics_emulator_) {
mfomitchev2600fd7c2016-02-17 20:53:391520 screen_metrics_emulator_->OnUpdateScreenRects(view_screen_rect,
1521 window_screen_rect);
[email protected]b2e4c70132013-10-03 02:07:511522 } else {
mfomitchev2600fd7c2016-02-17 20:53:391523 SetScreenRects(view_screen_rect, window_screen_rect);
[email protected]b2e4c70132013-10-03 02:07:511524 }
[email protected]80ad8622012-11-07 16:33:031525 Send(new ViewHostMsg_UpdateScreenRects_ACK(routing_id()));
1526}
1527
kenrbb4e2a3b2015-05-14 15:05:051528void RenderWidget::OnSetSurfaceIdNamespace(uint32_t surface_id_namespace) {
1529 if (compositor_)
1530 compositor_->SetSurfaceIdNamespace(surface_id_namespace);
1531}
1532
dtrainor5ef644e2015-11-19 00:12:471533void RenderWidget::OnHandleCompositorProto(const std::vector<uint8_t>& proto) {
1534 if (compositor_)
1535 compositor_->OnHandleCompositorProto(proto);
1536}
1537
[email protected]adb362312014-06-28 06:04:241538void RenderWidget::showImeIfNeeded() {
1539 OnShowImeIfNeeded();
[email protected]0d1ebed12013-08-05 22:01:131540}
1541
fsamuel72464894f2015-12-15 06:59:311542ui::TextInputType RenderWidget::GetTextInputType() {
1543 if (webwidget_)
1544 return WebKitToUiTextInputType(webwidget_->textInputType());
1545 return ui::TEXT_INPUT_TYPE_NONE;
1546}
1547
1548void RenderWidget::UpdateCompositionInfo(bool should_update_range) {
1549#if defined(OS_ANDROID)
1550// TODO(yukawa): Start sending character bounds when the browser side
1551// implementation becomes ready (crbug.com/424866).
1552#else
1553 TRACE_EVENT0("renderer", "RenderWidget::UpdateCompositionInfo");
1554 gfx::Range range = gfx::Range();
1555 if (should_update_range) {
1556 GetCompositionRange(&range);
1557 } else {
1558 range = composition_range_;
1559 }
1560 std::vector<gfx::Rect> character_bounds;
1561 GetCompositionCharacterBounds(&character_bounds);
1562
1563 if (!ShouldUpdateCompositionInfo(range, character_bounds))
1564 return;
1565 composition_character_bounds_ = character_bounds;
1566 composition_range_ = range;
1567 Send(new InputHostMsg_ImeCompositionRangeChanged(
1568 routing_id(), composition_range_, composition_character_bounds_));
1569#endif
1570}
1571
oshimaf866dab2015-12-05 00:41:541572void RenderWidget::convertViewportToWindow(blink::WebRect* rect) {
1573 if (IsUseZoomForDSFEnabled()) {
1574 float reverse = 1 / device_scale_factor_;
oshimad5279032015-12-16 18:22:331575 // TODO(oshima): We may need to allow pixel precision here as the the
oshimaf866dab2015-12-05 00:41:541576 // anchor element can be placed at half pixel.
1577 gfx::Rect window_rect =
1578 gfx::ScaleToEnclosedRect(gfx::Rect(*rect), reverse);
1579 rect->x = window_rect.x();
1580 rect->y = window_rect.y();
1581 rect->width = window_rect.width();
1582 rect->height = window_rect.height();
1583 }
1584}
1585
oshimaa6985b62016-01-27 08:58:301586void RenderWidget::convertWindowToViewport(blink::WebFloatRect* rect) {
1587 if (IsUseZoomForDSFEnabled()) {
1588 rect->x *= device_scale_factor_;
1589 rect->y *= device_scale_factor_;
1590 rect->width *= device_scale_factor_;
1591 rect->height *= device_scale_factor_;
1592 }
1593}
1594
[email protected]adb362312014-06-28 06:04:241595void RenderWidget::OnShowImeIfNeeded() {
1596#if defined(OS_ANDROID) || defined(USE_AURA)
fsamuel72464894f2015-12-15 06:59:311597 UpdateTextInputState(ShowIme::IF_NEEDED, ChangeSource::FROM_NON_IME);
[email protected]adb362312014-06-28 06:04:241598#endif
rouslanf7ebd8832015-01-22 01:54:141599
1600// TODO(rouslan): Fix ChromeOS and Windows 8 behavior of autofill popup with
1601// virtual keyboard.
1602#if !defined(OS_ANDROID)
1603 FocusChangeComplete();
1604#endif
[email protected]adb362312014-06-28 06:04:241605}
1606
1607#if defined(OS_ANDROID)
changwan3a841162015-08-11 02:53:371608void RenderWidget::OnImeEventSentForAck(const blink::WebTextInputInfo& info) {
1609 text_input_info_history_.push_back(info);
[email protected]0d1ebed12013-08-05 22:01:131610}
1611
1612void RenderWidget::OnImeEventAck() {
changwan3a841162015-08-11 02:53:371613 DCHECK_GE(text_input_info_history_.size(), 1u);
1614 text_input_info_history_.pop_front();
[email protected]2384b6c2013-02-28 23:58:511615}
changwan8c342742016-02-26 00:53:391616
1617void RenderWidget::OnRequestTextInputStateUpdate() {
1618 DCHECK(!ime_event_guard_);
1619 UpdateSelectionBounds();
1620 UpdateTextInputState(ShowIme::HIDE_IME, ChangeSource::FROM_IME);
1621}
[email protected]105dffb42013-02-20 03:46:211622#endif
1623
[email protected]0d1ebed12013-08-05 22:01:131624bool RenderWidget::ShouldHandleImeEvent() {
1625#if defined(OS_ANDROID)
changwan3a841162015-08-11 02:53:371626 if (!webwidget_)
1627 return false;
changwan8c342742016-02-26 00:53:391628 if (IsUsingImeThread())
1629 return true;
changwan3a841162015-08-11 02:53:371630
1631 // We cannot handle IME events if there is any chance that the event we are
1632 // receiving here from the browser is based on the state that is different
1633 // from our current one as indicated by |text_input_info_|.
1634 // The states the browser might be in are:
1635 // text_input_info_history_[0] - current state ack'd by browser
1636 // text_input_info_history_[1...N] - pending state changes
1637 for (size_t i = 0u; i < text_input_info_history_.size() - 1u; ++i) {
1638 if (text_input_info_history_[i] != text_input_info_)
1639 return false;
1640 }
1641 return true;
[email protected]0d1ebed12013-08-05 22:01:131642#else
1643 return !!webwidget_;
1644#endif
1645}
1646
[email protected]468ac582012-11-20 00:53:191647void RenderWidget::SetDeviceScaleFactor(float device_scale_factor) {
1648 if (device_scale_factor_ == device_scale_factor)
1649 return;
1650
1651 device_scale_factor_ = device_scale_factor;
oshimad5279032015-12-16 18:22:331652
1653 OnDeviceScaleFactorChanged();
1654
jdduke491a3f0c2015-06-15 23:30:261655 ScheduleComposite();
[email protected]468ac582012-11-20 00:53:191656}
1657
[email protected]28ed6b32014-06-08 02:16:271658bool RenderWidget::SetDeviceColorProfile(
1659 const std::vector<char>& color_profile) {
1660 if (device_color_profile_ == color_profile)
1661 return false;
1662
1663 device_color_profile_ = color_profile;
1664 return true;
1665}
1666
noeldb4df152014-09-16 17:45:201667void RenderWidget::ResetDeviceColorProfileForTesting() {
1668 if (!device_color_profile_.empty())
1669 device_color_profile_.clear();
1670 device_color_profile_.push_back('0');
1671}
1672
[email protected]fcdc5642014-05-09 14:32:241673void RenderWidget::OnOrientationChange() {
1674}
1675
[email protected]ceb36f7d2012-10-31 18:33:241676gfx::Vector2d RenderWidget::GetScrollOffset() {
[email protected]d54169e92011-01-21 09:19:521677 // Bare RenderWidgets don't support scroll offset.
[email protected]ceb36f7d2012-10-31 18:33:241678 return gfx::Vector2d();
[email protected]d54169e92011-01-21 09:19:521679}
1680
[email protected]bee16aab2009-08-26 15:55:031681void RenderWidget::SetHidden(bool hidden) {
1682 if (is_hidden_ == hidden)
1683 return;
1684
jdduke8fac9d102014-12-20 02:40:131685 // The status has changed. Tell the RenderThread about it and ensure
1686 // throttled acks are released in case frame production ceases.
[email protected]bee16aab2009-08-26 15:55:031687 is_hidden_ = hidden;
fsamuele8326c742016-01-12 00:49:391688 input_handler_->FlushPendingInputEventAck();
jdduke8fac9d102014-12-20 02:40:131689
[email protected]bee16aab2009-08-26 15:55:031690 if (is_hidden_)
[email protected]b2db9272014-01-10 17:42:001691 RenderThreadImpl::current()->WidgetHidden();
[email protected]bee16aab2009-08-26 15:55:031692 else
[email protected]b2db9272014-01-10 17:42:001693 RenderThreadImpl::current()->WidgetRestored();
alexclarke7fa93942015-10-21 15:37:111694
1695 if (render_widget_scheduling_state_)
1696 render_widget_scheduling_state_->SetHidden(hidden);
[email protected]bee16aab2009-08-26 15:55:031697}
1698
[email protected]2b624c562011-10-27 22:58:261699void RenderWidget::DidToggleFullscreen() {
[email protected]2b624c562011-10-27 22:58:261700 if (!webwidget_)
1701 return;
1702
mikhail.pozdnyakovf2c902a2015-04-14 08:09:121703 if (is_fullscreen_granted_) {
[email protected]2b624c562011-10-27 22:58:261704 webwidget_->didEnterFullScreen();
1705 } else {
1706 webwidget_->didExitFullScreen();
1707 }
[email protected]2b624c562011-10-27 22:58:261708}
1709
[email protected]674741932009-02-04 23:44:461710bool RenderWidget::next_paint_is_resize_ack() const {
[email protected]53d3f302009-12-21 04:42:051711 return ViewHostMsg_UpdateRect_Flags::is_resize_ack(next_paint_flags_);
[email protected]674741932009-02-04 23:44:461712}
1713
[email protected]674741932009-02-04 23:44:461714void RenderWidget::set_next_paint_is_resize_ack() {
[email protected]53d3f302009-12-21 04:42:051715 next_paint_flags_ |= ViewHostMsg_UpdateRect_Flags::IS_RESIZE_ACK;
[email protected]674741932009-02-04 23:44:461716}
1717
[email protected]674741932009-02-04 23:44:461718void RenderWidget::set_next_paint_is_repaint_ack() {
[email protected]53d3f302009-12-21 04:42:051719 next_paint_flags_ |= ViewHostMsg_UpdateRect_Flags::IS_REPAINT_ACK;
[email protected]674741932009-02-04 23:44:461720}
1721
changwan8c342742016-02-26 00:53:391722bool RenderWidget::IsUsingImeThread() {
1723#if defined(OS_ANDROID)
1724 return base::CommandLine::ForCurrentProcess()->HasSwitch(
1725 switches::kEnableImeThread) &&
1726 !base::CommandLine::ForCurrentProcess()->HasSwitch(
1727 switches::kDisableImeThread);
1728#else
1729 return false;
1730#endif
1731}
1732
changwanf2a707b2015-10-30 08:22:161733void RenderWidget::OnImeEventGuardStart(ImeEventGuard* guard) {
1734 if (!ime_event_guard_)
1735 ime_event_guard_ = guard;
[email protected]66fca5bc2013-05-23 06:58:291736}
1737
changwanf2a707b2015-10-30 08:22:161738void RenderWidget::OnImeEventGuardFinish(ImeEventGuard* guard) {
1739 if (ime_event_guard_ != guard) {
1740#if defined(OS_ANDROID)
1741 // In case a from-IME event (e.g. touch) ends up in not-from-IME event
1742 // (e.g. long press gesture), we want to treat it as not-from-IME event
changwan8c342742016-02-26 00:53:391743 // so that ReplicaInputConnection can make changes to its Editable model.
changwanf2a707b2015-10-30 08:22:161744 // Therefore, we want to mark this text state update as 'from IME' only
1745 // when all the nested events are all originating from IME.
1746 ime_event_guard_->set_from_ime(
1747 ime_event_guard_->from_ime() && guard->from_ime());
1748#endif
1749 return;
1750 }
1751 ime_event_guard_ = nullptr;
1752
[email protected]66fca5bc2013-05-23 06:58:291753 // While handling an ime event, text input state and selection bounds updates
1754 // are ignored. These must explicitly be updated once finished handling the
1755 // ime event.
1756 UpdateSelectionBounds();
[email protected]cb9e2632013-06-18 11:26:471757#if defined(OS_ANDROID)
changwanf2a707b2015-10-30 08:22:161758 UpdateTextInputState(
fsamuel72464894f2015-12-15 06:59:311759 guard->show_ime() ? ShowIme::IF_NEEDED : ShowIme::HIDE_IME,
1760 guard->from_ime() ? ChangeSource::FROM_IME : ChangeSource::FROM_NON_IME);
[email protected]cb9e2632013-06-18 11:26:471761#endif
[email protected]66fca5bc2013-05-23 06:58:291762}
1763
[email protected]7c8873e2013-02-05 08:03:011764void RenderWidget::GetSelectionBounds(gfx::Rect* focus, gfx::Rect* anchor) {
1765 WebRect focus_webrect;
1766 WebRect anchor_webrect;
1767 webwidget_->selectionBounds(focus_webrect, anchor_webrect);
oshima33ec97cd2015-12-14 19:40:241768 convertViewportToWindow(&focus_webrect);
1769 convertViewportToWindow(&anchor_webrect);
1770 *focus = focus_webrect;
1771 *anchor = anchor_webrect;
[email protected]73bf95812011-10-12 11:38:321772}
1773
[email protected]e99ef6f2011-10-16 01:13:001774void RenderWidget::UpdateSelectionBounds() {
jdduke1aebad8e2015-07-22 23:25:081775 TRACE_EVENT0("renderer", "RenderWidget::UpdateSelectionBounds");
[email protected]e99ef6f2011-10-16 01:13:001776 if (!webwidget_)
1777 return;
changwanf2a707b2015-10-30 08:22:161778 if (ime_event_guard_)
[email protected]66fca5bc2013-05-23 06:58:291779 return;
[email protected]e99ef6f2011-10-16 01:13:001780
mohsenb0eeba72015-08-09 06:20:081781#if defined(USE_AURA)
1782 // TODO(mohsen): For now, always send explicit selection IPC notifications for
1783 // Aura beucause composited selection updates are not working for webview tags
1784 // which regresses IME inside webview. Remove this when composited selection
1785 // updates are fixed for webviews. See, http://crbug.com/510568.
1786 bool send_ipc = true;
1787#else
jddukeacf809e2014-09-23 20:38:381788 // With composited selection updates, the selection bounds will be reported
1789 // directly by the compositor, in which case explicit IPC selection
1790 // notifications should be suppressed.
mohsenb0eeba72015-08-09 06:20:081791 bool send_ipc =
1792 !blink::WebRuntimeFeatures::isCompositedSelectionUpdateEnabled();
1793#endif
1794 if (send_ipc) {
jddukeacf809e2014-09-23 20:38:381795 ViewHostMsg_SelectionBounds_Params params;
1796 GetSelectionBounds(&params.anchor_rect, &params.focus_rect);
1797 if (selection_anchor_rect_ != params.anchor_rect ||
1798 selection_focus_rect_ != params.focus_rect) {
1799 selection_anchor_rect_ = params.anchor_rect;
1800 selection_focus_rect_ = params.focus_rect;
1801 webwidget_->selectionTextDirection(params.focus_dir, params.anchor_dir);
1802 params.is_anchor_first = webwidget_->isSelectionAnchorFirst();
1803 Send(new ViewHostMsg_SelectionBoundsChanged(routing_id_, params));
1804 }
[email protected]58b48a0d2012-06-13 07:01:351805 }
jddukeacf809e2014-09-23 20:38:381806
[email protected]88dbe32f2013-06-20 23:31:361807 UpdateCompositionInfo(false);
[email protected]e99ef6f2011-10-16 01:13:001808}
1809
[email protected]180ef242013-11-07 06:50:461810// Check blink::WebTextInputType and ui::TextInputType is kept in sync.
danakj365175c2016-02-06 00:37:371811STATIC_ASSERT_ENUM(blink::WebTextInputTypeNone, ui::TEXT_INPUT_TYPE_NONE);
1812STATIC_ASSERT_ENUM(blink::WebTextInputTypeText, ui::TEXT_INPUT_TYPE_TEXT);
1813STATIC_ASSERT_ENUM(blink::WebTextInputTypePassword,
1814 ui::TEXT_INPUT_TYPE_PASSWORD);
1815STATIC_ASSERT_ENUM(blink::WebTextInputTypeSearch, ui::TEXT_INPUT_TYPE_SEARCH);
1816STATIC_ASSERT_ENUM(blink::WebTextInputTypeEmail, ui::TEXT_INPUT_TYPE_EMAIL);
1817STATIC_ASSERT_ENUM(blink::WebTextInputTypeNumber, ui::TEXT_INPUT_TYPE_NUMBER);
1818STATIC_ASSERT_ENUM(blink::WebTextInputTypeTelephone,
1819 ui::TEXT_INPUT_TYPE_TELEPHONE);
1820STATIC_ASSERT_ENUM(blink::WebTextInputTypeURL, ui::TEXT_INPUT_TYPE_URL);
1821STATIC_ASSERT_ENUM(blink::WebTextInputTypeDate, ui::TEXT_INPUT_TYPE_DATE);
1822STATIC_ASSERT_ENUM(blink::WebTextInputTypeDateTime,
1823 ui::TEXT_INPUT_TYPE_DATE_TIME);
1824STATIC_ASSERT_ENUM(blink::WebTextInputTypeDateTimeLocal,
1825 ui::TEXT_INPUT_TYPE_DATE_TIME_LOCAL);
1826STATIC_ASSERT_ENUM(blink::WebTextInputTypeMonth, ui::TEXT_INPUT_TYPE_MONTH);
1827STATIC_ASSERT_ENUM(blink::WebTextInputTypeTime, ui::TEXT_INPUT_TYPE_TIME);
1828STATIC_ASSERT_ENUM(blink::WebTextInputTypeWeek, ui::TEXT_INPUT_TYPE_WEEK);
1829STATIC_ASSERT_ENUM(blink::WebTextInputTypeTextArea,
1830 ui::TEXT_INPUT_TYPE_TEXT_AREA);
1831STATIC_ASSERT_ENUM(blink::WebTextInputTypeContentEditable,
1832 ui::TEXT_INPUT_TYPE_CONTENT_EDITABLE);
1833STATIC_ASSERT_ENUM(blink::WebTextInputTypeDateTimeField,
1834 ui::TEXT_INPUT_TYPE_DATE_TIME_FIELD);
[email protected]ad26ef42011-06-17 07:59:451835
[email protected]5b739cb2012-08-21 20:35:211836ui::TextInputType RenderWidget::WebKitToUiTextInputType(
[email protected]180ef242013-11-07 06:50:461837 blink::WebTextInputType type) {
[email protected]5b739cb2012-08-21 20:35:211838 // Check the type is in the range representable by ui::TextInputType.
1839 DCHECK_LE(type, static_cast<int>(ui::TEXT_INPUT_TYPE_MAX)) <<
[email protected]180ef242013-11-07 06:50:461840 "blink::WebTextInputType and ui::TextInputType not synchronized";
[email protected]5b739cb2012-08-21 20:35:211841 return static_cast<ui::TextInputType>(type);
1842}
1843
[email protected]58b48a0d2012-06-13 07:01:351844void RenderWidget::GetCompositionCharacterBounds(
1845 std::vector<gfx::Rect>* bounds) {
1846 DCHECK(bounds);
1847 bounds->clear();
1848}
1849
[email protected]db4fc1e2013-09-06 20:01:511850void RenderWidget::GetCompositionRange(gfx::Range* range) {
[email protected]88dbe32f2013-06-20 23:31:361851 size_t location, length;
1852 if (webwidget_->compositionRange(&location, &length)) {
1853 range->set_start(location);
1854 range->set_end(location + length);
1855 } else if (webwidget_->caretOrSelectionRange(&location, &length)) {
1856 range->set_start(location);
1857 range->set_end(location + length);
1858 } else {
[email protected]db4fc1e2013-09-06 20:01:511859 *range = gfx::Range::InvalidRange();
[email protected]88dbe32f2013-06-20 23:31:361860 }
1861}
1862
[email protected]501ea13d2013-07-09 17:03:291863bool RenderWidget::ShouldUpdateCompositionInfo(
[email protected]db4fc1e2013-09-06 20:01:511864 const gfx::Range& range,
[email protected]501ea13d2013-07-09 17:03:291865 const std::vector<gfx::Rect>& bounds) {
1866 if (composition_range_ != range)
1867 return true;
1868 if (bounds.size() != composition_character_bounds_.size())
1869 return true;
1870 for (size_t i = 0; i < bounds.size(); ++i) {
1871 if (bounds[i] != composition_character_bounds_[i])
1872 return true;
1873 }
1874 return false;
1875}
[email protected]501ea13d2013-07-09 17:03:291876
[email protected]ad26ef42011-06-17 07:59:451877bool RenderWidget::CanComposeInline() {
1878 return true;
[email protected]56ea1a62011-05-30 07:05:571879}
1880
[email protected]4873c7d2009-07-16 06:36:281881WebScreenInfo RenderWidget::screenInfo() {
[email protected]842f10652012-06-06 01:54:041882 return screen_info_;
[email protected]4873c7d2009-07-16 06:36:281883}
1884
[email protected]fa7b1dc2010-06-23 17:53:041885void RenderWidget::resetInputMethod() {
[email protected]0e45bd02013-07-12 20:20:021886 ImeEventGuard guard(this);
[email protected]fa7b1dc2010-06-23 17:53:041887 // If the last text input type is not None, then we should finish any
1888 // ongoing composition regardless of the new text input type.
[email protected]ad26ef42011-06-17 07:59:451889 if (text_input_type_ != ui::TEXT_INPUT_TYPE_NONE) {
[email protected]fa7b1dc2010-06-23 17:53:041890 // If a composition text exists, then we need to let the browser process
1891 // to cancel the input method's ongoing composition session.
1892 if (webwidget_->confirmComposition())
[email protected]a2214eb2014-06-23 18:31:221893 Send(new InputHostMsg_ImeCancelComposition(routing_id()));
[email protected]fa7b1dc2010-06-23 17:53:041894 }
[email protected]d4cff272011-05-02 15:46:011895
[email protected]88dbe32f2013-06-20 23:31:361896 UpdateCompositionInfo(true);
[email protected]fa7b1dc2010-06-23 17:53:041897}
1898
donnda070f3c2015-01-16 19:54:111899#if defined(OS_ANDROID)
1900void RenderWidget::showUnhandledTapUIIfNeeded(
1901 const WebPoint& tapped_position,
1902 const WebNode& tapped_node,
1903 bool page_changed) {
fsamuele8326c742016-01-12 00:49:391904 DCHECK(input_handler_->handling_input_event());
donnda070f3c2015-01-16 19:54:111905 bool should_trigger = !page_changed && tapped_node.isTextNode() &&
donnd57e54f52015-02-26 19:03:371906 !tapped_node.isContentEditable() &&
1907 !tapped_node.isInsideFocusableElementOrARIAWidget();
donnda070f3c2015-01-16 19:54:111908 if (should_trigger) {
1909 Send(new ViewHostMsg_ShowUnhandledTapUIIfNeeded(routing_id_,
1910 tapped_position.x, tapped_position.y));
1911 }
1912}
1913#endif
1914
[email protected]c68c3e4e2013-01-24 00:36:561915void RenderWidget::didHandleGestureEvent(
1916 const WebGestureEvent& event,
1917 bool event_cancelled) {
[email protected]183e28d2014-01-20 18:18:021918#if defined(OS_ANDROID) || defined(USE_AURA)
[email protected]c68c3e4e2013-01-24 00:36:561919 if (event_cancelled)
1920 return;
[email protected]07c70d22014-08-21 08:33:461921 if (event.type == WebInputEvent::GestureTap) {
fsamuel72464894f2015-12-15 06:59:311922 UpdateTextInputState(ShowIme::IF_NEEDED, ChangeSource::FROM_NON_IME);
[email protected]07c70d22014-08-21 08:33:461923 } else if (event.type == WebInputEvent::GestureLongPress) {
1924 DCHECK(webwidget_);
1925 if (webwidget_->textInputInfo().value.isEmpty())
fsamuel72464894f2015-12-15 06:59:311926 UpdateTextInputState(ShowIme::HIDE_IME, ChangeSource::FROM_NON_IME);
[email protected]07c70d22014-08-21 08:33:461927 else
fsamuel72464894f2015-12-15 06:59:311928 UpdateTextInputState(ShowIme::IF_NEEDED, ChangeSource::FROM_NON_IME);
[email protected]c68c3e4e2013-01-24 00:36:561929 }
1930#endif
1931}
1932
sataya.m582c9ce2015-06-09 08:03:421933void RenderWidget::didOverscroll(
1934 const blink::WebFloatSize& unusedDelta,
1935 const blink::WebFloatSize& accumulatedRootOverScroll,
1936 const blink::WebFloatPoint& position,
1937 const blink::WebFloatSize& velocity) {
fsamuele8326c742016-01-12 00:49:391938 input_handler_->DidOverscrollFromBlink(unusedDelta, accumulatedRootOverScroll,
1939 position, velocity);
sataya.m582c9ce2015-06-09 08:03:421940}
1941
[email protected]7912e822014-04-16 02:37:031942void RenderWidget::StartCompositor() {
sievers71c62dd52015-10-07 01:44:391943 if (!is_hidden())
1944 compositor_->setVisible(true);
[email protected]7912e822014-04-16 02:37:031945}
1946
[email protected]29e2fb42013-07-19 01:13:471947void RenderWidget::SchedulePluginMove(const WebPluginGeometry& move) {
initial.commit09911bf2008-07-26 23:55:291948 size_t i = 0;
1949 for (; i < plugin_window_moves_.size(); ++i) {
1950 if (plugin_window_moves_[i].window == move.window) {
[email protected]16f89d02009-08-26 17:17:581951 if (move.rects_valid) {
1952 plugin_window_moves_[i] = move;
1953 } else {
1954 plugin_window_moves_[i].visible = move.visible;
1955 }
initial.commit09911bf2008-07-26 23:55:291956 break;
1957 }
1958 }
1959
1960 if (i == plugin_window_moves_.size())
1961 plugin_window_moves_.push_back(move);
1962}
[email protected]268654772009-08-06 23:02:041963
1964void RenderWidget::CleanupWindowInPluginMoves(gfx::PluginWindowHandle window) {
1965 for (WebPluginGeometryVector::iterator i = plugin_window_moves_.begin();
1966 i != plugin_window_moves_.end(); ++i) {
1967 if (i->window == window) {
1968 plugin_window_moves_.erase(i);
1969 break;
1970 }
1971 }
1972}
[email protected]67bfb83f2011-09-22 03:36:371973
[email protected]63b465922012-09-06 02:04:521974
[email protected]24ed0432013-04-24 07:50:311975RenderWidgetCompositor* RenderWidget::compositor() const {
1976 return compositor_.get();
1977}
1978
fsamuel72464894f2015-12-15 06:59:311979void RenderWidget::SetHandlingInputEventForTesting(bool handling_input_event) {
fsamuele8326c742016-01-12 00:49:391980 input_handler_->set_handling_input_event(handling_input_event);
[email protected]67bfb83f2011-09-22 03:36:371981}
[email protected]c3d45532011-10-07 19:20:401982
fsamuel72464894f2015-12-15 06:59:311983bool RenderWidget::SendAckForMouseMoveFromDebugger() {
fsamuele8326c742016-01-12 00:49:391984 return input_handler_->SendAckForMouseMoveFromDebugger();
[email protected]41d86852012-11-07 12:23:241985}
1986
fsamuel72464894f2015-12-15 06:59:311987void RenderWidget::IgnoreAckForMouseMoveFromDebugger() {
fsamuele8326c742016-01-12 00:49:391988 input_handler_->IgnoreAckForMouseMoveFromDebugger();
ccamerond4ba47902014-12-17 07:20:311989}
1990
[email protected]ce6689f2013-03-29 12:52:551991void RenderWidget::hasTouchEventHandlers(bool has_handlers) {
alexclarke7fa93942015-10-21 15:37:111992 if (render_widget_scheduling_state_)
1993 render_widget_scheduling_state_->SetHasTouchHandler(has_handlers);
[email protected]ce6689f2013-03-29 12:52:551994 Send(new ViewHostMsg_HasTouchEventHandlers(routing_id_, has_handlers));
1995}
1996
danakj365175c2016-02-06 00:37:371997// Check blink::WebTouchAction and content::TouchAction is kept in sync.
1998STATIC_ASSERT_ENUM(blink::WebTouchActionNone, TOUCH_ACTION_NONE);
1999STATIC_ASSERT_ENUM(blink::WebTouchActionPanLeft, TOUCH_ACTION_PAN_LEFT);
2000STATIC_ASSERT_ENUM(blink::WebTouchActionPanRight, TOUCH_ACTION_PAN_RIGHT);
2001STATIC_ASSERT_ENUM(blink::WebTouchActionPanX, TOUCH_ACTION_PAN_X);
2002STATIC_ASSERT_ENUM(blink::WebTouchActionPanUp, TOUCH_ACTION_PAN_UP);
2003STATIC_ASSERT_ENUM(blink::WebTouchActionPanDown, TOUCH_ACTION_PAN_DOWN);
2004STATIC_ASSERT_ENUM(blink::WebTouchActionPanY, TOUCH_ACTION_PAN_Y);
2005STATIC_ASSERT_ENUM(blink::WebTouchActionPan, TOUCH_ACTION_PAN);
2006STATIC_ASSERT_ENUM(blink::WebTouchActionPinchZoom, TOUCH_ACTION_PINCH_ZOOM);
2007STATIC_ASSERT_ENUM(blink::WebTouchActionManipulation,
2008 TOUCH_ACTION_MANIPULATION);
2009STATIC_ASSERT_ENUM(blink::WebTouchActionDoubleTapZoom,
2010 TOUCH_ACTION_DOUBLE_TAP_ZOOM);
2011STATIC_ASSERT_ENUM(blink::WebTouchActionAuto, TOUCH_ACTION_AUTO);
mostynbe29b6882015-01-13 09:59:172012
[email protected]5d0bbdfa92013-12-10 00:35:512013void RenderWidget::setTouchAction(
2014 blink::WebTouchAction web_touch_action) {
2015
2016 // Ignore setTouchAction calls that result from synthetic touch events (eg.
2017 // when blink is emulating touch with mouse).
fsamuele8326c742016-01-12 00:49:392018 if (input_handler_->handling_event_type() != WebInputEvent::TouchStart)
[email protected]5d0bbdfa92013-12-10 00:35:512019 return;
2020
[email protected]a18f67a2013-12-20 19:44:362021 content::TouchAction content_touch_action =
2022 static_cast<content::TouchAction>(web_touch_action);
[email protected]5d0bbdfa92013-12-10 00:35:512023 Send(new InputHostMsg_SetTouchAction(routing_id_, content_touch_action));
2024}
2025
[email protected]90f24152014-04-09 12:41:362026void RenderWidget::didUpdateTextOfFocusedElementByNonUserInput() {
2027#if defined(OS_ANDROID)
changwan8c342742016-02-26 00:53:392028 if (!IsUsingImeThread())
2029 text_field_is_dirty_ = true;
[email protected]90f24152014-04-09 12:41:362030#endif
2031}
2032
[email protected]0634cdd42013-08-16 00:46:092033scoped_ptr<WebGraphicsContext3DCommandBufferImpl>
piman990d8ea2016-01-12 15:35:312034RenderWidget::CreateGraphicsContext3D(GpuChannelHost* gpu_channel_host) {
[email protected]828a3932014-04-02 14:43:132035 // Explicitly disable antialiasing for the compositor. As of the time of
2036 // this writing, the only platform that supported antialiasing for the
2037 // compositor was Mac OS X, because the on-screen OpenGL context creation
2038 // code paths on Windows and Linux didn't yet have multisampling support.
2039 // Mac OS X essentially always behaves as though it's rendering offscreen.
2040 // Multisampling has a heavy cost especially on devices with relatively low
2041 // fill rate like most notebooks, and the Mac implementation would need to
2042 // be optimized to resolve directly into the IOSurface shared between the
2043 // GPU and browser processes. For these reasons and to avoid platform
2044 // disparities we explicitly disable antialiasing.
2045 blink::WebGraphicsContext3D::Attributes attributes;
2046 attributes.antialias = false;
2047 attributes.shareResources = true;
2048 attributes.noAutomaticFlushes = true;
2049 attributes.depth = false;
2050 attributes.stencil = false;
[email protected]828a3932014-04-02 14:43:132051 bool lose_context_when_out_of_memory = true;
[email protected]96ab016c2013-10-23 00:50:292052 WebGraphicsContext3DCommandBufferImpl::SharedMemoryLimits limits;
[email protected]b6eb8e332013-09-10 00:51:012053#if defined(OS_ANDROID)
boliu853d46052015-10-13 20:20:062054 bool using_synchronous_compositing =
boliubee541f42015-11-05 00:52:532055 SynchronousCompositorFactory::GetInstance() ||
2056 base::CommandLine::ForCurrentProcess()->HasSwitch(
2057 switches::kIPCSyncCompositing);
[email protected]b6eb8e332013-09-10 00:51:012058 // If we raster too fast we become upload bound, and pending
2059 // uploads consume memory. For maximum upload throughput, we would
2060 // want to allow for upload_throughput * pipeline_time of pending
2061 // uploads, after which we are just wasting memory. Since we don't
2062 // know our upload throughput yet, this just caps our memory usage.
boliu853d46052015-10-13 20:20:062063 // Synchronous compositor uses half because synchronous compositor
2064 // pipeline is only one frame deep. But twice of half for low end
2065 // because 16bit texture is not supported.
2066 size_t divider = using_synchronous_compositing ? 2 : 1;
[email protected]35b4f0c2014-06-26 16:55:272067 if (base::SysInfo::IsLowEndDevice())
[email protected]657be322013-09-20 08:50:032068 divider = 6;
[email protected]b6eb8e332013-09-10 00:51:012069 // For reference Nexus10 can upload 1MB in about 2.5ms.
[email protected]657be322013-09-20 08:50:032070 const double max_mb_uploaded_per_ms = 2.0 / (5 * divider);
[email protected]b6eb8e332013-09-10 00:51:012071 // Deadline to draw a frame to achieve 60 frames per second.
2072 const size_t kMillisecondsPerFrame = 16;
2073 // Assuming a two frame deep pipeline between the CPU and the GPU.
[email protected]657be322013-09-20 08:50:032074 size_t max_transfer_buffer_usage_mb =
2075 static_cast<size_t>(2 * kMillisecondsPerFrame * max_mb_uploaded_per_ms);
2076 static const size_t kBytesPerMegabyte = 1024 * 1024;
[email protected]b6eb8e332013-09-10 00:51:012077 // We keep the MappedMemoryReclaimLimit the same as the upload limit
2078 // to avoid unnecessarily stalling the compositor thread.
[email protected]96ab016c2013-10-23 00:50:292079 limits.mapped_memory_reclaim_limit =
[email protected]657be322013-09-20 08:50:032080 max_transfer_buffer_usage_mb * kBytesPerMegabyte;
[email protected]b6eb8e332013-09-10 00:51:012081#endif
piman990d8ea2016-01-12 15:35:312082 limits.command_buffer_size = 64 * 1024;
2083 limits.start_transfer_buffer_size = 64 * 1024;
2084 limits.min_transfer_buffer_size = 64 * 1024;
[email protected]96ab016c2013-10-23 00:50:292085
piman990d8ea2016-01-12 15:35:312086 return make_scoped_ptr(new WebGraphicsContext3DCommandBufferImpl(
2087 0, GetURLForGraphicsContext3D(), gpu_channel_host, attributes,
piman08f75532015-10-05 18:58:012088 lose_context_when_out_of_memory, limits, NULL));
[email protected]ed7defa2013-03-12 21:29:592089}
2090
[email protected]e3244ed2014-06-20 20:04:272091void RenderWidget::RegisterRenderFrameProxy(RenderFrameProxy* proxy) {
2092 render_frame_proxies_.AddObserver(proxy);
[email protected]bffc8302014-01-23 20:52:162093}
2094
[email protected]e3244ed2014-06-20 20:04:272095void RenderWidget::UnregisterRenderFrameProxy(RenderFrameProxy* proxy) {
2096 render_frame_proxies_.RemoveObserver(proxy);
[email protected]bffc8302014-01-23 20:52:162097}
2098
[email protected]de3c5d82014-05-28 22:12:592099void RenderWidget::RegisterRenderFrame(RenderFrameImpl* frame) {
2100 render_frames_.AddObserver(frame);
2101}
2102
2103void RenderWidget::UnregisterRenderFrame(RenderFrameImpl* frame) {
2104 render_frames_.RemoveObserver(frame);
2105}
2106
[email protected]a017938b2014-05-27 21:17:172107#if defined(VIDEO_HOLE)
2108void RenderWidget::RegisterVideoHoleFrame(RenderFrameImpl* frame) {
2109 video_hole_frames_.AddObserver(frame);
2110}
2111
2112void RenderWidget::UnregisterVideoHoleFrame(RenderFrameImpl* frame) {
2113 video_hole_frames_.RemoveObserver(frame);
2114}
2115#endif // defined(VIDEO_HOLE)
2116
lfg43e08e62016-02-03 18:51:372117void RenderWidget::OnWaitNextFrameForTests(int routing_id) {
2118 QueueMessage(new ViewHostMsg_WaitForNextFrameForTests_ACK(routing_id),
2119 MESSAGE_DELIVERY_POLICY_WITH_VISUAL_STATE);
2120}
2121
[email protected]e9ff79c2012-10-19 21:31:262122} // namespace content