Merge branch 'blender-v4.0-release'

This commit is contained in:
Campbell Barton 2023-10-18 14:40:39 +11:00
commit df6cedeee1
2 changed files with 58 additions and 15 deletions

@ -1169,16 +1169,23 @@ static void libdecor_frame_handle_configure(libdecor_frame *frame,
GWL_WindowFrame *frame_pending = &static_cast<GWL_Window *>(data)->frame_pending; GWL_WindowFrame *frame_pending = &static_cast<GWL_Window *>(data)->frame_pending;
/* Set the size. */ /* Set the size. */
int size_next[2]; int size_decor[2]{
libdecor_frame_get_content_width(frame),
libdecor_frame_get_content_height(frame),
};
int size_next[2] = {0, 0};
bool has_size = false;
{ {
GWL_Window *win = static_cast<GWL_Window *>(data); GWL_Window *win = static_cast<GWL_Window *>(data);
const int scale = win->frame.buffer_scale; const int fractional_scale = win->frame.fractional_scale;
if (!libdecor_configuration_get_content_size( /* The size from LIBDECOR wont use the GHOST windows buffer size.
* so it's important to calculate the buffer size that would have been used
* if fractional scaling wasn't supported. */
const int scale = fractional_scale ? (fractional_scale / FRACTIONAL_DENOMINATOR) + 1 :
win->frame.buffer_scale;
const int scale_as_fractional = scale * FRACTIONAL_DENOMINATOR;
if (libdecor_configuration_get_content_size(
configuration, frame, &size_next[0], &size_next[1])) { configuration, frame, &size_next[0], &size_next[1])) {
size_next[0] = win->frame.size[0] / scale;
size_next[1] = win->frame.size[1] / scale;
}
if (win->frame.fractional_scale) { if (win->frame.fractional_scale) {
win->frame_pending.size[0] = gwl_window_fractional_to_viewport_round(win->frame, win->frame_pending.size[0] = gwl_window_fractional_to_viewport_round(win->frame,
size_next[0]); size_next[0]);
@ -1190,14 +1197,38 @@ static void libdecor_frame_handle_configure(libdecor_frame *frame,
frame_pending->size[1] = size_next[1] * scale; frame_pending->size[1] = size_next[1] * scale;
} }
/* Account for buffer rounding requirement, once fractional scaling is enabled
* the buffer scale will be 1, rounding is a requirement until then. */
gwl_round_int2_by(frame_pending->size, win->frame.buffer_scale);
has_size = true;
}
else {
/* The window decorations may be zero on startup. */
if (UNLIKELY(size_decor[0] == 0 || size_decor[1] == 0)) {
if (fractional_scale != 0 && (scale_as_fractional != fractional_scale)) {
/* Invert the fractional part: (1.25 -> 1.75), (2.75 -> 2.25), (1.5 -> 1.5).
* Needed to properly set the initial window size. */
const int scale_fractional_part_inv = scale_as_fractional -
(FRACTIONAL_DENOMINATOR -
(scale_as_fractional - fractional_scale));
size_decor[0] = ((win->frame.size[0] / scale_as_fractional) * scale_fractional_part_inv);
size_decor[1] = ((win->frame.size[1] / scale_as_fractional) * scale_fractional_part_inv);
}
else {
size_decor[0] = win->frame.size[0] / scale;
size_decor[1] = win->frame.size[1] / scale;
}
}
}
# ifdef USE_EVENT_BACKGROUND_THREAD # ifdef USE_EVENT_BACKGROUND_THREAD
/* NOTE(@ideasman42): when running from the event handling thread, /* NOTE(@ideasman42): when running from the event handling thread,
* don't apply the new window size back to LIBDECOR, otherwise the window content * don't apply the new window size back to LIBDECOR, otherwise the window content
* (which uses a deferred update) and the window get noticeably out of sync. * (which uses a deferred update) and the window get noticeably out of sync.
* Rely on the new `frame_pending->size` to resize the window later. */ * Rely on the new `frame_pending->size` to resize the window later. */
if (is_main_thread == false) { if (is_main_thread == false) {
size_next[0] = win->frame.size[0] / scale; has_size = false;
size_next[1] = win->frame.size[1] / scale;
} }
# endif # endif
} }
@ -1230,6 +1261,10 @@ static void libdecor_frame_handle_configure(libdecor_frame *frame,
{ {
GWL_Window *win = static_cast<GWL_Window *>(data); GWL_Window *win = static_cast<GWL_Window *>(data);
WGL_LibDecor_Window &decor = *win->libdecor; WGL_LibDecor_Window &decor = *win->libdecor;
if (has_size == false) {
size_next[0] = size_decor[0];
size_next[1] = size_decor[1];
}
libdecor_state *state = libdecor_state_new(UNPACK2(size_next)); libdecor_state *state = libdecor_state_new(UNPACK2(size_next));
libdecor_frame_commit(frame, state, configuration); libdecor_frame_commit(frame, state, configuration);
libdecor_state_free(state); libdecor_state_free(state);

@ -21,6 +21,8 @@ WAYLAND_DYNLOAD_FN(libdecor_configuration_get_window_state)
WAYLAND_DYNLOAD_FN(libdecor_decorate) WAYLAND_DYNLOAD_FN(libdecor_decorate)
WAYLAND_DYNLOAD_FN(libdecor_dispatch) WAYLAND_DYNLOAD_FN(libdecor_dispatch)
WAYLAND_DYNLOAD_FN(libdecor_frame_commit) WAYLAND_DYNLOAD_FN(libdecor_frame_commit)
WAYLAND_DYNLOAD_FN(libdecor_frame_get_content_height)
WAYLAND_DYNLOAD_FN(libdecor_frame_get_content_width)
WAYLAND_DYNLOAD_FN(libdecor_frame_get_xdg_toplevel) WAYLAND_DYNLOAD_FN(libdecor_frame_get_xdg_toplevel)
WAYLAND_DYNLOAD_FN(libdecor_frame_map) WAYLAND_DYNLOAD_FN(libdecor_frame_map)
WAYLAND_DYNLOAD_FN(libdecor_frame_set_app_id) WAYLAND_DYNLOAD_FN(libdecor_frame_set_app_id)
@ -76,6 +78,8 @@ struct WaylandDynload_Libdecor {
void WL_DYN_FN(libdecor_frame_commit)(struct libdecor_frame *frame, void WL_DYN_FN(libdecor_frame_commit)(struct libdecor_frame *frame,
struct libdecor_state *state, struct libdecor_state *state,
struct libdecor_configuration *configuration); struct libdecor_configuration *configuration);
int WL_DYN_FN(libdecor_frame_get_content_width)(struct libdecor_frame *frame);
int WL_DYN_FN(libdecor_frame_get_content_height)(struct libdecor_frame *frame);
struct xdg_toplevel *WL_DYN_FN(libdecor_frame_get_xdg_toplevel)(struct libdecor_frame *frame); struct xdg_toplevel *WL_DYN_FN(libdecor_frame_get_xdg_toplevel)(struct libdecor_frame *frame);
void WL_DYN_FN(libdecor_frame_map)(struct libdecor_frame *frame); void WL_DYN_FN(libdecor_frame_map)(struct libdecor_frame *frame);
void WL_DYN_FN(libdecor_frame_set_app_id)(struct libdecor_frame *frame, const char *app_id); void WL_DYN_FN(libdecor_frame_set_app_id)(struct libdecor_frame *frame, const char *app_id);
@ -112,6 +116,10 @@ struct WaylandDynload_Libdecor {
# define libdecor_dispatch(...) (*wayland_dynload_libdecor.libdecor_dispatch)(__VA_ARGS__) # define libdecor_dispatch(...) (*wayland_dynload_libdecor.libdecor_dispatch)(__VA_ARGS__)
# define libdecor_frame_commit(...) \ # define libdecor_frame_commit(...) \
(*wayland_dynload_libdecor.libdecor_frame_commit)(__VA_ARGS__) (*wayland_dynload_libdecor.libdecor_frame_commit)(__VA_ARGS__)
# define libdecor_frame_get_content_height(...) \
(*wayland_dynload_libdecor.libdecor_frame_get_content_height)(__VA_ARGS__)
# define libdecor_frame_get_content_width(...) \
(*wayland_dynload_libdecor.libdecor_frame_get_content_width)(__VA_ARGS__)
# define libdecor_frame_get_xdg_toplevel(...) \ # define libdecor_frame_get_xdg_toplevel(...) \
(*wayland_dynload_libdecor.libdecor_frame_get_xdg_toplevel)(__VA_ARGS__) (*wayland_dynload_libdecor.libdecor_frame_get_xdg_toplevel)(__VA_ARGS__)
# define libdecor_frame_map(...) (*wayland_dynload_libdecor.libdecor_frame_map)(__VA_ARGS__) # define libdecor_frame_map(...) (*wayland_dynload_libdecor.libdecor_frame_map)(__VA_ARGS__)