| OLD | NEW |
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #import "ui/views/cocoa/bridged_native_widget.h" | 5 #import "ui/views/cocoa/bridged_native_widget.h" |
| 6 | 6 |
| 7 #import <objc/runtime.h> | 7 #import <objc/runtime.h> |
| 8 #include <stddef.h> | 8 #include <stddef.h> |
| 9 #include <stdint.h> | 9 #include <stdint.h> |
| 10 | 10 |
| (...skipping 1045 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1056 Widget* widget = native_widget_mac_->GetWidget(); | 1056 Widget* widget = native_widget_mac_->GetWidget(); |
| 1057 RankNSViews(widget->GetRootView(), associated_views_, &rank); | 1057 RankNSViews(widget->GetRootView(), associated_views_, &rank); |
| 1058 // Unassociated NSViews should be ordered above associated ones. The exception | 1058 // Unassociated NSViews should be ordered above associated ones. The exception |
| 1059 // is the UI compositor's superview, which should always be on the very | 1059 // is the UI compositor's superview, which should always be on the very |
| 1060 // bottom, so give it an explicit negative rank. | 1060 // bottom, so give it an explicit negative rank. |
| 1061 if (compositor_superview_) | 1061 if (compositor_superview_) |
| 1062 rank[compositor_superview_] = -1; | 1062 rank[compositor_superview_] = -1; |
| 1063 [bridged_view_ sortSubviewsUsingFunction:&SubviewSorter context:&rank]; | 1063 [bridged_view_ sortSubviewsUsingFunction:&SubviewSorter context:&rank]; |
| 1064 } | 1064 } |
| 1065 | 1065 |
| 1066 void BridgedNativeWidget::PumpCompositor() { |
| 1067 // Set the "needs commit" flag in the LayerTreeHost if isn't already set. |
| 1068 compositor_->ScheduleDraw(); |
| 1069 frame_swapped_ = false; |
| 1070 |
| 1071 constexpr int kPumpTimeoutMS = 100; |
| 1072 WaitForFrame(kPumpTimeoutMS, [this] { return frame_swapped_; }); |
| 1073 } |
| 1074 |
| 1066 //////////////////////////////////////////////////////////////////////////////// | 1075 //////////////////////////////////////////////////////////////////////////////// |
| 1067 // BridgedNativeWidget, internal::InputMethodDelegate: | 1076 // BridgedNativeWidget, internal::InputMethodDelegate: |
| 1068 | 1077 |
| 1069 ui::EventDispatchDetails BridgedNativeWidget::DispatchKeyEventPostIME( | 1078 ui::EventDispatchDetails BridgedNativeWidget::DispatchKeyEventPostIME( |
| 1070 ui::KeyEvent* key) { | 1079 ui::KeyEvent* key) { |
| 1071 DCHECK(focus_manager_); | 1080 DCHECK(focus_manager_); |
| 1072 native_widget_mac_->GetWidget()->OnKeyEvent(key); | 1081 native_widget_mac_->GetWidget()->OnKeyEvent(key); |
| 1073 if (!key->handled()) { | 1082 if (!key->handled()) { |
| 1074 if (!focus_manager_->OnKeyEvent(*key)) | 1083 if (!focus_manager_->OnKeyEvent(*key)) |
| 1075 key->StopPropagation(); | 1084 key->StopPropagation(); |
| (...skipping 75 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1151 if (initial_visibility_suppressed_) { | 1160 if (initial_visibility_suppressed_) { |
| 1152 initial_visibility_suppressed_ = false; | 1161 initial_visibility_suppressed_ = false; |
| 1153 [window_ setAlphaValue:1.0]; | 1162 [window_ setAlphaValue:1.0]; |
| 1154 [window_ setIgnoresMouseEvents:NO]; | 1163 [window_ setIgnoresMouseEvents:NO]; |
| 1155 } | 1164 } |
| 1156 | 1165 |
| 1157 if (invalidate_shadow_on_frame_swap_) { | 1166 if (invalidate_shadow_on_frame_swap_) { |
| 1158 invalidate_shadow_on_frame_swap_ = false; | 1167 invalidate_shadow_on_frame_swap_ = false; |
| 1159 [window_ invalidateShadow]; | 1168 [window_ invalidateShadow]; |
| 1160 } | 1169 } |
| 1170 |
| 1171 frame_swapped_ = true; |
| 1161 } | 1172 } |
| 1162 | 1173 |
| 1163 //////////////////////////////////////////////////////////////////////////////// | 1174 //////////////////////////////////////////////////////////////////////////////// |
| 1164 // BridgedNativeWidget, BridgedNativeWidgetOwner: | 1175 // BridgedNativeWidget, BridgedNativeWidgetOwner: |
| 1165 | 1176 |
| 1166 NSWindow* BridgedNativeWidget::GetNSWindow() { | 1177 NSWindow* BridgedNativeWidget::GetNSWindow() { |
| 1167 return window_; | 1178 return window_; |
| 1168 } | 1179 } |
| 1169 | 1180 |
| 1170 gfx::Vector2d BridgedNativeWidget::GetChildWindowOffset() const { | 1181 gfx::Vector2d BridgedNativeWidget::GetChildWindowOffset() const { |
| (...skipping 195 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1366 // For a translucent window, the shadow calculation needs to be carried out | 1377 // For a translucent window, the shadow calculation needs to be carried out |
| 1367 // after the frame from the compositor arrives. | 1378 // after the frame from the compositor arrives. |
| 1368 if (![window_ isOpaque]) | 1379 if (![window_ isOpaque]) |
| 1369 invalidate_shadow_on_frame_swap_ = true; | 1380 invalidate_shadow_on_frame_swap_ = true; |
| 1370 } | 1381 } |
| 1371 | 1382 |
| 1372 void BridgedNativeWidget::MaybeWaitForFrame(const gfx::Size& size_in_dip) { | 1383 void BridgedNativeWidget::MaybeWaitForFrame(const gfx::Size& size_in_dip) { |
| 1373 if (!layer()->IsDrawn() || compositor_widget_->HasFrameOfSize(size_in_dip)) | 1384 if (!layer()->IsDrawn() || compositor_widget_->HasFrameOfSize(size_in_dip)) |
| 1374 return; | 1385 return; |
| 1375 | 1386 |
| 1376 const int kPaintMsgTimeoutMS = 50; | 1387 constexpr int kPaintMsgTimeoutMS = 50; |
| 1388 WaitForFrame(kPaintMsgTimeoutMS, [&, this] { |
| 1389 // Since the UI thread is blocked, the size shouldn't change. |
| 1390 DCHECK(size_in_dip == GetClientAreaSize()); |
| 1391 return compositor_widget_->HasFrameOfSize(size_in_dip); |
| 1392 }); |
| 1393 } |
| 1394 |
| 1395 void BridgedNativeWidget::WaitForFrame(int timeout_ms, |
| 1396 std::function<bool()> predicate) { |
| 1377 const base::TimeTicks start_time = base::TimeTicks::Now(); | 1397 const base::TimeTicks start_time = base::TimeTicks::Now(); |
| 1378 const base::TimeTicks timeout_time = | 1398 const base::TimeTicks timeout_time = |
| 1379 start_time + base::TimeDelta::FromMilliseconds(kPaintMsgTimeoutMS); | 1399 start_time + base::TimeDelta::FromMilliseconds(timeout_ms); |
| 1380 | 1400 |
| 1381 ui::WindowResizeHelperMac* resize_helper = ui::WindowResizeHelperMac::Get(); | 1401 ui::WindowResizeHelperMac* resize_helper = ui::WindowResizeHelperMac::Get(); |
| 1382 for (base::TimeTicks now = start_time; now < timeout_time; | 1402 for (base::TimeTicks now = start_time; now < timeout_time; |
| 1383 now = base::TimeTicks::Now()) { | 1403 now = base::TimeTicks::Now()) { |
| 1384 if (!resize_helper->WaitForSingleTaskToRun(timeout_time - now)) | 1404 if (!resize_helper->WaitForSingleTaskToRun(timeout_time - now)) |
| 1385 return; // Timeout. | 1405 return; // Timeout. |
| 1386 | 1406 if (predicate()) |
| 1387 // Since the UI thread is blocked, the size shouldn't change. | |
| 1388 DCHECK(size_in_dip == GetClientAreaSize()); | |
| 1389 if (compositor_widget_->HasFrameOfSize(size_in_dip)) | |
| 1390 return; // Frame arrived. | 1407 return; // Frame arrived. |
| 1391 } | 1408 } |
| 1392 } | 1409 } |
| 1393 | 1410 |
| 1394 void BridgedNativeWidget::ShowAsModalSheet() { | 1411 void BridgedNativeWidget::ShowAsModalSheet() { |
| 1395 // -[NSApp beginSheet:] will block the UI thread while the animation runs. | 1412 // -[NSApp beginSheet:] will block the UI thread while the animation runs. |
| 1396 // So that it doesn't animate a fully transparent window, first wait for a | 1413 // So that it doesn't animate a fully transparent window, first wait for a |
| 1397 // frame. The first step is to pretend that the window is already visible. | 1414 // frame. The first step is to pretend that the window is already visible. |
| 1398 window_visible_ = true; | 1415 window_visible_ = true; |
| 1399 layer()->SetVisible(true); | 1416 layer()->SetVisible(true); |
| (...skipping 27 matching lines...) Expand all Loading... |
| 1427 [bridged_view_ setMouseDownCanMoveWindow:draggable]; | 1444 [bridged_view_ setMouseDownCanMoveWindow:draggable]; |
| 1428 // AppKit will not update its cache of mouseDownCanMoveWindow unless something | 1445 // AppKit will not update its cache of mouseDownCanMoveWindow unless something |
| 1429 // changes. Previously we tried adding an NSView and removing it, but for some | 1446 // changes. Previously we tried adding an NSView and removing it, but for some |
| 1430 // reason it required reposting the mouse-down event, and didn't always work. | 1447 // reason it required reposting the mouse-down event, and didn't always work. |
| 1431 // Calling the below seems to be an effective solution. | 1448 // Calling the below seems to be an effective solution. |
| 1432 [window_ setMovableByWindowBackground:NO]; | 1449 [window_ setMovableByWindowBackground:NO]; |
| 1433 [window_ setMovableByWindowBackground:YES]; | 1450 [window_ setMovableByWindowBackground:YES]; |
| 1434 } | 1451 } |
| 1435 | 1452 |
| 1436 } // namespace views | 1453 } // namespace views |
| OLD | NEW |