pyglet 2.1.13__py3-none-any.whl → 3.0.dev1__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- pyglet/__init__.py +67 -61
- pyglet/__init__.pyi +15 -8
- pyglet/app/__init__.py +22 -13
- pyglet/app/async_app.py +212 -0
- pyglet/app/base.py +2 -1
- pyglet/app/{xlib.py → linux.py} +3 -3
- pyglet/config/__init__.py +101 -0
- pyglet/config/gl/__init__.py +30 -0
- pyglet/config/gl/egl.py +120 -0
- pyglet/config/gl/macos.py +262 -0
- pyglet/config/gl/windows.py +267 -0
- pyglet/config/gl/x11.py +142 -0
- pyglet/customtypes.py +43 -2
- pyglet/display/__init__.py +8 -6
- pyglet/display/base.py +3 -63
- pyglet/display/cocoa.py +12 -17
- pyglet/display/emscripten.py +39 -0
- pyglet/display/headless.py +23 -30
- pyglet/display/wayland.py +157 -0
- pyglet/display/win32.py +5 -21
- pyglet/display/xlib.py +19 -27
- pyglet/display/xlib_vidmoderestore.py +2 -2
- pyglet/enums.py +183 -0
- pyglet/event.py +0 -1
- pyglet/experimental/geoshader_sprite.py +15 -13
- pyglet/experimental/hidraw.py +6 -15
- pyglet/experimental/multitexture_sprite.py +31 -19
- pyglet/experimental/particles.py +13 -35
- pyglet/font/__init__.py +251 -85
- pyglet/font/base.py +116 -61
- pyglet/font/dwrite/__init__.py +349 -204
- pyglet/font/dwrite/dwrite_lib.py +27 -5
- pyglet/font/fontconfig.py +14 -6
- pyglet/font/freetype.py +138 -87
- pyglet/font/freetype_lib.py +19 -0
- pyglet/font/group.py +179 -0
- pyglet/font/harfbuzz/__init__.py +3 -3
- pyglet/font/pyodide_js.py +310 -0
- pyglet/font/quartz.py +319 -126
- pyglet/font/ttf.py +45 -3
- pyglet/font/user.py +14 -19
- pyglet/font/win32.py +45 -21
- pyglet/graphics/__init__.py +8 -787
- pyglet/graphics/allocation.py +115 -1
- pyglet/graphics/api/__init__.py +77 -0
- pyglet/graphics/api/base.py +299 -0
- pyglet/graphics/api/gl/__init__.py +58 -0
- pyglet/graphics/api/gl/base.py +24 -0
- pyglet/graphics/{vertexbuffer.py → api/gl/buffer.py} +104 -159
- pyglet/graphics/api/gl/cocoa/context.py +76 -0
- pyglet/graphics/api/gl/context.py +391 -0
- pyglet/graphics/api/gl/default_shaders.py +0 -0
- pyglet/graphics/api/gl/draw.py +627 -0
- pyglet/graphics/api/gl/egl/__init__.py +0 -0
- pyglet/graphics/api/gl/egl/context.py +92 -0
- pyglet/graphics/api/gl/enums.py +76 -0
- pyglet/graphics/api/gl/framebuffer.py +315 -0
- pyglet/graphics/api/gl/gl.py +5463 -0
- pyglet/graphics/api/gl/gl_info.py +188 -0
- pyglet/graphics/api/gl/global_opengl.py +226 -0
- pyglet/{gl → graphics/api/gl}/lib.py +34 -18
- pyglet/graphics/api/gl/shader.py +1476 -0
- pyglet/graphics/api/gl/shapes.py +55 -0
- pyglet/graphics/api/gl/sprite.py +102 -0
- pyglet/graphics/api/gl/state.py +219 -0
- pyglet/graphics/api/gl/text.py +190 -0
- pyglet/graphics/api/gl/texture.py +1526 -0
- pyglet/graphics/{vertexarray.py → api/gl/vertexarray.py} +11 -13
- pyglet/graphics/api/gl/vertexdomain.py +751 -0
- pyglet/graphics/api/gl/win32/__init__.py +0 -0
- pyglet/graphics/api/gl/win32/context.py +108 -0
- pyglet/graphics/api/gl/win32/wgl_info.py +24 -0
- pyglet/graphics/api/gl/xlib/__init__.py +0 -0
- pyglet/graphics/api/gl/xlib/context.py +174 -0
- pyglet/{gl → graphics/api/gl/xlib}/glx_info.py +26 -31
- pyglet/graphics/api/gl1/__init__.py +0 -0
- pyglet/{gl → graphics/api/gl1}/gl_compat.py +3 -2
- pyglet/graphics/api/gl2/__init__.py +0 -0
- pyglet/graphics/api/gl2/buffer.py +320 -0
- pyglet/graphics/api/gl2/draw.py +600 -0
- pyglet/graphics/api/gl2/global_opengl.py +122 -0
- pyglet/graphics/api/gl2/shader.py +200 -0
- pyglet/graphics/api/gl2/shapes.py +51 -0
- pyglet/graphics/api/gl2/sprite.py +79 -0
- pyglet/graphics/api/gl2/text.py +175 -0
- pyglet/graphics/api/gl2/vertexdomain.py +364 -0
- pyglet/graphics/api/webgl/__init__.py +233 -0
- pyglet/graphics/api/webgl/buffer.py +302 -0
- pyglet/graphics/api/webgl/context.py +234 -0
- pyglet/graphics/api/webgl/draw.py +590 -0
- pyglet/graphics/api/webgl/enums.py +76 -0
- pyglet/graphics/api/webgl/framebuffer.py +360 -0
- pyglet/graphics/api/webgl/gl.py +1537 -0
- pyglet/graphics/api/webgl/gl_info.py +130 -0
- pyglet/graphics/api/webgl/shader.py +1346 -0
- pyglet/graphics/api/webgl/shapes.py +92 -0
- pyglet/graphics/api/webgl/sprite.py +102 -0
- pyglet/graphics/api/webgl/state.py +227 -0
- pyglet/graphics/api/webgl/text.py +187 -0
- pyglet/graphics/api/webgl/texture.py +1227 -0
- pyglet/graphics/api/webgl/vertexarray.py +54 -0
- pyglet/graphics/api/webgl/vertexdomain.py +616 -0
- pyglet/graphics/api/webgl/webgl_js.pyi +307 -0
- pyglet/{image → graphics}/atlas.py +33 -32
- pyglet/graphics/base.py +10 -0
- pyglet/graphics/buffer.py +245 -0
- pyglet/graphics/draw.py +578 -0
- pyglet/graphics/framebuffer.py +26 -0
- pyglet/graphics/instance.py +178 -69
- pyglet/graphics/shader.py +267 -1553
- pyglet/graphics/state.py +83 -0
- pyglet/graphics/texture.py +703 -0
- pyglet/graphics/vertexdomain.py +695 -538
- pyglet/gui/ninepatch.py +10 -10
- pyglet/gui/widgets.py +120 -10
- pyglet/image/__init__.py +20 -1973
- pyglet/image/animation.py +12 -12
- pyglet/image/base.py +730 -0
- pyglet/image/codecs/__init__.py +9 -0
- pyglet/image/codecs/bmp.py +53 -30
- pyglet/image/codecs/dds.py +53 -31
- pyglet/image/codecs/gdiplus.py +38 -14
- pyglet/image/codecs/gdkpixbuf2.py +0 -2
- pyglet/image/codecs/js_image.py +99 -0
- pyglet/image/codecs/ktx2.py +161 -0
- pyglet/image/codecs/pil.py +1 -1
- pyglet/image/codecs/png.py +1 -1
- pyglet/image/codecs/wic.py +11 -2
- pyglet/info.py +26 -24
- pyglet/input/__init__.py +8 -0
- pyglet/input/base.py +163 -105
- pyglet/input/controller.py +13 -19
- pyglet/input/controller_db.py +39 -24
- pyglet/input/emscripten/__init__.py +18 -0
- pyglet/input/emscripten/gamepad_js.py +397 -0
- pyglet/input/linux/__init__.py +11 -5
- pyglet/input/linux/evdev.py +10 -11
- pyglet/input/linux/x11_xinput.py +2 -2
- pyglet/input/linux/x11_xinput_tablet.py +1 -1
- pyglet/input/macos/__init__.py +7 -2
- pyglet/input/macos/darwin_gc.py +559 -0
- pyglet/input/win32/__init__.py +1 -1
- pyglet/input/win32/directinput.py +34 -29
- pyglet/input/win32/xinput.py +11 -61
- pyglet/lib.py +3 -3
- pyglet/libs/__init__.py +1 -1
- pyglet/{gl → libs/darwin}/agl.py +1 -1
- pyglet/libs/darwin/cocoapy/__init__.py +2 -2
- pyglet/libs/darwin/cocoapy/cocoahelpers.py +181 -0
- pyglet/libs/darwin/cocoapy/cocoalibs.py +31 -0
- pyglet/libs/darwin/cocoapy/cocoatypes.py +27 -0
- pyglet/libs/darwin/cocoapy/runtime.py +81 -45
- pyglet/libs/darwin/coreaudio.py +4 -4
- pyglet/{gl → libs/darwin}/lib_agl.py +9 -8
- pyglet/libs/darwin/quartzkey.py +1 -3
- pyglet/libs/egl/__init__.py +2 -0
- pyglet/libs/egl/egl_lib.py +576 -0
- pyglet/libs/egl/eglext.py +51 -5
- pyglet/libs/linux/__init__.py +0 -0
- pyglet/libs/linux/egl/__init__.py +0 -0
- pyglet/libs/linux/egl/eglext.py +22 -0
- pyglet/libs/linux/glx/__init__.py +0 -0
- pyglet/{gl → libs/linux/glx}/glx.py +13 -14
- pyglet/{gl → libs/linux/glx}/glxext_arb.py +408 -192
- pyglet/{gl → libs/linux/glx}/glxext_mesa.py +1 -1
- pyglet/{gl → libs/linux/glx}/glxext_nv.py +345 -164
- pyglet/{gl → libs/linux/glx}/lib_glx.py +3 -2
- pyglet/libs/linux/wayland/__init__.py +0 -0
- pyglet/libs/linux/wayland/client.py +1068 -0
- pyglet/libs/linux/wayland/lib_wayland.py +207 -0
- pyglet/libs/linux/wayland/wayland_egl.py +38 -0
- pyglet/libs/{wayland → linux/wayland}/xkbcommon.py +26 -0
- pyglet/libs/{x11 → linux/x11}/xf86vmode.py +4 -4
- pyglet/libs/{x11 → linux/x11}/xinerama.py +2 -2
- pyglet/libs/{x11 → linux/x11}/xinput.py +10 -10
- pyglet/libs/linux/x11/xrandr.py +0 -0
- pyglet/libs/{x11 → linux/x11}/xrender.py +1 -1
- pyglet/libs/shared/__init__.py +0 -0
- pyglet/libs/shared/spirv/__init__.py +0 -0
- pyglet/libs/shared/spirv/lib_shaderc.py +85 -0
- pyglet/libs/shared/spirv/lib_spirv_cross.py +126 -0
- pyglet/libs/win32/__init__.py +28 -8
- pyglet/libs/win32/constants.py +59 -48
- pyglet/libs/win32/context_managers.py +20 -3
- pyglet/libs/win32/dinput.py +105 -88
- pyglet/{gl → libs/win32}/lib_wgl.py +52 -26
- pyglet/libs/win32/types.py +58 -23
- pyglet/{gl → libs/win32}/wgl.py +32 -25
- pyglet/{gl → libs/win32}/wglext_arb.py +364 -2
- pyglet/media/__init__.py +9 -10
- pyglet/media/codecs/__init__.py +12 -1
- pyglet/media/codecs/base.py +99 -96
- pyglet/media/codecs/ffmpeg.py +2 -2
- pyglet/media/codecs/ffmpeg_lib/libavformat.py +3 -8
- pyglet/media/codecs/webaudio_pyodide.py +111 -0
- pyglet/media/drivers/__init__.py +9 -4
- pyglet/media/drivers/base.py +4 -4
- pyglet/media/drivers/openal/__init__.py +1 -1
- pyglet/media/drivers/openal/adaptation.py +3 -3
- pyglet/media/drivers/pulse/__init__.py +1 -1
- pyglet/media/drivers/pulse/adaptation.py +3 -3
- pyglet/media/drivers/pyodide_js/__init__.py +8 -0
- pyglet/media/drivers/pyodide_js/adaptation.py +288 -0
- pyglet/media/drivers/xaudio2/adaptation.py +3 -3
- pyglet/media/player.py +276 -193
- pyglet/media/player_worker_thread.py +1 -1
- pyglet/model/__init__.py +39 -29
- pyglet/model/codecs/base.py +4 -4
- pyglet/model/codecs/gltf.py +3 -3
- pyglet/model/codecs/obj.py +71 -43
- pyglet/resource.py +129 -78
- pyglet/shapes.py +154 -194
- pyglet/sprite.py +47 -164
- pyglet/text/__init__.py +44 -54
- pyglet/text/caret.py +12 -7
- pyglet/text/document.py +19 -17
- pyglet/text/formats/html.py +2 -2
- pyglet/text/formats/structured.py +10 -40
- pyglet/text/layout/__init__.py +20 -13
- pyglet/text/layout/base.py +176 -287
- pyglet/text/layout/incremental.py +9 -10
- pyglet/text/layout/scrolling.py +7 -95
- pyglet/window/__init__.py +183 -172
- pyglet/window/cocoa/__init__.py +62 -51
- pyglet/window/cocoa/pyglet_delegate.py +2 -25
- pyglet/window/cocoa/pyglet_view.py +9 -8
- pyglet/window/dialog/__init__.py +184 -0
- pyglet/window/dialog/base.py +99 -0
- pyglet/window/dialog/darwin.py +121 -0
- pyglet/window/dialog/linux.py +72 -0
- pyglet/window/dialog/windows.py +194 -0
- pyglet/window/emscripten/__init__.py +779 -0
- pyglet/window/headless/__init__.py +44 -28
- pyglet/window/key.py +2 -0
- pyglet/window/mouse.py +2 -2
- pyglet/window/wayland/__init__.py +377 -0
- pyglet/window/win32/__init__.py +101 -46
- pyglet/window/xlib/__init__.py +104 -66
- {pyglet-2.1.13.dist-info → pyglet-3.0.dev1.dist-info}/METADATA +2 -3
- pyglet-3.0.dev1.dist-info/RECORD +322 -0
- {pyglet-2.1.13.dist-info → pyglet-3.0.dev1.dist-info}/WHEEL +1 -1
- pyglet/gl/__init__.py +0 -208
- pyglet/gl/base.py +0 -499
- pyglet/gl/cocoa.py +0 -309
- pyglet/gl/gl.py +0 -4625
- pyglet/gl/gl.pyi +0 -2320
- pyglet/gl/gl_compat.pyi +0 -3097
- pyglet/gl/gl_info.py +0 -190
- pyglet/gl/headless.py +0 -166
- pyglet/gl/wgl_info.py +0 -36
- pyglet/gl/wglext_nv.py +0 -1096
- pyglet/gl/win32.py +0 -268
- pyglet/gl/xlib.py +0 -295
- pyglet/image/buffer.py +0 -274
- pyglet/image/codecs/s3tc.py +0 -354
- pyglet/libs/x11/xrandr.py +0 -166
- pyglet-2.1.13.dist-info/RECORD +0 -234
- /pyglet/{libs/wayland → graphics/api/gl/cocoa}/__init__.py +0 -0
- /pyglet/libs/{egl → linux/egl}/egl.py +0 -0
- /pyglet/libs/{egl → linux/egl}/lib.py +0 -0
- /pyglet/libs/{ioctl.py → linux/ioctl.py} +0 -0
- /pyglet/libs/{wayland → linux/wayland}/gbm.py +0 -0
- /pyglet/libs/{x11 → linux/x11}/__init__.py +0 -0
- /pyglet/libs/{x11 → linux/x11}/cursorfont.py +0 -0
- /pyglet/libs/{x11 → linux/x11}/xlib.py +0 -0
- /pyglet/libs/{x11 → linux/x11}/xsync.py +0 -0
- {pyglet-2.1.13.dist-info/licenses → pyglet-3.0.dev1.dist-info}/LICENSE +0 -0
pyglet/window/win32/__init__.py
CHANGED
|
@@ -2,7 +2,7 @@ from __future__ import annotations
|
|
|
2
2
|
|
|
3
3
|
import sys
|
|
4
4
|
import unicodedata
|
|
5
|
-
from ctypes.wintypes import DWORD, HICON, HWND, MSG, POINT, RECT, SIZE, UINT
|
|
5
|
+
from ctypes.wintypes import DWORD, HICON, HWND, MSG, POINT, RECT, SIZE, UINT, BOOL, HKEY, LPBYTE
|
|
6
6
|
from functools import lru_cache
|
|
7
7
|
from typing import Callable, Sequence
|
|
8
8
|
|
|
@@ -38,11 +38,10 @@ from ctypes import (
|
|
|
38
38
|
create_unicode_buffer,
|
|
39
39
|
memmove,
|
|
40
40
|
sizeof,
|
|
41
|
-
wstring_at,
|
|
41
|
+
wstring_at, c_ubyte,
|
|
42
42
|
)
|
|
43
43
|
|
|
44
44
|
import pyglet
|
|
45
|
-
from pyglet.display.win32 import Win32Canvas
|
|
46
45
|
from pyglet.event import EventDispatcher
|
|
47
46
|
from pyglet.libs.win32 import (
|
|
48
47
|
BITMAPV5HEADER,
|
|
@@ -56,6 +55,7 @@ from pyglet.libs.win32 import (
|
|
|
56
55
|
_kernel32,
|
|
57
56
|
_shell32,
|
|
58
57
|
_user32,
|
|
58
|
+
_advapi32,
|
|
59
59
|
)
|
|
60
60
|
from pyglet.window import (
|
|
61
61
|
BaseWindow,
|
|
@@ -91,7 +91,7 @@ _motion_map: dict[tuple[int, bool], int] = {
|
|
|
91
91
|
|
|
92
92
|
|
|
93
93
|
class Win32MouseCursor(MouseCursor):
|
|
94
|
-
|
|
94
|
+
api_drawable: bool = False
|
|
95
95
|
hw_drawable: bool = True
|
|
96
96
|
|
|
97
97
|
def __init__(self, cursor: HCURSOR) -> None:
|
|
@@ -106,16 +106,6 @@ Win32EventHandler = _PlatformEventHandler
|
|
|
106
106
|
ViewEventHandler = _ViewEventHandler
|
|
107
107
|
|
|
108
108
|
|
|
109
|
-
# Some events should not be queued, especially those with pointers or structures.
|
|
110
|
-
# Data is only guaranteed to be available for the duration of the initial function call.
|
|
111
|
-
_priority_events = [
|
|
112
|
-
constants.WM_GETMINMAXINFO,
|
|
113
|
-
constants.WM_GETDPISCALEDSIZE,
|
|
114
|
-
constants.WM_DPICHANGED,
|
|
115
|
-
constants.WM_INPUT,
|
|
116
|
-
]
|
|
117
|
-
|
|
118
|
-
|
|
119
109
|
class Win32Window(BaseWindow):
|
|
120
110
|
_window_class = None
|
|
121
111
|
_hwnd = None
|
|
@@ -203,13 +193,11 @@ class Win32Window(BaseWindow):
|
|
|
203
193
|
width = self.screen.width
|
|
204
194
|
height = self.screen.height
|
|
205
195
|
else:
|
|
206
|
-
if pyglet.options.dpi_scaling
|
|
196
|
+
if pyglet.options.dpi_scaling == "stretch":
|
|
207
197
|
w, h = self.get_requested_size()
|
|
208
198
|
self._width = int(w * self.scale)
|
|
209
199
|
self._height = int(h * self.scale)
|
|
210
|
-
|
|
211
|
-
if pyglet.options.dpi_scaling == "stretch":
|
|
212
|
-
self._mouse_scale = self.scale
|
|
200
|
+
self._mouse_scale = self.scale
|
|
213
201
|
|
|
214
202
|
width, height = \
|
|
215
203
|
self._client_to_window_size(self._width, self._height, self._dpi)
|
|
@@ -267,14 +255,31 @@ class Win32Window(BaseWindow):
|
|
|
267
255
|
self._view_window_class.lpszClassName,
|
|
268
256
|
'',
|
|
269
257
|
constants.WS_CHILD | constants.WS_VISIBLE,
|
|
270
|
-
0,
|
|
258
|
+
0,
|
|
259
|
+
0,
|
|
260
|
+
0,
|
|
261
|
+
0,
|
|
271
262
|
self._hwnd,
|
|
272
263
|
0,
|
|
273
264
|
self._view_window_class.hInstance,
|
|
274
|
-
0
|
|
265
|
+
0,
|
|
266
|
+
)
|
|
275
267
|
|
|
276
268
|
self._dc = _user32.GetDC(self._view_hwnd)
|
|
277
269
|
|
|
270
|
+
if not self._fullscreen and constants.WINDOWS_11_21H2_OR_GREATER:
|
|
271
|
+
self._update_light_mode(_ShouldSystemUseLightMode())
|
|
272
|
+
|
|
273
|
+
# Context must be created after window is created.
|
|
274
|
+
if pyglet.options.backend and not self._shadow:
|
|
275
|
+
if "gl" in pyglet.options.backend and not self._wgl_context:
|
|
276
|
+
self._assign_config()
|
|
277
|
+
self.context.attach(self)
|
|
278
|
+
self._wgl_context = self.context._context # noqa: SLF001
|
|
279
|
+
else:
|
|
280
|
+
self._assign_config()
|
|
281
|
+
self.context.attach(self)
|
|
282
|
+
|
|
278
283
|
# Only allow files being dropped if specified.
|
|
279
284
|
if self._file_drops:
|
|
280
285
|
# Allows UAC to not block the drop files request if low permissions. All 3 must be set.
|
|
@@ -323,16 +328,11 @@ class Win32Window(BaseWindow):
|
|
|
323
328
|
|
|
324
329
|
self._update_view_location(self._width, self._height)
|
|
325
330
|
|
|
326
|
-
# Context must be created after window is created.
|
|
327
|
-
if not self._wgl_context:
|
|
328
|
-
self.canvas = Win32Canvas(self.display, self._view_hwnd, self._dc)
|
|
329
|
-
self.context.attach(self.canvas)
|
|
330
|
-
self._wgl_context = self.context._context # noqa: SLF001
|
|
331
|
-
|
|
332
|
-
self.switch_to()
|
|
333
|
-
|
|
334
331
|
self.set_caption(self._caption)
|
|
335
|
-
|
|
332
|
+
|
|
333
|
+
if pyglet.options.backend and not self._shadow:
|
|
334
|
+
self.switch_to()
|
|
335
|
+
self.set_vsync(self._vsync)
|
|
336
336
|
|
|
337
337
|
if self._visible:
|
|
338
338
|
self.set_visible()
|
|
@@ -340,6 +340,10 @@ class Win32Window(BaseWindow):
|
|
|
340
340
|
self.dispatch_event('_on_internal_resize', self._width, self._height)
|
|
341
341
|
self.dispatch_event('on_expose')
|
|
342
342
|
|
|
343
|
+
@property
|
|
344
|
+
def dc(self):
|
|
345
|
+
return self._dc
|
|
346
|
+
|
|
343
347
|
def _update_view_location(self, width: int, height: int) -> None:
|
|
344
348
|
if self._fullscreen:
|
|
345
349
|
x = (self.screen.width - width) // 2
|
|
@@ -354,7 +358,7 @@ class Win32Window(BaseWindow):
|
|
|
354
358
|
super().close()
|
|
355
359
|
return
|
|
356
360
|
|
|
357
|
-
self.
|
|
361
|
+
self.set_mouse_cursor_platform_visible(True)
|
|
358
362
|
|
|
359
363
|
_user32.DestroyWindow(self._hwnd)
|
|
360
364
|
_user32.UnregisterClassW(self._view_window_class.lpszClassName, 0)
|
|
@@ -382,8 +386,8 @@ class Win32Window(BaseWindow):
|
|
|
382
386
|
return bool(self._interval)
|
|
383
387
|
|
|
384
388
|
def set_vsync(self, vsync: bool) -> None:
|
|
385
|
-
if pyglet.options
|
|
386
|
-
vsync = pyglet.options
|
|
389
|
+
if pyglet.options.vsync is not None:
|
|
390
|
+
vsync = pyglet.options.vsync
|
|
387
391
|
|
|
388
392
|
self._interval = vsync
|
|
389
393
|
|
|
@@ -414,7 +418,8 @@ class Win32Window(BaseWindow):
|
|
|
414
418
|
if not self._fullscreen and not self._always_dwm and self._dwm_composition_enabled() and self._interval:
|
|
415
419
|
_dwmapi.DwmFlush()
|
|
416
420
|
|
|
417
|
-
self.
|
|
421
|
+
if self._context:
|
|
422
|
+
self._context.flip()
|
|
418
423
|
|
|
419
424
|
def set_mouse_passthrough(self, state: bool) -> None:
|
|
420
425
|
color_ref = COLORREF()
|
|
@@ -437,6 +442,8 @@ class Win32Window(BaseWindow):
|
|
|
437
442
|
if state:
|
|
438
443
|
_user32.SetLayeredWindowAttributes(self._hwnd, color_ref.value, alpha.value, flags.value)
|
|
439
444
|
|
|
445
|
+
|
|
446
|
+
|
|
440
447
|
def set_location(self, x: int, y: int) -> None:
|
|
441
448
|
x, y = self._client_to_window_pos(x, y)
|
|
442
449
|
_user32.SetWindowPos(self._hwnd, 0, x, y, 0, 0,
|
|
@@ -450,7 +457,7 @@ class Win32Window(BaseWindow):
|
|
|
450
457
|
return point.x, point.y
|
|
451
458
|
|
|
452
459
|
def set_size(self, width: int, height: int) -> None:
|
|
453
|
-
if pyglet.options.dpi_scaling
|
|
460
|
+
if pyglet.options.dpi_scaling == "stretch":
|
|
454
461
|
width = int(width * self.scale)
|
|
455
462
|
height = int(height * self.scale)
|
|
456
463
|
|
|
@@ -481,7 +488,7 @@ class Win32Window(BaseWindow):
|
|
|
481
488
|
_user32.ShowWindow(self._hwnd, constants.SW_HIDE)
|
|
482
489
|
self.dispatch_event('on_hide')
|
|
483
490
|
self._visible = visible
|
|
484
|
-
self.
|
|
491
|
+
self.set_mouse_cursor_platform_visible()
|
|
485
492
|
|
|
486
493
|
def minimize(self) -> None:
|
|
487
494
|
_user32.ShowWindow(self._hwnd, constants.SW_MINIMIZE)
|
|
@@ -500,11 +507,11 @@ class Win32Window(BaseWindow):
|
|
|
500
507
|
self._caption = caption
|
|
501
508
|
_user32.SetWindowTextW(self._hwnd, c_wchar_p(caption))
|
|
502
509
|
|
|
503
|
-
def
|
|
510
|
+
def set_mouse_cursor_platform_visible(self, platform_visible: bool | None = None) -> None:
|
|
504
511
|
if platform_visible is None:
|
|
505
512
|
platform_visible = (self._mouse_visible and
|
|
506
513
|
not self._exclusive_mouse and
|
|
507
|
-
(not self._mouse_cursor.
|
|
514
|
+
(not self._mouse_cursor.api_drawable or self._mouse_cursor.hw_drawable)) or \
|
|
508
515
|
(not self._mouse_in_window or
|
|
509
516
|
not self._has_focus)
|
|
510
517
|
|
|
@@ -588,7 +595,7 @@ class Win32Window(BaseWindow):
|
|
|
588
595
|
|
|
589
596
|
self._exclusive_mouse = exclusive
|
|
590
597
|
self._exclusive_mouse_focus = self._has_focus
|
|
591
|
-
self.
|
|
598
|
+
self.set_mouse_cursor_platform_visible(not exclusive)
|
|
592
599
|
|
|
593
600
|
def set_mouse_position(self, x: int, y: int, absolute: bool = False) -> None:
|
|
594
601
|
if not absolute:
|
|
@@ -685,7 +692,7 @@ class Win32Window(BaseWindow):
|
|
|
685
692
|
_user32.ReleaseDC(None, hdc)
|
|
686
693
|
|
|
687
694
|
img = img.get_image_data()
|
|
688
|
-
data = img.
|
|
695
|
+
data = img.get_bytes(fmt, pitch)
|
|
689
696
|
memmove(dataptr, data, len(data))
|
|
690
697
|
|
|
691
698
|
mask = _gdi32.CreateBitmap(img.width, img.height, 1, 1, None)
|
|
@@ -734,7 +741,7 @@ class Win32Window(BaseWindow):
|
|
|
734
741
|
_user32.ReleaseDC(None, hdc)
|
|
735
742
|
|
|
736
743
|
image = image.get_image_data()
|
|
737
|
-
data = image.
|
|
744
|
+
data = image.get_bytes(fmt, pitch)
|
|
738
745
|
memmove(dataptr, data, len(data))
|
|
739
746
|
|
|
740
747
|
mask = _gdi32.CreateBitmap(image.width, image.height, 1, 1, None)
|
|
@@ -867,7 +874,7 @@ class Win32Window(BaseWindow):
|
|
|
867
874
|
event_handler = event_handlers.get(msg)
|
|
868
875
|
result = None
|
|
869
876
|
if event_handler:
|
|
870
|
-
if self._allow_dispatch_event or not self._enable_event_queue
|
|
877
|
+
if self._allow_dispatch_event or not self._enable_event_queue:
|
|
871
878
|
result = event_handler(msg, wParam, lParam)
|
|
872
879
|
else:
|
|
873
880
|
result = 0
|
|
@@ -1070,7 +1077,7 @@ class Win32Window(BaseWindow):
|
|
|
1070
1077
|
# to determine when to recreate the tracking structure after
|
|
1071
1078
|
# re-entering (to track the next WM_MOUSELEAVE).
|
|
1072
1079
|
self._mouse_in_window = True
|
|
1073
|
-
self.
|
|
1080
|
+
self.set_mouse_cursor_platform_visible()
|
|
1074
1081
|
self.dispatch_event('on_mouse_enter', x / self._mouse_scale, y / self._mouse_scale)
|
|
1075
1082
|
self._tracking = True
|
|
1076
1083
|
track = TRACKMOUSEEVENT()
|
|
@@ -1119,7 +1126,7 @@ class Win32Window(BaseWindow):
|
|
|
1119
1126
|
y = self._height - point.y
|
|
1120
1127
|
self._tracking = False
|
|
1121
1128
|
self._mouse_in_window = False
|
|
1122
|
-
self.
|
|
1129
|
+
self.set_mouse_cursor_platform_visible()
|
|
1123
1130
|
self.dispatch_event('on_mouse_leave', x / self._mouse_scale, y / self._mouse_scale)
|
|
1124
1131
|
return 0
|
|
1125
1132
|
|
|
@@ -1382,7 +1389,7 @@ class Win32Window(BaseWindow):
|
|
|
1382
1389
|
|
|
1383
1390
|
@Win32EventHandler(constants.WM_GETDPISCALEDSIZE)
|
|
1384
1391
|
def _event_dpi_scaled_size(self, msg: int, wParam: int, lParam: int) -> int | None:
|
|
1385
|
-
if pyglet.options.dpi_scaling
|
|
1392
|
+
if pyglet.options.dpi_scaling == "stretch":
|
|
1386
1393
|
return None
|
|
1387
1394
|
|
|
1388
1395
|
size = cast(lParam, POINTER(SIZE)).contents
|
|
@@ -1416,7 +1423,7 @@ class Win32Window(BaseWindow):
|
|
|
1416
1423
|
self._dpi = x_dpi
|
|
1417
1424
|
|
|
1418
1425
|
if not self._fullscreen and \
|
|
1419
|
-
(pyglet.options.dpi_scaling != "
|
|
1426
|
+
(pyglet.options.dpi_scaling != "stretch" or constants.WINDOWS_10_CREATORS_UPDATE_OR_GREATER):
|
|
1420
1427
|
suggested_rect = cast(lParam, POINTER(RECT)).contents
|
|
1421
1428
|
|
|
1422
1429
|
x = suggested_rect.left
|
|
@@ -1434,6 +1441,54 @@ class Win32Window(BaseWindow):
|
|
|
1434
1441
|
self.dispatch_event('_on_internal_scale', scale, x_dpi)
|
|
1435
1442
|
return 1
|
|
1436
1443
|
|
|
1437
|
-
|
|
1444
|
+
@Win32EventHandler(constants.WM_SETTINGCHANGE)
|
|
1445
|
+
def _event_setting_change(self, msg: int, wParam: int, lParam: int) -> int:
|
|
1446
|
+
if wParam == 0 and lParam != 0 and constants.WINDOWS_11_21H2_OR_GREATER:
|
|
1447
|
+
ptr = cast(lParam, c_wchar_p)
|
|
1448
|
+
if ptr.value == 'ImmersiveColorSet':
|
|
1449
|
+
self._update_light_mode(_ShouldSystemUseLightMode())
|
|
1450
|
+
|
|
1451
|
+
def _update_light_mode(self, is_light_mode: bool) -> None:
|
|
1452
|
+
value = BOOL(not is_light_mode)
|
|
1453
|
+
|
|
1454
|
+
_dwmapi.DwmSetWindowAttribute(self._hwnd, constants.DWMWA_USE_IMMERSIVE_DARK_MODE, byref(value), sizeof(value))
|
|
1455
|
+
|
|
1456
|
+
def _ShouldSystemUseLightMode() -> bool:
|
|
1457
|
+
"""With Windows 11 there is no stable API to get the current light mode.
|
|
1458
|
+
|
|
1459
|
+
uxtheme.dll does have hidden functions that seemingly work. However, there are many reports it's not stable across
|
|
1460
|
+
versions. The functions (138, which should be `ShouldAppsUseDarkMode`) are also not publicly exposed.
|
|
1461
|
+
|
|
1462
|
+
This was documented over 4 years ago here: https://github.com/microsoft/WindowsAppSDK/issues/41
|
|
1463
|
+
|
|
1464
|
+
With no solution from Microsoft, we have to rely on checking the registry key associated with this.
|
|
1465
|
+
"""
|
|
1466
|
+
subkey = r"Software\Microsoft\Windows\CurrentVersion\Themes\Personalize"
|
|
1467
|
+
value_name = "AppsUseLightTheme"
|
|
1468
|
+
hkey = HKEY()
|
|
1469
|
+
|
|
1470
|
+
if _advapi32.RegOpenKeyExW(constants.HKEY_CURRENT_USER, subkey, 0, constants.KEY_READ, byref(hkey)) != 0:
|
|
1471
|
+
return True
|
|
1472
|
+
|
|
1473
|
+
data_type = DWORD()
|
|
1474
|
+
data_value = (c_ubyte * 4)() # DWORD = 4 bytes
|
|
1475
|
+
data_size = DWORD(sizeof(data_value))
|
|
1476
|
+
|
|
1477
|
+
try:
|
|
1478
|
+
result = _advapi32.RegQueryValueExW(
|
|
1479
|
+
hkey,
|
|
1480
|
+
value_name,
|
|
1481
|
+
None,
|
|
1482
|
+
byref(data_type),
|
|
1483
|
+
cast(data_value, LPBYTE),
|
|
1484
|
+
byref(data_size),
|
|
1485
|
+
)
|
|
1486
|
+
if result == 0 and data_type.value == constants.REG_DWORD:
|
|
1487
|
+
value = int.from_bytes(bytes(data_value), "little")
|
|
1488
|
+
return bool(value)
|
|
1489
|
+
finally:
|
|
1490
|
+
_advapi32.RegCloseKey(hkey)
|
|
1491
|
+
|
|
1492
|
+
return True
|
|
1438
1493
|
|
|
1439
1494
|
__all__ = ['Win32EventHandler', 'Win32Window']
|