Chromium Code Reviews| Index: ash/display/extended_mouse_warp_controller.cc |
| diff --git a/ash/display/extended_mouse_warp_controller.cc b/ash/display/extended_mouse_warp_controller.cc |
| index 879b04baa1234c778f7c3dfcd252ea5c9b6052a3..26a199dd27277132ab0f1a48171f0cc889ef2f4a 100644 |
| --- a/ash/display/extended_mouse_warp_controller.cc |
| +++ b/ash/display/extended_mouse_warp_controller.cc |
| @@ -31,8 +31,6 @@ const int kMaximumSnapHeight = 16; |
| // this, entire edge will be used as a draggable space. |
| const int kMinimumIndicatorHeight = 200; |
| -const int kIndicatorThickness = 1; |
| - |
| // Helper method that maps a gfx::Display to an aura::Window. |
| aura::Window* GetRootWindowForDisplayId(int64_t display_id) { |
| return Shell::GetInstance() |
| @@ -40,9 +38,25 @@ aura::Window* GetRootWindowForDisplayId(int64_t display_id) { |
| ->GetRootWindowForDisplayId(display_id); |
| } |
| -// Helper method that maps an aura::Window to a gfx::Display. |
| -gfx::Display GetDisplayFromWindow(aura::Window* window) { |
| - return gfx::Screen::GetScreen()->GetDisplayNearestWindow(window); |
| +// Helper method that maps an aura::Window to display id; |
| +int64_t GetDisplayIdFromWindow(aura::Window* window) { |
| + return gfx::Screen::GetScreen()->GetDisplayNearestWindow(window).id(); |
| +} |
| + |
| +// Adjust the edge so that it has |barrier_size| gap at the top to |
| +// trigger snap window action. |
| +void AdjustSourceEdgeBounds(const gfx::Rect& display_bounds, |
| + int barrier_size, |
| + gfx::Rect* edge) { |
| + DCHECK_GT(edge->height(), edge->width()); |
| + int target_y = display_bounds.y() + barrier_size; |
| + if (target_y < edge->y()) |
| + return; |
| + |
| + int available_height = edge->height() - kMinimumIndicatorHeight; |
| + if (available_height <= 0) |
| + return; |
| + edge->Inset(0, std::min(available_height, target_y - edge->y()), 0, 0); |
| } |
| } // namespace |
| @@ -72,29 +86,32 @@ ExtendedMouseWarpController::WarpRegion::WarpRegion( |
| ExtendedMouseWarpController::WarpRegion::~WarpRegion() {} |
| +const gfx::Rect& |
| +ExtendedMouseWarpController::WarpRegion::GetIndicatorBoundsForTest( |
| + int64_t id) const { |
| + if (a_display_id_ == id) |
| + return a_indicator_bounds_; |
| + CHECK_EQ(b_display_id_, id); |
| + return b_indicator_bounds_; |
| +} |
| + |
| ExtendedMouseWarpController::ExtendedMouseWarpController( |
| aura::Window* drag_source) |
| : drag_source_root_(drag_source), |
| allow_non_native_event_(false) { |
| ash::DisplayManager* display_manager = |
| Shell::GetInstance()->display_manager(); |
| - |
| - // TODO(oshima): Use ComputeBondary instead and try all combinations. |
| - for (const auto& placement : |
| - display_manager->GetCurrentDisplayLayout().placement_list) { |
| - DisplayPlacement::Position position = placement.position; |
| - const gfx::Display& a = |
| - display_manager->GetDisplayForId(placement.parent_display_id); |
| - const gfx::Display& b = |
| - display_manager->GetDisplayForId(placement.display_id); |
| - |
| - if (position == DisplayPlacement::TOP || |
| - position == DisplayPlacement::BOTTOM) { |
| - AddWarpRegion(CreateHorizontalEdgeBounds(a, b, position), |
| - drag_source != nullptr); |
| - } else { |
| - AddWarpRegion(CreateVerticalEdgeBounds(a, b, position), |
| - drag_source != nullptr); |
| + int64_t drag_source_id = drag_source ? GetDisplayIdFromWindow(drag_source) |
| + : gfx::Display::kInvalidDisplayID; |
| + DisplayList display_list = display_manager->active_display_list(); |
| + while (display_list.size() > 0) { |
| + gfx::Display display = display_list.back(); |
|
stevenjb
2016/03/24 18:08:29
Maybe add a comment here? I wrote something simila
|
| + display_list.pop_back(); |
| + for (const gfx::Display& peer : display_list) { |
| + scoped_ptr<WarpRegion> region = |
| + CreateWarpRegion(display, peer, drag_source_id); |
| + if (region) |
| + AddWarpRegion(std::move(region), drag_source != nullptr); |
| } |
| } |
| } |
| @@ -179,92 +196,27 @@ bool ExtendedMouseWarpController::WarpMouseCursorInNativeCoords( |
| } |
| scoped_ptr<ExtendedMouseWarpController::WarpRegion> |
| -ExtendedMouseWarpController::CreateHorizontalEdgeBounds( |
| - const gfx::Display& a, |
| - const gfx::Display& b, |
| - DisplayPlacement::Position position) { |
| - bool from_a = a.id() == GetDisplayFromWindow(drag_source_root_).id(); |
| - |
| - const gfx::Rect& a_bounds = a.bounds(); |
| - const gfx::Rect& b_bounds = b.bounds(); |
| - |
| - gfx::Rect a_indicator_bounds; |
| - a_indicator_bounds.set_x(std::max(a_bounds.x(), b_bounds.x())); |
| - a_indicator_bounds.set_width(std::min(a_bounds.right(), b_bounds.right()) - |
| - a_indicator_bounds.x()); |
| - a_indicator_bounds.set_height(kIndicatorThickness); |
| - a_indicator_bounds.set_y( |
| - position == DisplayPlacement::TOP |
| - ? a_bounds.y() - (from_a ? 0 : kIndicatorThickness) |
| - : a_bounds.bottom() - (from_a ? kIndicatorThickness : 0)); |
| - |
| - gfx::Rect b_indicator_bounds; |
| - b_indicator_bounds = a_indicator_bounds; |
| - b_indicator_bounds.set_height(kIndicatorThickness); |
| - b_indicator_bounds.set_y( |
| - position == DisplayPlacement::TOP |
| - ? a_bounds.y() - (from_a ? kIndicatorThickness : 0) |
| - : a_bounds.bottom() - (from_a ? 0 : kIndicatorThickness)); |
| - |
| - return make_scoped_ptr( |
| - new WarpRegion(a.id(), b.id(), a_indicator_bounds, b_indicator_bounds)); |
| -} |
| - |
| -scoped_ptr<ExtendedMouseWarpController::WarpRegion> |
| -ExtendedMouseWarpController::CreateVerticalEdgeBounds( |
| - const gfx::Display& a, |
| - const gfx::Display& b, |
| - DisplayPlacement::Position position) { |
| - int snap_height = drag_source_root_ ? kMaximumSnapHeight : 0; |
| - bool in_a = a.id() == GetDisplayFromWindow(drag_source_root_).id(); |
| - |
| - const gfx::Rect& a_bounds = a.bounds(); |
| - const gfx::Rect& b_bounds = b.bounds(); |
| - |
| - int upper_shared_y = std::max(a_bounds.y(), b_bounds.y()); |
| - int lower_shared_y = std::min(a_bounds.bottom(), b_bounds.bottom()); |
| - int shared_height = lower_shared_y - upper_shared_y; |
| - |
| - gfx::Rect a_indicator_bounds; |
| - gfx::Rect b_indicator_bounds; |
| - |
| - int dst_x = position == DisplayPlacement::LEFT |
| - ? a_bounds.x() - (in_a ? kIndicatorThickness : 0) |
| - : a_bounds.right() - (in_a ? 0 : kIndicatorThickness); |
| - b_indicator_bounds.SetRect(dst_x, upper_shared_y, kIndicatorThickness, |
| - shared_height); |
| - |
| - // The indicator on the source display. |
| - a_indicator_bounds.set_width(kIndicatorThickness); |
| - a_indicator_bounds.set_x(position == DisplayPlacement::LEFT |
| - ? a_bounds.x() - (in_a ? 0 : kIndicatorThickness) |
| - : a_bounds.right() - |
| - (in_a ? kIndicatorThickness : 0)); |
| - |
| - const gfx::Rect& source_bounds = in_a ? a_bounds : b_bounds; |
| - int upper_indicator_y = source_bounds.y() + snap_height; |
| - int lower_indicator_y = std::min(source_bounds.bottom(), lower_shared_y); |
| - |
| - // This gives a hight that can be used without sacrifying the snap space. |
| - int available_space = |
| - lower_indicator_y - std::max(upper_shared_y, upper_indicator_y); |
| - |
| - if (shared_height < kMinimumIndicatorHeight) { |
| - // If the shared height is smaller than minimum height, use the |
| - // entire height. |
| - upper_indicator_y = upper_shared_y; |
| - } else if (available_space < kMinimumIndicatorHeight) { |
| - // Snap to the bottom. |
| - upper_indicator_y = |
| - std::max(upper_shared_y, lower_indicator_y + kMinimumIndicatorHeight); |
| - } else { |
| - upper_indicator_y = std::max(upper_indicator_y, upper_shared_y); |
| +ExtendedMouseWarpController::CreateWarpRegion(const gfx::Display& a, |
| + const gfx::Display& b, |
| + int64_t drag_source_id) { |
| + gfx::Rect a_edge; |
| + gfx::Rect b_edge; |
| + int snap_barrier = drag_source_id == gfx::Display::kInvalidDisplayID |
| + ? 0 |
| + : kMaximumSnapHeight; |
| + |
| + if (!ComputeBoundary(a, b, &a_edge, &b_edge)) |
| + return nullptr; |
| + |
| + // Creates the snap window barrirer only when horizontally connected. |
| + if (a_edge.height() > a_edge.width()) { |
| + if (drag_source_id == a.id()) |
| + AdjustSourceEdgeBounds(a.bounds(), snap_barrier, &a_edge); |
| + else if (drag_source_id == b.id()) |
| + AdjustSourceEdgeBounds(b.bounds(), snap_barrier, &b_edge); |
| } |
| - a_indicator_bounds.set_y(upper_indicator_y); |
| - a_indicator_bounds.set_height(lower_indicator_y - upper_indicator_y); |
| - return make_scoped_ptr( |
| - new WarpRegion(a.id(), b.id(), a_indicator_bounds, b_indicator_bounds)); |
| + return make_scoped_ptr(new WarpRegion(a.id(), b.id(), a_edge, b_edge)); |
| } |
| } // namespace ash |