summaryrefslogtreecommitdiffstats
path: root/ash
diff options
context:
space:
mode:
authormazda@chromium.org <mazda@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2012-09-11 20:18:35 +0000
committermazda@chromium.org <mazda@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2012-09-11 20:18:35 +0000
commit151ffdff429adc13dea9afbe18602745981a9dcc (patch)
tree65ea7ff184d3e543d2a6213e29a96119eed4081b /ash
parent843fe4276bb2a001d6bdbb74dda7ef44a707cec7 (diff)
downloadchromium_src-151ffdff429adc13dea9afbe18602745981a9dcc.zip
chromium_src-151ffdff429adc13dea9afbe18602745981a9dcc.tar.gz
chromium_src-151ffdff429adc13dea9afbe18602745981a9dcc.tar.bz2
Move ash specific cursor code to CursorManager.
Main changes are as follows. - Move the responsibility of managing cursors to ash::CursorManager from aura::RootWindowHostLinux. - Set the same cursor to all root windows with CursorManager so that cursor is updated properly while dragging across displays - Introduce CursorLoader class, which implements platform specific cursor loading. - Add SetDeviceScaleFactor to CursorClient, which sets the device scale factor used for the cursor. BUG=132862,144756 Review URL: https://chromiumcodereview.appspot.com/10919135 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@156109 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'ash')
-rw-r--r--ash/ash.gyp2
-rw-r--r--ash/display/mouse_cursor_event_filter.cc2
-rw-r--r--ash/drag_drop/drag_drop_controller.cc8
-rw-r--r--ash/drag_drop/drag_drop_controller.h2
-rw-r--r--ash/extended_desktop_unittest.cc6
-rw-r--r--ash/shell.cc3
-rw-r--r--ash/wm/cursor_manager.cc24
-rw-r--r--ash/wm/cursor_manager.h11
-rw-r--r--ash/wm/image_cursors.cc123
-rw-r--r--ash/wm/image_cursors.h43
-rw-r--r--ash/wm/toplevel_window_event_handler.cc6
11 files changed, 214 insertions, 16 deletions
diff --git a/ash/ash.gyp b/ash/ash.gyp
index e4b0877..8d1f53b 100644
--- a/ash/ash.gyp
+++ b/ash/ash.gyp
@@ -274,6 +274,8 @@
'wm/gestures/system_pinch_handler.h',
'wm/gestures/two_finger_drag_handler.cc',
'wm/gestures/two_finger_drag_handler.h',
+ 'wm/image_cursors.cc',
+ 'wm/image_cursors.h',
'wm/image_grid.cc',
'wm/image_grid.h',
'wm/maximize_bubble_controller.cc',
diff --git a/ash/display/mouse_cursor_event_filter.cc b/ash/display/mouse_cursor_event_filter.cc
index 2973ef8..469db41 100644
--- a/ash/display/mouse_cursor_event_filter.cc
+++ b/ash/display/mouse_cursor_event_filter.cc
@@ -153,6 +153,8 @@ bool MouseCursorEventFilter::WarpMouseCursorIfNecessary(
if (dst_root->bounds().Contains(point_in_dst_screen)) {
DCHECK_NE(dst_root, current_root);
dst_root->MoveCursorTo(point_in_dst_screen);
+ ash::Shell::GetInstance()->cursor_manager()->SetDeviceScaleFactor(
+ dst_root->AsRootWindowHostDelegate()->GetDeviceScaleFactor());
return true;
}
return false;
diff --git a/ash/drag_drop/drag_drop_controller.cc b/ash/drag_drop/drag_drop_controller.cc
index eb33f3d..acecc81 100644
--- a/ash/drag_drop/drag_drop_controller.cc
+++ b/ash/drag_drop/drag_drop_controller.cc
@@ -62,7 +62,6 @@ int DragDropController::StartDragAndDrop(const ui::OSExchangeData& data,
int operation) {
DCHECK(!IsDragDropInProgress());
- drag_cursor_ = ui::kCursorPointer;
drag_drop_tracker_.reset(new DragDropTracker(root_window));
drag_data_ = &data;
@@ -128,7 +127,6 @@ void DragDropController::DragUpdate(aura::Window* target,
cursor = ui::kCursorAlias;
else if (op & ui::DragDropTypes::DRAG_MOVE)
cursor = ui::kCursorMove;
- drag_cursor_ = cursor;
ash::Shell::GetInstance()->cursor_manager()->SetCursor(cursor);
}
}
@@ -145,7 +143,6 @@ void DragDropController::DragUpdate(aura::Window* target,
void DragDropController::Drop(aura::Window* target,
const ui::LocatedEvent& event) {
- drag_cursor_ = ui::kCursorPointer;
ash::Shell::GetInstance()->cursor_manager()->SetCursor(ui::kCursorPointer);
aura::client::DragDropDelegate* delegate = NULL;
@@ -175,7 +172,6 @@ void DragDropController::Drop(aura::Window* target,
}
void DragDropController::DragCancel() {
- drag_cursor_ = ui::kCursorPointer;
ash::Shell::GetInstance()->cursor_manager()->SetCursor(ui::kCursorPointer);
// |drag_window_| can be NULL if we have just started the drag and have not
@@ -197,10 +193,6 @@ bool DragDropController::IsDragDropInProgress() {
return !!drag_drop_tracker_.get();
}
-gfx::NativeCursor DragDropController::GetDragCursor() {
- return drag_cursor_;
-}
-
bool DragDropController::PreHandleKeyEvent(aura::Window* target,
ui::KeyEvent* event) {
if (IsDragDropInProgress() && event->key_code() == ui::VKEY_ESCAPE) {
diff --git a/ash/drag_drop/drag_drop_controller.h b/ash/drag_drop/drag_drop_controller.h
index d138ef6..59f1f32 100644
--- a/ash/drag_drop/drag_drop_controller.h
+++ b/ash/drag_drop/drag_drop_controller.h
@@ -59,7 +59,6 @@ class ASH_EXPORT DragDropController
const ui::LocatedEvent& event) OVERRIDE;
virtual void DragCancel() OVERRIDE;
virtual bool IsDragDropInProgress() OVERRIDE;
- virtual gfx::NativeCursor GetDragCursor() OVERRIDE;
// Overridden from aura::EventFilter:
virtual bool PreHandleKeyEvent(aura::Window* target,
@@ -92,7 +91,6 @@ class ASH_EXPORT DragDropController
gfx::Point drag_image_offset_;
const ui::OSExchangeData* drag_data_;
int drag_operation_;
- gfx::NativeCursor drag_cursor_;
// Window that is currently under the drag cursor.
aura::Window* drag_window_;
diff --git a/ash/extended_desktop_unittest.cc b/ash/extended_desktop_unittest.cc
index b1e9583..20e4115 100644
--- a/ash/extended_desktop_unittest.cc
+++ b/ash/extended_desktop_unittest.cc
@@ -165,17 +165,17 @@ TEST_F(ExtendedDesktopTest, SystemModal) {
TEST_F(ExtendedDesktopTest, TestCursor) {
UpdateDisplay("1000x600,600x400");
- Shell::GetInstance()->ShowCursor(false);
+ Shell::GetInstance()->cursor_manager()->ShowCursor(false);
Shell::RootWindowList root_windows = Shell::GetAllRootWindows();
EXPECT_FALSE(root_windows[0]->cursor_shown());
EXPECT_FALSE(root_windows[1]->cursor_shown());
- Shell::GetInstance()->ShowCursor(true);
+ Shell::GetInstance()->cursor_manager()->ShowCursor(true);
EXPECT_TRUE(root_windows[0]->cursor_shown());
EXPECT_TRUE(root_windows[1]->cursor_shown());
EXPECT_EQ(ui::kCursorPointer, root_windows[0]->last_cursor().native_type());
EXPECT_EQ(ui::kCursorPointer, root_windows[1]->last_cursor().native_type());
- Shell::GetInstance()->SetCursor(ui::kCursorCopy);
+ Shell::GetInstance()->cursor_manager()->SetCursor(ui::kCursorCopy);
EXPECT_EQ(ui::kCursorCopy, root_windows[0]->last_cursor().native_type());
EXPECT_EQ(ui::kCursorCopy, root_windows[1]->last_cursor().native_type());
}
diff --git a/ash/shell.cc b/ash/shell.cc
index 6c26a09..ebfa9eb 100644
--- a/ash/shell.cc
+++ b/ash/shell.cc
@@ -372,6 +372,9 @@ void Shell::Init() {
aura::RootWindow* root_window = display_controller_->GetPrimaryRootWindow();
active_root_window_ = root_window;
+ cursor_manager_.SetDeviceScaleFactor(
+ root_window->AsRootWindowHostDelegate()->GetDeviceScaleFactor());
+
#if !defined(OS_MACOSX)
nested_dispatcher_controller_.reset(new NestedDispatcherController);
accelerator_controller_.reset(new AcceleratorController);
diff --git a/ash/wm/cursor_manager.cc b/ash/wm/cursor_manager.cc
index 1ebc72b..3afee4b 100644
--- a/ash/wm/cursor_manager.cc
+++ b/ash/wm/cursor_manager.cc
@@ -5,8 +5,10 @@
#include "ash/wm/cursor_manager.h"
#include "ash/wm/cursor_delegate.h"
+#include "ash/wm/image_cursors.h"
#include "base/logging.h"
#include "ui/aura/env.h"
+#include "ui/base/cursor/cursor.h"
namespace ash {
@@ -15,7 +17,9 @@ CursorManager::CursorManager()
cursor_lock_count_(0),
did_cursor_change_(false),
cursor_to_set_on_unlock_(0),
- cursor_visible_(true) {
+ cursor_visible_(true),
+ current_cursor_(ui::kCursorNone),
+ image_cursors_(new ImageCursors) {
}
CursorManager::~CursorManager() {
@@ -42,7 +46,7 @@ void CursorManager::UnlockCursor() {
void CursorManager::SetCursor(gfx::NativeCursor cursor) {
if (cursor_lock_count_ == 0) {
if (delegate_)
- delegate_->SetCursor(cursor);
+ SetCursorInternal(cursor);
} else {
cursor_to_set_on_unlock_ = cursor;
did_cursor_change_ = true;
@@ -59,4 +63,20 @@ bool CursorManager::IsCursorVisible() const {
return cursor_visible_;
}
+void CursorManager::SetDeviceScaleFactor(float device_scale_factor) {
+ if (image_cursors_->GetDeviceScaleFactor() == device_scale_factor)
+ return;
+ image_cursors_->SetDeviceScaleFactor(device_scale_factor);
+ SetCursorInternal(current_cursor_);
+}
+
+void CursorManager::SetCursorInternal(gfx::NativeCursor cursor) {
+ DCHECK(delegate_);
+ current_cursor_ = cursor;
+ image_cursors_->SetPlatformCursor(&current_cursor_);
+ current_cursor_.set_device_scale_factor(
+ image_cursors_->GetDeviceScaleFactor());
+ delegate_->SetCursor(current_cursor_);
+}
+
} // namespace ash
diff --git a/ash/wm/cursor_manager.h b/ash/wm/cursor_manager.h
index 9f2cc8b..f5b5548 100644
--- a/ash/wm/cursor_manager.h
+++ b/ash/wm/cursor_manager.h
@@ -7,12 +7,14 @@
#include "base/basictypes.h"
#include "base/compiler_specific.h"
+#include "base/memory/scoped_ptr.h"
#include "ui/aura/aura_export.h"
#include "ui/aura/client/cursor_client.h"
#include "ui/gfx/native_widget_types.h"
namespace ash {
class CursorDelegate;
+class ImageCursors;
// This class controls the visibility and the type of the cursor.
// The cursor type can be locked so that the type stays the same
@@ -33,11 +35,15 @@ class CursorManager : public aura::client::CursorClient {
// Shows or hides the cursor.
bool cursor_visible() const { return cursor_visible_; }
+ // Overridden from aura::client::CursorClient:
virtual void SetCursor(gfx::NativeCursor) OVERRIDE;
virtual void ShowCursor(bool show) OVERRIDE;
virtual bool IsCursorVisible() const OVERRIDE;
+ virtual void SetDeviceScaleFactor(float device_scale_factor) OVERRIDE;
private:
+ void SetCursorInternal(gfx::NativeCursor cursor);
+
CursorDelegate* delegate_;
// Number of times LockCursor() has been invoked without a corresponding
@@ -54,6 +60,11 @@ class CursorManager : public aura::client::CursorClient {
// Is cursor visible?
bool cursor_visible_;
+ // The cursor currently set.
+ gfx::NativeCursor current_cursor_;
+
+ scoped_ptr<ImageCursors> image_cursors_;
+
DISALLOW_COPY_AND_ASSIGN(CursorManager);
};
diff --git a/ash/wm/image_cursors.cc b/ash/wm/image_cursors.cc
new file mode 100644
index 0000000..b0ec3f5
--- /dev/null
+++ b/ash/wm/image_cursors.cc
@@ -0,0 +1,123 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "ash/wm/image_cursors.h"
+
+#include "base/logging.h"
+#include "ui/base/cursor/cursor_loader.h"
+#include "ui/base/cursor/cursor.h"
+#include "ui/gfx/point.h"
+#include "grit/ui_resources.h"
+
+namespace {
+
+const int kAnimatedCursorFrameDelayMs = 25;
+
+struct HotPoint {
+ int x;
+ int y;
+};
+
+struct CursorData {
+ int id;
+ int resource_id;
+ HotPoint hot_1x;
+ HotPoint hot_2x;
+};
+
+// TODO(oshima): Remove this comment (http://crbug.com/141586).
+// The cursor's hot points are defined in chromeos cursor images at:
+// http://folder/kuscher/projects/Chrome_OS/Pointers/focuspoint
+const CursorData kImageCursors[] = {
+ {ui::kCursorNull, IDR_AURA_CURSOR_PTR, {4, 4}, {8, 9}},
+ {ui::kCursorPointer, IDR_AURA_CURSOR_PTR, {4, 4}, {8, 9}},
+ {ui::kCursorNoDrop, IDR_AURA_CURSOR_NO_DROP, {4, 4}, {8, 9}},
+ {ui::kCursorNotAllowed, IDR_AURA_CURSOR_NO_DROP, {4, 4}, {8, 9}},
+ {ui::kCursorCopy, IDR_AURA_CURSOR_COPY, {4, 4}, {8, 9}},
+ {ui::kCursorHand, IDR_AURA_CURSOR_HAND, {9, 4}, {19, 8}},
+ {ui::kCursorMove, IDR_AURA_CURSOR_MOVE, {11, 11}, {23, 23}},
+ {ui::kCursorNorthEastResize, IDR_AURA_CURSOR_NORTH_EAST_RESIZE,
+ {12, 11}, {25, 23}},
+ {ui::kCursorSouthWestResize, IDR_AURA_CURSOR_SOUTH_WEST_RESIZE,
+ {12, 11}, {25, 23}},
+ {ui::kCursorSouthEastResize, IDR_AURA_CURSOR_SOUTH_EAST_RESIZE,
+ {11, 11}, {24, 23}},
+ {ui::kCursorNorthWestResize, IDR_AURA_CURSOR_NORTH_WEST_RESIZE,
+ {11, 11}, {24, 23}},
+ {ui::kCursorNorthResize, IDR_AURA_CURSOR_NORTH_RESIZE, {11, 12}, {23, 23}},
+ {ui::kCursorSouthResize, IDR_AURA_CURSOR_SOUTH_RESIZE, {11, 12}, {23, 23}},
+ {ui::kCursorEastResize, IDR_AURA_CURSOR_EAST_RESIZE, {12, 11}, {25, 23}},
+ {ui::kCursorWestResize, IDR_AURA_CURSOR_WEST_RESIZE, {12, 11}, {25, 23}},
+ {ui::kCursorIBeam, IDR_AURA_CURSOR_IBEAM, {12, 12}, {24, 25}},
+ {ui::kCursorAlias, IDR_AURA_CURSOR_ALIAS, {8, 6}, {15, 11}},
+ {ui::kCursorCell, IDR_AURA_CURSOR_CELL, {11, 11}, {24, 23}},
+ {ui::kCursorContextMenu, IDR_AURA_CURSOR_CONTEXT_MENU, {4, 4}, {8, 9}},
+ {ui::kCursorCross, IDR_AURA_CURSOR_CROSSHAIR, {12, 12}, {25, 23}},
+ {ui::kCursorHelp, IDR_AURA_CURSOR_HELP, {4, 4}, {8, 9}},
+ {ui::kCursorVerticalText, IDR_AURA_CURSOR_XTERM_HORIZ, {12, 11}, {26, 23}},
+ {ui::kCursorZoomIn, IDR_AURA_CURSOR_ZOOM_IN, {10, 10}, {20, 20}},
+ {ui::kCursorZoomOut, IDR_AURA_CURSOR_ZOOM_OUT, {10, 10}, {20, 20}},
+ {ui::kCursorRowResize, IDR_AURA_CURSOR_ROW_RESIZE, {11, 12}, {23, 23}},
+ {ui::kCursorColumnResize, IDR_AURA_CURSOR_COL_RESIZE, {12, 11}, {25, 23}},
+ {ui::kCursorEastWestResize, IDR_AURA_CURSOR_EAST_WEST_RESIZE,
+ {12, 11}, {25, 23}},
+ {ui::kCursorNorthSouthResize, IDR_AURA_CURSOR_NORTH_SOUTH_RESIZE,
+ {11, 12}, {23, 23}},
+ {ui::kCursorNorthEastSouthWestResize,
+ IDR_AURA_CURSOR_NORTH_EAST_SOUTH_WEST_RESIZE, {12, 11}, {25, 23}},
+ {ui::kCursorNorthWestSouthEastResize,
+ IDR_AURA_CURSOR_NORTH_WEST_SOUTH_EAST_RESIZE, {11, 11}, {24, 23}},
+ {ui::kCursorGrab, IDR_AURA_CURSOR_GRAB, {8, 5}, {16, 10}},
+ {ui::kCursorGrabbing, IDR_AURA_CURSOR_GRABBING, {9, 9}, {18, 18}},
+};
+
+const CursorData kAnimatedCursors[] = {
+ {ui::kCursorWait, IDR_THROBBER, {7, 7}, {14, 14}},
+ {ui::kCursorProgress, IDR_THROBBER, {7, 7}, {14, 14}},
+};
+
+} // namespace
+
+namespace ash {
+
+ImageCursors::ImageCursors()
+ : cursor_loader_(ui::CursorLoader::Create()) {
+}
+
+ImageCursors::~ImageCursors() {
+}
+
+float ImageCursors::GetDeviceScaleFactor() const {
+ return cursor_loader_->device_scale_factor();
+}
+
+void ImageCursors::SetDeviceScaleFactor(float device_scale_factor) {
+ if (GetDeviceScaleFactor() == device_scale_factor)
+ return;
+
+ cursor_loader_->UnloadAll();
+ cursor_loader_->set_device_scale_factor(device_scale_factor);
+
+ for (size_t i = 0; i < arraysize(kImageCursors); ++i) {
+ const HotPoint& hot = device_scale_factor == 1.0f ?
+ kImageCursors[i].hot_1x : kImageCursors[i].hot_2x;
+ cursor_loader_->LoadImageCursor(kImageCursors[i].id,
+ kImageCursors[i].resource_id,
+ gfx::Point(hot.x, hot.y));
+ }
+ for (size_t i = 0; i < arraysize(kAnimatedCursors); ++i) {
+ const HotPoint& hot = device_scale_factor == 1.0f ?
+ kAnimatedCursors[i].hot_1x : kAnimatedCursors[i].hot_2x;
+ cursor_loader_->LoadAnimatedCursor(kAnimatedCursors[i].id,
+ kAnimatedCursors[i].resource_id,
+ gfx::Point(hot.x, hot.y),
+ kAnimatedCursorFrameDelayMs);
+ }
+}
+
+void ImageCursors::SetPlatformCursor(gfx::NativeCursor* cursor) {
+ cursor_loader_->SetPlatformCursor(cursor);
+}
+
+} // namespace ash
diff --git a/ash/wm/image_cursors.h b/ash/wm/image_cursors.h
new file mode 100644
index 0000000..a1a7c41
--- /dev/null
+++ b/ash/wm/image_cursors.h
@@ -0,0 +1,43 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef ASH_WM_IMAGE_CURSORS_H_
+#define ASH_WM_IMAGE_CURSORS_H_
+
+#include "ash/ash_export.h"
+#include "base/memory/scoped_ptr.h"
+#include "ui/gfx/native_widget_types.h"
+
+namespace ui {
+class CursorLoader;
+}
+
+namespace ash {
+
+// A utility class that provides cursors for NativeCursors for which we have
+// image resources.
+class ASH_EXPORT ImageCursors {
+ public:
+ ImageCursors();
+ ~ImageCursors();
+
+ // Returns the device scale factor of cursors.
+ float GetDeviceScaleFactor() const;
+
+ // Sets the device scale factor of the cursors with |device_scale_factor| and
+ // reloads the cursor images if necessary.
+ void SetDeviceScaleFactor(float device_scale_factor);
+
+ // Sets the platform cursor based on the native type of |cursor|.
+ void SetPlatformCursor(gfx::NativeCursor* cursor);
+
+ private:
+ scoped_ptr<ui::CursorLoader> cursor_loader_;
+
+ DISALLOW_COPY_AND_ASSIGN(ImageCursors);
+};
+
+} // namespace ash
+
+#endif // ASH_WM_IMAGE_CURSORS_H_
diff --git a/ash/wm/toplevel_window_event_handler.cc b/ash/wm/toplevel_window_event_handler.cc
index aa0f754..ce4be53 100644
--- a/ash/wm/toplevel_window_event_handler.cc
+++ b/ash/wm/toplevel_window_event_handler.cc
@@ -14,6 +14,7 @@
#include "base/message_loop.h"
#include "base/run_loop.h"
#include "ui/aura/client/aura_constants.h"
+#include "ui/aura/client/cursor_client.h"
#include "ui/aura/env.h"
#include "ui/aura/root_window.h"
#include "ui/aura/window.h"
@@ -276,7 +277,10 @@ aura::client::WindowMoveResult ToplevelWindowEventHandler::RunMoveLoop(
root_window, source->parent(), &drag_location);
}
CreateScopedWindowResizer(source, drag_location, HTCAPTION);
- source->GetRootWindow()->SetCursor(ui::kCursorPointer);
+ aura::client::CursorClient* cursor_client =
+ aura::client::GetCursorClient(root_window);
+ if (cursor_client)
+ cursor_client->SetCursor(ui::kCursorPointer);
#if !defined(OS_MACOSX)
MessageLoopForUI* loop = MessageLoopForUI::current();
MessageLoop::ScopedNestableTaskAllower allow_nested(loop);