From 7c439f371010b271a9523ff210aef6a1fe4a7902 Mon Sep 17 00:00:00 2001 From: Andre Weissflog Date: Sat, 19 Sep 2020 19:19:44 +0200 Subject: sokol_audio.h win32: ignore CoInitializeEx return value (fixes #381) --- sokol_audio.h | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/sokol_audio.h b/sokol_audio.h index dd6d2d63..d016720a 100644 --- a/sokol_audio.h +++ b/sokol_audio.h @@ -1187,11 +1187,12 @@ _SOKOL_PRIVATE void _saudio_wasapi_release(void) { } _SOKOL_PRIVATE bool _saudio_backend_init(void) { - REFERENCE_TIME dur; - if (FAILED(CoInitializeEx(0, COINIT_MULTITHREADED))) { - SOKOL_LOG("sokol_audio wasapi: CoInitializeEx failed"); - return false; - } + /* CoInitializeEx could have been called elsewhere already, in which + case the function returns with S_FALSE (thus it doesn't make much + sense to check the result) + */ + CoInitializeEx(0, COINIT_MULTITHREADED); + _saudio.backend.thread.buffer_end_event = CreateEvent(0, FALSE, FALSE, 0); if (0 == _saudio.backend.thread.buffer_end_event) { SOKOL_LOG("sokol_audio wasapi: failed to create buffer_end_event"); @@ -1228,8 +1229,7 @@ _SOKOL_PRIVATE bool _saudio_backend_init(void) { fmt.wBitsPerSample = 16; fmt.nBlockAlign = (fmt.nChannels * fmt.wBitsPerSample) / 8; fmt.nAvgBytesPerSec = fmt.nSamplesPerSec * fmt.nBlockAlign; - dur = (REFERENCE_TIME) - (((double)_saudio.buffer_frames) / (((double)_saudio.sample_rate) * (1.0/10000000.0))); + REFERENCE_TIME dur = (REFERENCE_TIME) (((double)_saudio.buffer_frames) / (((double)_saudio.sample_rate) * (1.0/10000000.0))); if (FAILED(IAudioClient_Initialize(_saudio.backend.audio_client, AUDCLNT_SHAREMODE_SHARED, AUDCLNT_STREAMFLAGS_EVENTCALLBACK|AUDCLNT_STREAMFLAGS_AUTOCONVERTPCM|AUDCLNT_STREAMFLAGS_SRC_DEFAULT_QUALITY, -- cgit v1.2.3 From fcc33fdc81c97ec4e5473c27560379ce94917a0a Mon Sep 17 00:00:00 2001 From: Andre Weissflog Date: Tue, 22 Sep 2020 15:56:25 +0200 Subject: sokol_audio.h: blind fix for #386 (can't reproduce this though) --- sokol_audio.h | 22 +++++++++++++--------- 1 file changed, 13 insertions(+), 9 deletions(-) diff --git a/sokol_audio.h b/sokol_audio.h index d016720a..bf7e4a71 100644 --- a/sokol_audio.h +++ b/sokol_audio.h @@ -1191,8 +1191,9 @@ _SOKOL_PRIVATE bool _saudio_backend_init(void) { case the function returns with S_FALSE (thus it doesn't make much sense to check the result) */ - CoInitializeEx(0, COINIT_MULTITHREADED); - + HRESULT hr = CoInitializeEx(0, COINIT_MULTITHREADED); + _SOKOL_UNUSED(hr); + _saudio.backend.thread.buffer_end_event = CreateEvent(0, FALSE, FALSE, 0); if (0 == _saudio.backend.thread.buffer_end_event) { SOKOL_LOG("sokol_audio wasapi: failed to create buffer_end_event"); @@ -1229,14 +1230,17 @@ _SOKOL_PRIVATE bool _saudio_backend_init(void) { fmt.wBitsPerSample = 16; fmt.nBlockAlign = (fmt.nChannels * fmt.wBitsPerSample) / 8; fmt.nAvgBytesPerSec = fmt.nSamplesPerSec * fmt.nBlockAlign; - REFERENCE_TIME dur = (REFERENCE_TIME) (((double)_saudio.buffer_frames) / (((double)_saudio.sample_rate) * (1.0/10000000.0))); - if (FAILED(IAudioClient_Initialize(_saudio.backend.audio_client, - AUDCLNT_SHAREMODE_SHARED, - AUDCLNT_STREAMFLAGS_EVENTCALLBACK|AUDCLNT_STREAMFLAGS_AUTOCONVERTPCM|AUDCLNT_STREAMFLAGS_SRC_DEFAULT_QUALITY, - dur, 0, &fmt, 0))) + /* extra scope block to silence warning about goto skipping variable declaration */ { - SOKOL_LOG("sokol_audio wasapi: audio client initialize failed"); - goto error; + REFERENCE_TIME dur = (REFERENCE_TIME) (((double)_saudio.buffer_frames) / (((double)_saudio.sample_rate) * (1.0/10000000.0))); + if (FAILED(IAudioClient_Initialize(_saudio.backend.audio_client, + AUDCLNT_SHAREMODE_SHARED, + AUDCLNT_STREAMFLAGS_EVENTCALLBACK|AUDCLNT_STREAMFLAGS_AUTOCONVERTPCM|AUDCLNT_STREAMFLAGS_SRC_DEFAULT_QUALITY, + dur, 0, &fmt, 0))) + { + SOKOL_LOG("sokol_audio wasapi: audio client initialize failed"); + goto error; + } } if (FAILED(IAudioClient_GetBufferSize(_saudio.backend.audio_client, &_saudio.backend.thread.dst_buffer_frames))) { SOKOL_LOG("sokol_audio wasapi: audio client get buffer size failed"); -- cgit v1.2.3 From 78b9b6c4787ae4569e636168ac8ce33adec18941 Mon Sep 17 00:00:00 2001 From: Andre Weissflog Date: Tue, 22 Sep 2020 17:46:33 +0200 Subject: sokol_app.h win32: call SetCapture/ReleaseCapture on mouse button down/up Fixes #329 --- README.md | 11 ++++++++++- sokol_app.h | 24 ++++++++++++++++++++++++ 2 files changed, 34 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index 229a6cac..554ebb08 100644 --- a/README.md +++ b/README.md @@ -6,7 +6,7 @@ Simple [STB-style](https://github.com/nothings/stb/blob/master/docs/stb_howto.txt) cross-platform libraries for C and C++, written in C. -[See what's new](#updates) (**31-Aug-2020**: sokol_gfx.h and sokol_app.h automatically select D3D11 C++ or C API) +[See what's new](#updates) (**22-Sep-2020** sokol_app.h SetCapture/ReleaseCapture) [Live Samples](https://floooh.github.io/sokol-html5/index.html) via WASM. @@ -460,6 +460,15 @@ Mainly some "missing features" for desktop apps: # Updates +- **22-Sep-2020**: + A small fix in sokol_app.h: when a mouse button is pressed, mouse input + is now 'captured' by calling SetCapture(), and when the last mouse button + is released, ReleaseCapture() is called. This also provides mouse events + outside the window area as long as a mouse button is pressed, which is + useful for windowed UI applicaction. This is not the same as the more + 'rigorous' pointer-lock feature though (which is more useful for + camera-controls) + - **31-Aug-2020**: Internal change: The D3D11/DXGI backend code in sokol_gfx.h and sokol_app.h now use the D3D11 and DXGI C++-APIs when the implementation is compiled as diff --git a/sokol_app.h b/sokol_app.h index 1f92d908..6ef0bcaa 100644 --- a/sokol_app.h +++ b/sokol_app.h @@ -1418,6 +1418,7 @@ typedef struct { bool in_create_window; bool iconified; bool mouse_tracked; + uint8_t mouse_capture_mask; _sapp_win32_dpi_t dpi; bool raw_input_mousepos_valid; LONG raw_input_mousepos_x; @@ -4850,6 +4851,22 @@ _SOKOL_PRIVATE void _sapp_win32_show_mouse(bool visible) { ShowCursor((BOOL)visible); } +_SOKOL_PRIVATE void _sapp_win32_capture_mouse(uint8_t btn_mask) { + if (0 == _sapp.win32.mouse_capture_mask) { + SetCapture(_sapp.win32.hwnd); + } + _sapp.win32.mouse_capture_mask |= btn_mask; +} + +_SOKOL_PRIVATE void _sapp_win32_release_mouse(uint8_t btn_mask) { + if (0 != _sapp.win32.mouse_capture_mask) { + _sapp.win32.mouse_capture_mask &= ~btn_mask; + if (0 == _sapp.win32.mouse_capture_mask) { + ReleaseCapture(); + } + } +} + _SOKOL_PRIVATE void _sapp_win32_lock_mouse(bool lock) { if (lock == _sapp.mouse.locked) { return; @@ -4857,6 +4874,7 @@ _SOKOL_PRIVATE void _sapp_win32_lock_mouse(bool lock) { _sapp.mouse.dx = 0.0f; _sapp.mouse.dy = 0.0f; _sapp.mouse.locked = lock; + _sapp_win32_release_mouse(0xFF); if (_sapp.mouse.locked) { /* store the current mouse position, so it can be restored when unlocked */ POINT pos; @@ -5195,21 +5213,27 @@ _SOKOL_PRIVATE LRESULT CALLBACK _sapp_win32_wndproc(HWND hWnd, UINT uMsg, WPARAM break; case WM_LBUTTONDOWN: _sapp_win32_mouse_event(SAPP_EVENTTYPE_MOUSE_DOWN, SAPP_MOUSEBUTTON_LEFT); + _sapp_win32_capture_mouse(1< Date: Tue, 22 Sep 2020 17:53:50 +0200 Subject: make the readme about mouse capture a bit clearer --- README.md | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index 554ebb08..1d14364b 100644 --- a/README.md +++ b/README.md @@ -6,7 +6,7 @@ Simple [STB-style](https://github.com/nothings/stb/blob/master/docs/stb_howto.txt) cross-platform libraries for C and C++, written in C. -[See what's new](#updates) (**22-Sep-2020** sokol_app.h SetCapture/ReleaseCapture) +[See what's new](#updates) (**22-Sep-2020** sokol_app.h win32: mouse input SetCapture/ReleaseCapture) [Live Samples](https://floooh.github.io/sokol-html5/index.html) via WASM. @@ -461,12 +461,12 @@ Mainly some "missing features" for desktop apps: # Updates - **22-Sep-2020**: - A small fix in sokol_app.h: when a mouse button is pressed, mouse input - is now 'captured' by calling SetCapture(), and when the last mouse button - is released, ReleaseCapture() is called. This also provides mouse events - outside the window area as long as a mouse button is pressed, which is - useful for windowed UI applicaction. This is not the same as the more - 'rigorous' pointer-lock feature though (which is more useful for + A small fix in sokol_app.h's Win32 backend: when a mouse button is pressed, + mouse input is now 'captured' by calling SetCapture(), and when the last + mouse button is released, ReleaseCapture() is called. This also provides + mouse events outside the window area as long as a mouse button is pressed, + which is useful for windowed UI applicaction. This is not the same as the + more 'rigorous' pointer-lock feature though (which is more useful for camera-controls) - **31-Aug-2020**: -- cgit v1.2.3 From 210f2884f8bdbdd7cc4515c285be42b56584ac31 Mon Sep 17 00:00:00 2001 From: Andre Weissflog Date: Tue, 22 Sep 2020 17:56:04 +0200 Subject: fix readme typos --- README.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 1d14364b..f763fade 100644 --- a/README.md +++ b/README.md @@ -465,8 +465,8 @@ Mainly some "missing features" for desktop apps: mouse input is now 'captured' by calling SetCapture(), and when the last mouse button is released, ReleaseCapture() is called. This also provides mouse events outside the window area as long as a mouse button is pressed, - which is useful for windowed UI applicaction. This is not the same as the - more 'rigorous' pointer-lock feature though (which is more useful for + which is useful for windowed UI applicactions (this is not the same as the + more 'rigorous' and explicit pointer-lock feature which is more useful for camera-controls) - **31-Aug-2020**: -- cgit v1.2.3 From c6f54195f5b77565f8e3ba5f3c1d4f5a675185bc Mon Sep 17 00:00:00 2001 From: Andre Weissflog Date: Tue, 22 Sep 2020 18:31:19 +0200 Subject: sokol_app.h macos: implement otherMouseDragged handler --- sokol_app.h | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/sokol_app.h b/sokol_app.h index 6ef0bcaa..4f331cb1 100644 --- a/sokol_app.h +++ b/sokol_app.h @@ -2868,7 +2868,15 @@ _SOKOL_PRIVATE void _sapp_macos_frame(void) { _sapp_macos_mouse_event(SAPP_EVENTTYPE_MOUSE_UP, SAPP_MOUSEBUTTON_MIDDLE, _sapp_macos_mod(event.modifierFlags)); } } -// FIXME: otherMouseDragged? +- (void)otherMouseDragged:(NSEvent*)event { + if (2 == event.buttonNumber) { + if (_sapp.mouse.locked) { + _sapp.mouse.dx = [event deltaX]; + _sapp.mouse.dy = [event deltaY]; + } + _sapp_macos_mouse_event(SAPP_EVENTTYPE_MOUSE_MOVE, SAPP_MOUSEBUTTON_MIDDLE, _sapp_macos_mod(event.modifierFlags)); + } +} - (void)mouseMoved:(NSEvent*)event { if (_sapp.mouse.locked) { _sapp.mouse.dx = [event deltaX]; -- cgit v1.2.3 From fcacc89864793f5cc571f23e909a6a246a8718a3 Mon Sep 17 00:00:00 2001 From: Andre Weissflog Date: Tue, 22 Sep 2020 18:45:06 +0200 Subject: sokol_app.h macos: don't send mouse enter/leave events while mouse button held down --- sokol_app.h | 18 ++++++++++++++++-- 1 file changed, 16 insertions(+), 2 deletions(-) diff --git a/sokol_app.h b/sokol_app.h index 4f331cb1..e7def8d7 100644 --- a/sokol_app.h +++ b/sokol_app.h @@ -1311,6 +1311,7 @@ inline int sapp_run(const sapp_desc& desc) { return sapp_run(&desc); } typedef struct { uint32_t flags_changed_store; + uint8_t mouse_buttons; NSWindow* window; NSTrackingArea* tracking_area; _sapp_macos_app_delegate* app_dlg; @@ -2841,31 +2842,44 @@ _SOKOL_PRIVATE void _sapp_macos_frame(void) { [super updateTrackingAreas]; } - (void)mouseEntered:(NSEvent*)event { - _sapp_macos_mouse_event(SAPP_EVENTTYPE_MOUSE_ENTER, SAPP_MOUSEBUTTON_INVALID, _sapp_macos_mod(event.modifierFlags)); + /* don't send mouse enter/leave while dragging (so that it behaves the same as + on Windows while SetCapture is active + */ + if (0 == _sapp.macos.mouse_buttons) { + _sapp_macos_mouse_event(SAPP_EVENTTYPE_MOUSE_ENTER, SAPP_MOUSEBUTTON_INVALID, _sapp_macos_mod(event.modifierFlags)); + } } - (void)mouseExited:(NSEvent*)event { - _sapp_macos_mouse_event(SAPP_EVENTTYPE_MOUSE_LEAVE, SAPP_MOUSEBUTTON_INVALID, _sapp_macos_mod(event.modifierFlags)); + if (0 == _sapp.macos.mouse_buttons) { + _sapp_macos_mouse_event(SAPP_EVENTTYPE_MOUSE_LEAVE, SAPP_MOUSEBUTTON_INVALID, _sapp_macos_mod(event.modifierFlags)); + } } - (void)mouseDown:(NSEvent*)event { _sapp_macos_mouse_event(SAPP_EVENTTYPE_MOUSE_DOWN, SAPP_MOUSEBUTTON_LEFT, _sapp_macos_mod(event.modifierFlags)); + _sapp.macos.mouse_buttons |= (1< Date: Tue, 22 Sep 2020 19:24:51 +0200 Subject: sokol_app.h linux: don't send mouse enter/leave events while buttons are pressed --- sokol_app.h | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/sokol_app.h b/sokol_app.h index e7def8d7..437ca993 100644 --- a/sokol_app.h +++ b/sokol_app.h @@ -1605,6 +1605,7 @@ typedef struct { } _sapp_xi_t; typedef struct { + uint8_t mouse_buttons; Display* display; int screen; Window root; @@ -8035,6 +8036,7 @@ _SOKOL_PRIVATE void _sapp_x11_process_event(XEvent* event) { const uint32_t mods = _sapp_x11_mod(event->xbutton.state); if (btn != SAPP_MOUSEBUTTON_INVALID) { _sapp_x11_mouse_event(SAPP_EVENTTYPE_MOUSE_DOWN, btn, mods); + _sapp.x11.mouse_buttons |= (1 << btn); } else { /* might be a scroll event */ @@ -8052,14 +8054,20 @@ _SOKOL_PRIVATE void _sapp_x11_process_event(XEvent* event) { const sapp_mousebutton btn = _sapp_x11_translate_button(event); if (btn != SAPP_MOUSEBUTTON_INVALID) { _sapp_x11_mouse_event(SAPP_EVENTTYPE_MOUSE_UP, btn, _sapp_x11_mod(event->xbutton.state)); + _sapp.x11.mouse_buttons &= ~(1 << btn); } } break; case EnterNotify: - _sapp_x11_mouse_event(SAPP_EVENTTYPE_MOUSE_ENTER, SAPP_MOUSEBUTTON_INVALID, _sapp_x11_mod(event->xcrossing.state)); + /* don't send enter/leave events while mouse button held down */ + if (0 == _sapp.x11.mouse_buttons) { + _sapp_x11_mouse_event(SAPP_EVENTTYPE_MOUSE_ENTER, SAPP_MOUSEBUTTON_INVALID, _sapp_x11_mod(event->xcrossing.state)); + } break; case LeaveNotify: - _sapp_x11_mouse_event(SAPP_EVENTTYPE_MOUSE_LEAVE, SAPP_MOUSEBUTTON_INVALID, _sapp_x11_mod(event->xcrossing.state)); + if (0 == _sapp.x11.mouse_buttons) { + _sapp_x11_mouse_event(SAPP_EVENTTYPE_MOUSE_LEAVE, SAPP_MOUSEBUTTON_INVALID, _sapp_x11_mod(event->xcrossing.state)); + } break; case MotionNotify: if (!_sapp.mouse.locked) { -- cgit v1.2.3