summaryrefslogtreecommitdiffstats
path: root/video
diff options
context:
space:
mode:
authorJames Ross-Gowan <rossymiles@gmail.com>2013-07-14 22:57:39 +1000
committerwm4 <wm4@nowhere>2013-07-21 18:05:22 +0200
commitd784759bc05bcc62401940148d9aaa7cace6975c (patch)
treea961423a49b49a1070cff70ddab5c2c470b1e6e9 /video
parent5f265d5930588a4a1b065e18a84b25a15b4b1d66 (diff)
downloadmpv-d784759bc05bcc62401940148d9aaa7cace6975c.tar.bz2
mpv-d784759bc05bcc62401940148d9aaa7cace6975c.tar.xz
w32_common: show the cursor in the window border
When the cursor was in the window border, it could be hidden but it wouldn't appear again, since mpv doesn't process mouse input there. The code used ShowCursor, which is a horrid stateful API designed for mouseless Win16 systems that incremented or decremented a global counter to keep track of how many applications needed to display a special cursor (like a busy cursor.) Replace that with a simple flag, handle WM_SETCURSOR and use SetCursor(NULL) to hide the mouse cursor, but only when the mouse is in the client area. DefWindowProc will set the correct cursor on the border as long as it isn't hidden with ShowCursor. PowerPoint also uses SetCursor(NULL) to hide the cursor when showing a presentation, so it's probably safe. See http://blogs.msdn.com/b/oldnewthing/archive/2009/12/17/9937972.aspx
Diffstat (limited to 'video')
-rw-r--r--video/out/w32_common.c27
-rw-r--r--video/out/w32_common.h1
2 files changed, 22 insertions, 6 deletions
diff --git a/video/out/w32_common.c b/video/out/w32_common.c
index 69a98e94ed..b51078b5f1 100644
--- a/video/out/w32_common.c
+++ b/video/out/w32_common.c
@@ -221,6 +221,12 @@ static LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam,
}
break;
}
+ case WM_SETCURSOR:
+ if (LOWORD(lParam) == HTCLIENT && !w32->cursor_visible) {
+ SetCursor(NULL);
+ return TRUE;
+ }
+ break;
case WM_MOUSEMOVE:
vo_mouse_movement(vo, GET_X_LPARAM(lParam), GET_Y_LPARAM(lParam));
break;
@@ -592,7 +598,7 @@ int vo_w32_init(struct vo *vo)
.lpfnWndProc = WndProc,
.hInstance = hInstance,
.hIcon = mplayerIcon,
- .hCursor = LoadCursor(0, IDC_ARROW),
+ .hCursor = LoadCursor(NULL, IDC_ARROW),
.lpszClassName = classname,
.hIconSm = mplayerIcon,
};
@@ -628,6 +634,7 @@ int vo_w32_init(struct vo *vo)
if (vo->opts->WinID >= 0)
EnableWindow(w32->window, 0);
+ w32->cursor_visible = true;
// we don't have proper event handling
vo->wakeup_period = 0.02;
@@ -678,6 +685,12 @@ static void vo_w32_ontop(struct vo *vo)
reinit_window_state(vo);
}
+static bool vo_w32_is_cursor_in_client(struct vo *vo)
+{
+ DWORD pos = GetMessagePos();
+ return SendMessage(vo->w32->window, WM_NCHITTEST, 0, pos) == HTCLIENT;
+}
+
int vo_w32_control(struct vo *vo, int *events, int request, void *arg)
{
struct vo_w32_state *w32 = vo->w32;
@@ -700,10 +713,13 @@ int vo_w32_control(struct vo *vo, int *events, int request, void *arg)
w32_update_xinerama_info(vo);
return VO_TRUE;
case VOCTRL_SET_CURSOR_VISIBILITY:
- if (*(bool *)arg) {
- while (ShowCursor(1) < 0) { }
- } else {
- while (ShowCursor(0) >= 0) { }
+ w32->cursor_visible = *(bool *)arg;
+
+ if (vo_w32_is_cursor_in_client(vo)) {
+ if (w32->cursor_visible)
+ SetCursor(LoadCursor(NULL, IDC_ARROW));
+ else
+ SetCursor(NULL);
}
return VO_TRUE;
case VOCTRL_KILL_SCREENSAVER:
@@ -737,7 +753,6 @@ void vo_w32_uninit(struct vo *vo)
mp_msg(MSGT_VO, MSGL_V, "vo: win32: uninit\n");
if (!w32)
return;
- while (ShowCursor(1) < 0) { }
SetThreadExecutionState(ES_CONTINUOUS);
DestroyWindow(w32->window);
UnregisterClassW(classname, 0);
diff --git a/video/out/w32_common.h b/video/out/w32_common.h
index 3db34a8472..8465f028d6 100644
--- a/video/out/w32_common.h
+++ b/video/out/w32_common.h
@@ -45,6 +45,7 @@ struct vo_w32_state {
uint32_t o_dheight;
bool disable_screensaver;
+ bool cursor_visible;
int event_flags;
int mon_cnt;
int mon_id;