Skip to content

Commit

Permalink
Support loading non system cursors in Chrome AURA/ASH windows.
Browse files Browse the repository at this point in the history
This is mostly intended to support special cursors passed by Webkit like the middle scroll panning cursor, etc.
On Windows AURA the code to load the platform cursor is implemented in CursorLoaderWin, which attempts to
load the cursor via the LoadCursor API always passing NULL as the module handle. This would not work for non
system cursors.

To enable support for the same added support to pass the cursor module name in the Cursor interfaces for AURA.
These include the following:-
1. CursorClient
2. CursorLoader
3. NativeCursorManager

Added a method SetCursorResourceModule to these interfaces. The NativeCursorManager is registered as the cursor client
in AURA/ASH. It forwards calls to the CursorClient which then forwards the calls over to the CursorLoader.

For ASH, I added a SetCursorResourceModule method to the ImageCursor class used by ASH.

We pass the resource dll name from RenderWidgetHostViewAura::UpdateCursorIfOverSelf method. 

Added code in the CursorLoaderWin::SetPlatformCursor function to use the platform cursor from the passed in cursor if
available, as the resource dll name may not be available to all cursor clients.

BUG=176079
Review URL: https://codereview.chromium.org/12903002

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@188911 0039d316-1c4b-4281-b951-d872f2087c98
  • Loading branch information
ananta@chromium.org committed Mar 19, 2013
1 parent 4f644da commit c21fcc5
Show file tree
Hide file tree
Showing 20 changed files with 114 additions and 14 deletions.
3 changes: 3 additions & 0 deletions ash/ash.gyp
Original file line number Diff line number Diff line change
Expand Up @@ -691,6 +691,9 @@
['exclude', 'magnifier/magnification_controller_unittest.cc'],
['exclude', 'wm/workspace/workspace_window_resizer_unittest.cc'],
],
'sources': [
'<(SHARED_INTERMEDIATE_DIR)/ui/ui_resources/ui_unscaled_resources.rc',
],
# TODO(jschuh): crbug.com/167187 fix size_t to int truncations.
'msvs_disabled_warnings': [ 4267, ],
}],
Expand Down
6 changes: 6 additions & 0 deletions ash/wm/ash_native_cursor_manager.cc
Original file line number Diff line number Diff line change
Expand Up @@ -107,4 +107,10 @@ void AshNativeCursorManager::SetMouseEventsEnabled(
NotifyMouseEventsEnableStateChange(enabled);
}

void AshNativeCursorManager::SetCursorResourceModule(
const string16& module_name) {
image_cursors_->SetCursorResourceModule(module_name);
}


} // namespace ash
2 changes: 2 additions & 0 deletions ash/wm/ash_native_cursor_manager.h
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
#include "base/basictypes.h"
#include "base/compiler_specific.h"
#include "base/memory/scoped_ptr.h"
#include "base/string16.h"
#include "ui/gfx/native_widget_types.h"
#include "ui/gfx/point.h"
#include "ui/views/corewm/native_cursor_manager.h"
Expand Down Expand Up @@ -48,6 +49,7 @@ class ASH_EXPORT AshNativeCursorManager
virtual void SetMouseEventsEnabled(
bool enabled,
views::corewm::NativeCursorManagerDelegate* delegate) OVERRIDE;
virtual void SetCursorResourceModule(const string16& module_name) OVERRIDE;

