macOS: Render OS windows during windowDidResize for even smoother live resize rendering

This commit is contained in:
Kovid Goyal 2023-07-11 17:22:35 +05:30
parent e244d9da92
commit b00c2d644e
No known key found for this signature in database
GPG key ID: 06BC317B515ACE7C
7 changed files with 49 additions and 0 deletions

View file

@ -157,6 +157,7 @@ typedef struct _GLFWwindowNS
GLFWcocoarenderframefun renderFrameCallback;
// update cursor after switching desktops with Mission Control
bool delayed_cursor_update_requested;
GLFWcocoarenderframefun resizeCallback;
} _GLFWwindowNS;
typedef struct _GLFWDisplayLinkNS

View file

@ -646,6 +646,7 @@ - (void)windowDidResize:(NSNotification *)notification
window->ns.height = (int)contentRect.size.height;
_glfwInputWindowSize(window, (int)contentRect.size.width, (int)contentRect.size.height);
}
if (window->ns.resizeCallback) window->ns.resizeCallback((GLFWwindow*)window);
}
- (void)windowDidMove:(NSNotification *)notification
@ -2964,6 +2965,13 @@ GLFWAPI int glfwCocoaSetBackgroundBlur(GLFWwindow *w, int radius) {
return orig;
}
GLFWAPI GLFWcocoarenderframefun glfwCocoaSetWindowResizeCallback(GLFWwindow *w, GLFWcocoarenderframefun cb) {
_GLFWwindow* window = (_GLFWwindow*)w;
GLFWcocoarenderframefun current = window->ns.resizeCallback;
window->ns.resizeCallback = cb;
return current;
}
GLFWAPI void glfwCocoaSetWindowChrome(GLFWwindow *w, unsigned int color, bool use_system_color, unsigned int system_color, int background_blur, unsigned int hide_window_decorations, bool show_text_in_titlebar, int color_space, float background_opacity, bool resizable) { @autoreleasepool {
_GLFWwindow* window = (_GLFWwindow*)w;
const bool is_transparent = ![window->ns.object isOpaque];

View file

@ -248,6 +248,7 @@ def generate_wrappers(glfw_header: str) -> None:
GLFWapplicationwillfinishlaunchingfun glfwSetApplicationWillFinishLaunching(GLFWapplicationwillfinishlaunchingfun callback)
uint32_t glfwGetCocoaKeyEquivalent(uint32_t glfw_key, int glfw_mods, int* cocoa_mods)
void glfwCocoaRequestRenderFrame(GLFWwindow *w, GLFWcocoarenderframefun callback)
GLFWcocoarenderframefun glfwCocoaSetWindowResizeCallback(GLFWwindow *w, GLFWcocoarenderframefun callback)
int glfwCocoaSetBackgroundBlur(GLFWwindow *w, int blur_radius)
bool glfwSetX11WindowBlurred(GLFWwindow *w, bool enable_blur)
void* glfwGetX11Display(void)

View file

@ -841,6 +841,10 @@ render(monotonic_t now, bool input_read) {
for (size_t i = 0; i < global_state.num_os_windows; i++) {
OSWindow *w = global_state.os_windows + i;
#ifdef __APPLE__
// rendering is done in cocoa_os_window_resized()
if (w->live_resize.in_progress) continue;
#endif
if (!render_os_window(w, now, false, scan_for_animated_images)) {
// since we didn't scan the window for animations, force a rescan on next wakeup/render frame
if (scan_for_animated_images) global_state.check_for_active_animated_images = true;

3
kitty/glfw-wrapper.c generated
View file

@ -440,6 +440,9 @@ load_glfw(const char* path) {
*(void **) (&glfwCocoaRequestRenderFrame_impl) = dlsym(handle, "glfwCocoaRequestRenderFrame");
if (glfwCocoaRequestRenderFrame_impl == NULL) dlerror(); // clear error indicator
*(void **) (&glfwCocoaSetWindowResizeCallback_impl) = dlsym(handle, "glfwCocoaSetWindowResizeCallback");
if (glfwCocoaSetWindowResizeCallback_impl == NULL) dlerror(); // clear error indicator
*(void **) (&glfwCocoaSetBackgroundBlur_impl) = dlsym(handle, "glfwCocoaSetBackgroundBlur");
if (glfwCocoaSetBackgroundBlur_impl == NULL) dlerror(); // clear error indicator

4
kitty/glfw-wrapper.h generated
View file

@ -2217,6 +2217,10 @@ typedef void (*glfwCocoaRequestRenderFrame_func)(GLFWwindow*, GLFWcocoarenderfra
GFW_EXTERN glfwCocoaRequestRenderFrame_func glfwCocoaRequestRenderFrame_impl;
#define glfwCocoaRequestRenderFrame glfwCocoaRequestRenderFrame_impl
typedef GLFWcocoarenderframefun (*glfwCocoaSetWindowResizeCallback_func)(GLFWwindow*, GLFWcocoarenderframefun);
GFW_EXTERN glfwCocoaSetWindowResizeCallback_func glfwCocoaSetWindowResizeCallback_impl;
#define glfwCocoaSetWindowResizeCallback glfwCocoaSetWindowResizeCallback_impl
typedef int (*glfwCocoaSetBackgroundBlur_func)(GLFWwindow*, int);
GFW_EXTERN glfwCocoaSetBackgroundBlur_func glfwCocoaSetBackgroundBlur_impl;
#define glfwCocoaSetBackgroundBlur glfwCocoaSetBackgroundBlur_impl

View file

@ -289,11 +289,38 @@ window_iconify_callback(GLFWwindow *window, int iconified) {
global_state.callback_os_window = NULL;
}
#ifdef __APPLE__
static void
cocoa_out_of_sequence_render(OSWindow *window) {
make_os_window_context_current(window);
window->needs_render = true;
bool rendered = render_os_window(window, monotonic(), true, true);
if (!rendered) {
blank_os_window(window);
swap_window_buffers(window);
}
window->needs_render = true;
}
static void
cocoa_os_window_resized(GLFWwindow *w) {
if (!set_callback_window(w)) return;
cocoa_out_of_sequence_render(global_state.callback_os_window);
global_state.callback_os_window = NULL;
}
#endif
void
change_live_resize_state(OSWindow *w, bool in_progress) {
if (in_progress != w->live_resize.in_progress) {
w->live_resize.in_progress = in_progress;
w->live_resize.num_of_resize_events = 0;
apply_swap_interval(in_progress ? 0 : -1);
#ifdef __APPLE__
cocoa_out_of_sequence_render(w);
#endif
}
}
@ -1083,6 +1110,7 @@ create_os_window(PyObject UNUSED *self, PyObject *args, PyObject *kw) {
#ifdef __APPLE__
if (OPT(macos_option_as_alt)) glfwSetCocoaTextInputFilter(glfw_window, filter_option);
glfwSetCocoaToggleFullscreenIntercept(glfw_window, intercept_cocoa_fullscreen);
glfwCocoaSetWindowResizeCallback(glfw_window, cocoa_os_window_resized);
#endif
send_prerendered_sprites_for_window(w);
if (logo.pixels && logo.width && logo.height) glfwSetWindowIcon(glfw_window, 1, &logo);