// The cursor location where the cursor was disabled.
gfx::Point disabled_cursor_location_;
Expand Down
8 changes: 6 additions & 2 deletions ash/wm/ash_native_cursor_manager_unittest.cc
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,9 @@ TEST_F(AshNativeCursorManagerTest, LockCursor) {
CursorManager* cursor_manager = Shell::GetInstance()->cursor_manager();
CursorManagerTestApi test_api(cursor_manager);
gfx::Display display(0);

#if defined(OS_WIN)
cursor_manager->SetCursorResourceModule(L"ash_unittests.exe");
#endif
cursor_manager->SetCursor(ui::kCursorCopy);
EXPECT_EQ(ui::kCursorCopy, test_api.GetCurrentCursor().native_type());
display.set_device_scale_factor(2.0f);
Expand Down Expand Up @@ -85,7 +87,9 @@ TEST_F(AshNativeCursorManagerTest, LockCursor) {
TEST_F(AshNativeCursorManagerTest, SetCursor) {
CursorManager* cursor_manager = Shell::GetInstance()->cursor_manager();
CursorManagerTestApi test_api(cursor_manager);

#if defined(OS_WIN)
cursor_manager->SetCursorResourceModule(L"ash_unittests.exe");
#endif
cursor_manager->SetCursor(ui::kCursorCopy);
EXPECT_EQ(ui::kCursorCopy, test_api.GetCurrentCursor().native_type());
EXPECT_TRUE(test_api.GetCurrentCursor().platform());
Expand Down
5 changes: 5 additions & 0 deletions ash/wm/image_cursors.cc
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
#include "ash/wm/image_cursors.h"

#include "base/logging.h"
#include "base/string16.h"
#include "ui/base/cursor/cursor_loader.h"
#include "ui/base/cursor/cursor.h"
#include "ui/gfx/display.h"
Expand Down Expand Up @@ -134,4 +135,8 @@ void ImageCursors::SetPlatformCursor(gfx::NativeCursor* cursor) {
cursor_loader_->SetPlatformCursor(cursor);
}

void ImageCursors::SetCursorResourceModule(const string16& module_name) {
cursor_loader_->SetCursorResourceModule(module_name);
}

} // namespace ash
4 changes: 4 additions & 0 deletions ash/wm/image_cursors.h
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@

#include "ash/ash_export.h"
#include "base/memory/scoped_ptr.h"
#include "base/string16.h"
#include "ui/gfx/native_widget_types.h"

namespace gfx {
Expand Down Expand Up @@ -39,6 +40,9 @@ class ASH_EXPORT ImageCursors {
// Sets the platform cursor based on the native type of |cursor|.
void SetPlatformCursor(gfx::NativeCursor* cursor);

// Sets the cursor resource module name for non system cursors.
void SetCursorResourceModule(const string16& module_name);

private:
scoped_ptr<ui::CursorLoader> cursor_loader_;

Expand Down
11 changes: 10 additions & 1 deletion content/browser/renderer_host/render_widget_host_view_aura.cc
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@
#include "content/port/browser/render_widget_host_view_port.h"
#include "content/public/browser/browser_context.h"
#include "content/public/browser/browser_thread.h"
#include "content/public/browser/content_browser_client.h"
#include "content/public/browser/render_process_host.h"
#include "content/public/browser/render_view_host.h"
#include "content/public/browser/user_metrics.h"
Expand Down Expand Up @@ -2449,8 +2450,16 @@ void RenderWidgetHostViewAura::UpdateCursorIfOverSelf() {

aura::client::CursorClient* cursor_client =
aura::client::GetCursorClient(root_window);
if (cursor_client)
if (cursor_client) {
#if defined(OS_WIN)
if (GetContentClient() && GetContentClient()->browser() &&
GetContentClient()->browser()->GetResourceDllName()) {
cursor_client->SetCursorResourceModule(
GetContentClient()->browser()->GetResourceDllName());
}
#endif
cursor_client->SetCursor(cursor);
}
}

ui::InputMethod* RenderWidgetHostViewAura::GetInputMethod() const {
Expand Down
1 change: 1 addition & 0 deletions ui/DEPS
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ include_rules = [
"+grit/native_theme_resources.h",
"+grit/ui_resources.h",
"+grit/ui_strings.h",
"+grit/ui_unscaled_resources.h",
"+jni",
"+net",
"+skia",
Expand Down
5 changes: 5 additions & 0 deletions ui/aura/client/cursor_client.h
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
#ifndef UI_AURA_CLIENT_CURSOR_CLIENT_H_
#define UI_AURA_CLIENT_CURSOR_CLIENT_H_

#include "base/string16.h"
#include "ui/aura/aura_export.h"
#include "ui/gfx/native_widget_types.h"

Expand Down Expand Up @@ -55,6 +56,10 @@ class AURA_EXPORT CursorClient {
// EnableMouseEvents/DisableMouseEvents.
virtual void UnlockCursor() = 0;

// Used to pass the cursor resource module name to the cursor loader. This is
// typically used to load non system cursors.
virtual void SetCursorResourceModule(const string16& module_name) = 0;

protected:
virtual ~CursorClient() {}
};
Expand Down
5 changes: 5 additions & 0 deletions ui/base/cursor/cursor_loader.h
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
#define UI_BASE_CURSOR_CURSOR_LOADER_H_

#include "base/logging.h"
#include "base/string16.h"
#include "ui/base/ui_export.h"
#include "ui/gfx/display.h"
#include "ui/gfx/native_widget_types.h"
Expand Down Expand Up @@ -49,6 +50,10 @@ class UI_EXPORT CursorLoader {
// Sets the platform cursor based on the native type of |cursor|.
virtual void SetPlatformCursor(gfx::NativeCursor* cursor) = 0;

// Used to pass the cursor resource module name to the cursor loader. This is
// typically used to load non system cursors.
virtual void SetCursorResourceModule(const string16& module_name) = 0;

// Creates a CursorLoader.
static CursorLoader* Create();

Expand Down
50 changes: 39 additions & 11 deletions ui/base/cursor/cursor_loader_win.cc
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
// found in the LICENSE file.

#include "ui/base/cursor/cursor_loader_win.h"
#include "grit/ui_unscaled_resources.h"

namespace ui {

Expand Down Expand Up @@ -59,29 +60,46 @@ const wchar_t* GetCursorId(gfx::NativeCursor native_cursor) {
case kCursorNotAllowed:
return IDC_NO;
case kCursorColumnResize:
return MAKEINTRESOURCE(IDC_COLRESIZE);
case kCursorRowResize:
return MAKEINTRESOURCE(IDC_ROWRESIZE);
case kCursorMiddlePanning:
return MAKEINTRESOURCE(IDC_PAN_MIDDLE);
case kCursorEastPanning:
return MAKEINTRESOURCE(IDC_PAN_EAST);
case kCursorNorthPanning:
return MAKEINTRESOURCE(IDC_PAN_NORTH);
case kCursorNorthEastPanning:
return MAKEINTRESOURCE(IDC_PAN_NORTH_EAST);
case kCursorNorthWestPanning:
return MAKEINTRESOURCE(IDC_PAN_NORTH_WEST);
case kCursorSouthPanning:
return MAKEINTRESOURCE(IDC_PAN_SOUTH);
case kCursorSouthEastPanning:
return MAKEINTRESOURCE(IDC_PAN_SOUTH_EAST);
case kCursorSouthWestPanning:
return MAKEINTRESOURCE(IDC_PAN_SOUTH_WEST);
case kCursorWestPanning:
return MAKEINTRESOURCE(IDC_PAN_WEST);
case kCursorVerticalText:
return MAKEINTRESOURCE(IDC_VERTICALTEXT);
case kCursorCell:
case kCursorContextMenu:
case kCursorAlias:
case kCursorCopy:
case kCursorNone:
return MAKEINTRESOURCE(IDC_CELL);
case kCursorZoomIn:
return MAKEINTRESOURCE(IDC_ZOOMIN);
case kCursorZoomOut:
return MAKEINTRESOURCE(IDC_ZOOMOUT);
case kCursorGrab:
return MAKEINTRESOURCE(IDC_HAND_GRAB);
case kCursorGrabbing:
return MAKEINTRESOURCE(IDC_HAND_GRABBING);
case kCursorCopy:
return MAKEINTRESOURCE(IDC_COPYCUR);
case kCursorAlias:
return MAKEINTRESOURCE(IDC_ALIAS);
case kCursorContextMenu:
case kCursorNone:
case kCursorCustom:
// TODO(jamescook): Should we use WebKit glue resources for these?
// Or migrate those resources to someplace ui/aura can share?
NOTIMPLEMENTED();
return IDC_ARROW;
default:
Expand Down Expand Up @@ -124,13 +142,23 @@ void CursorLoaderWin::UnloadAll() {
void CursorLoaderWin::SetPlatformCursor(gfx::NativeCursor* cursor) {
#if defined(USE_AURA)
if (cursor->native_type() != kCursorCustom) {
const wchar_t* cursor_id = GetCursorId(*cursor);

// TODO(jamescook): Support for non-system cursors will require finding
// the appropriate module to pass to LoadCursor().
cursor->SetPlatformCursor(LoadCursor(NULL, cursor_id));
if (cursor->platform()) {
cursor->SetPlatformCursor(cursor->platform());
} else {
const wchar_t* cursor_id = GetCursorId(*cursor);
PlatformCursor platform_cursor = LoadCursor(NULL, cursor_id);
if (!platform_cursor && !cursor_resource_module_name_.empty()) {
platform_cursor = LoadCursor(
GetModuleHandle(cursor_resource_module_name_.c_str()), cursor_id);
}
cursor->SetPlatformCursor(platform_cursor);
}
}
#endif
}

void CursorLoaderWin::SetCursorResourceModule(const string16& module_name) {
cursor_resource_module_name_ = module_name;
}

} // namespace ui
4 changes: 4 additions & 0 deletions ui/base/cursor/cursor_loader_win.h
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
#define UI_BASE_CURSOR_CURSOR_LOADER_WIN_H_

#include "base/compiler_specific.h"
#include "base/string16.h"
#include "ui/base/cursor/cursor_loader.h"

namespace ui {
Expand All @@ -25,8 +26,11 @@ class UI_EXPORT CursorLoaderWin : public CursorLoader {
int frame_delay_ms) OVERRIDE;
virtual void UnloadAll() OVERRIDE;
virtual void SetPlatformCursor(gfx::NativeCursor* cursor) OVERRIDE;
virtual void SetCursorResourceModule(const string16& module_name) OVERRIDE;

private:
string16 cursor_resource_module_name_;

DISALLOW_COPY_AND_ASSIGN(CursorLoaderWin);
};

Expand Down
2 changes: 2 additions & 0 deletions ui/base/cursor/cursor_loader_x11.h
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,8 @@ class UI_EXPORT CursorLoaderX11 : public CursorLoader {
int frame_delay_ms) OVERRIDE;
virtual void UnloadAll() OVERRIDE;
virtual void SetPlatformCursor(gfx::NativeCursor* cursor) OVERRIDE;
virtual void SetCursorResourceModule(const string16& module_name) OVERRIDE {
}

private:
// Returns true if we have an image resource loaded for the |native_cursor|.
Expand Down
3 changes: 3 additions & 0 deletions ui/views/corewm/compound_event_filter_unittest.cc
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,9 @@ class TestCursorClient : public aura::client::CursorClient {
virtual void UnlockCursor() OVERRIDE {
}

virtual void SetCursorResourceModule(const string16& module_name) OVERRIDE {
}

private:
bool visible_;
bool mouse_events_enabled_;
Expand Down
4 changes: 4 additions & 0 deletions ui/views/corewm/cursor_manager.cc
Original file line number Diff line number Diff line change
Expand Up @@ -150,6 +150,10 @@ void CursorManager::UnlockCursor() {
}
}

void CursorManager::SetCursorResourceModule(const string16& module_name) {
delegate_->SetCursorResourceModule(module_name);
}

gfx::NativeCursor CursorManager::GetCurrentCursor() const {
return current_state_->cursor();
}
Expand Down
1 change: 1 addition & 0 deletions ui/views/corewm/cursor_manager.h
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,7 @@ class VIEWS_EXPORT CursorManager : public aura::client::CursorClient,
virtual void SetDisplay(const gfx::Display& display) OVERRIDE;
virtual void LockCursor() OVERRIDE;
virtual void UnlockCursor() OVERRIDE;
virtual void SetCursorResourceModule(const string16& module_name) OVERRIDE;

private:
// Overridden from NativeCursorManagerDelegate:
Expand Down
3 changes: 3 additions & 0 deletions ui/views/corewm/cursor_manager_unittest.cc
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,9 @@ class TestingCursorManager : public views::corewm::NativeCursorManager {
delegate->CommitMouseEventsEnabled(enabled);
}

virtual void SetCursorResourceModule(const string16& module_name) OVERRIDE {
}

private:
gfx::NativeCursor cursor_;
};
Expand Down
5 changes: 5 additions & 0 deletions ui/views/corewm/native_cursor_manager.h
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
#ifndef UI_VIEWS_COREWM_NATIVE_CURSOR_MANAGER_H_
#define UI_VIEWS_COREWM_NATIVE_CURSOR_MANAGER_H_

#include "base/string16.h"
#include "ui/views/corewm/native_cursor_manager_delegate.h"
#include "ui/views/views_export.h"

Expand Down Expand Up @@ -48,6 +49,10 @@ class VIEWS_EXPORT NativeCursorManager {
virtual void SetMouseEventsEnabled(
bool enabled,
views::corewm::NativeCursorManagerDelegate* delegate) = 0;

// Used to pass the cursor resource module name to the cursor loader. This is
// typically used to load non system cursors.
virtual void SetCursorResourceModule(const string16& module_name) = 0;
};

} // namespace corewm
Expand Down
5 changes: 5 additions & 0 deletions ui/views/widget/desktop_aura/desktop_native_cursor_manager.cc
Original file line number Diff line number Diff line change
Expand Up @@ -66,4 +66,9 @@ void DesktopNativeCursorManager::SetMouseEventsEnabled(
root_window_->OnMouseEventsEnableStateChanged(enabled);
}

void DesktopNativeCursorManager::SetCursorResourceModule(
const string16& module_name) {
cursor_loader_->SetCursorResourceModule(module_name);
}

} // namespace views
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@ class VIEWS_EXPORT DesktopNativeCursorManager
virtual void SetMouseEventsEnabled(
bool enabled,
views::corewm::NativeCursorManagerDelegate* delegate) OVERRIDE;
virtual void SetCursorResourceModule(const string16& module_name) OVERRIDE;

aura::RootWindow* root_window_;
scoped_ptr<ui::CursorLoader> cursor_loader_;
Expand Down

0 comments on commit c21fcc5

Please sign in to comment.