Merge pull request #94706 from alvinhochun/window-set-transient-parent-on-create

Pass window exclusive and transient properties for subwindow creation
This commit is contained in:
Rémi Verschelde 2024-07-26 13:44:03 +02:00
commit 13c6c0cdb7
No known key found for this signature in database
GPG Key ID: C3336907360768E1
10 changed files with 44 additions and 25 deletions

View File

@ -1735,7 +1735,7 @@ Vector<DisplayServer::WindowID> DisplayServerX11::get_window_list() const {
return ret;
}
DisplayServer::WindowID DisplayServerX11::create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect) {
DisplayServer::WindowID DisplayServerX11::create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect, bool p_exclusive, WindowID p_transient_parent) {
_THREAD_SAFE_METHOD_
WindowID id = _create_window(p_mode, p_vsync_mode, p_flags, p_rect);
@ -1749,6 +1749,11 @@ DisplayServer::WindowID DisplayServerX11::create_sub_window(WindowMode p_mode, V
rendering_device->screen_create(id);
}
#endif
if (p_transient_parent != INVALID_WINDOW_ID) {
window_set_transient(id, p_transient_parent);
}
return id;
}

View File

@ -438,7 +438,7 @@ public:
virtual Vector<DisplayServer::WindowID> get_window_list() const override;
virtual WindowID create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect = Rect2i()) override;
virtual WindowID create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect = Rect2i(), bool p_exclusive = false, WindowID p_transient_parent = INVALID_WINDOW_ID) override;
virtual void show_window(WindowID p_id) override;
virtual void delete_sub_window(WindowID p_id) override;

View File

@ -326,7 +326,7 @@ public:
virtual Vector<int> get_window_list() const override;
virtual WindowID create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect = Rect2i()) override;
virtual WindowID create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect = Rect2i(), bool p_exclusive = false, WindowID p_transient_parent = INVALID_WINDOW_ID) override;
virtual void show_window(WindowID p_id) override;
virtual void delete_sub_window(WindowID p_id) override;

View File

@ -1714,7 +1714,7 @@ Vector<DisplayServer::WindowID> DisplayServerMacOS::get_window_list() const {
return ret;
}
DisplayServer::WindowID DisplayServerMacOS::create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect) {
DisplayServer::WindowID DisplayServerMacOS::create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect, bool p_exclusive, WindowID p_transient_parent) {
_THREAD_SAFE_METHOD_
WindowID id = _create_window(p_mode, p_vsync_mode, p_rect);
@ -1728,6 +1728,12 @@ DisplayServer::WindowID DisplayServerMacOS::create_sub_window(WindowMode p_mode,
rendering_device->screen_create(id);
}
#endif
window_set_exclusive(id, p_exclusive);
if (p_transient_parent != INVALID_WINDOW_ID) {
window_set_transient(id, p_transient_parent);
}
return id;
}

View File

@ -1306,10 +1306,10 @@ DisplayServer::WindowID DisplayServerWindows::get_window_at_screen_position(cons
return INVALID_WINDOW_ID;
}
DisplayServer::WindowID DisplayServerWindows::create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect) {
DisplayServer::WindowID DisplayServerWindows::create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect, bool p_exclusive, WindowID p_transient_parent) {
_THREAD_SAFE_METHOD_
WindowID window_id = _create_window(p_mode, p_vsync_mode, p_flags, p_rect);
WindowID window_id = _create_window(p_mode, p_vsync_mode, p_flags, p_rect, p_exclusive, p_transient_parent);
ERR_FAIL_COND_V_MSG(window_id == INVALID_WINDOW_ID, INVALID_WINDOW_ID, "Failed to create sub window.");
WindowData &wd = windows[window_id];
@ -5326,7 +5326,7 @@ void DisplayServerWindows::_update_tablet_ctx(const String &p_old_driver, const
}
}
DisplayServer::WindowID DisplayServerWindows::_create_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect) {
DisplayServer::WindowID DisplayServerWindows::_create_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect, bool p_exclusive, WindowID p_transient_parent) {
DWORD dwExStyle;
DWORD dwStyle;
@ -5376,6 +5376,18 @@ DisplayServer::WindowID DisplayServerWindows::_create_window(WindowMode p_mode,
WindowID id = window_id_counter;
{
WindowData *wd_transient_parent = nullptr;
HWND owner_hwnd = nullptr;
if (p_transient_parent != INVALID_WINDOW_ID && !windows.has(p_transient_parent)) {
ERR_PRINT("Condition \"!windows.has(p_transient_parent)\" is true.");
p_transient_parent = INVALID_WINDOW_ID;
} else {
wd_transient_parent = &windows[p_transient_parent];
if (p_exclusive) {
owner_hwnd = wd_transient_parent->hWnd;
}
}
WindowData &wd = windows[id];
wd.hWnd = CreateWindowExW(
@ -5386,7 +5398,7 @@ DisplayServer::WindowID DisplayServerWindows::_create_window(WindowMode p_mode,
WindowRect.top,
WindowRect.right - WindowRect.left,
WindowRect.bottom - WindowRect.top,
nullptr,
owner_hwnd,
nullptr,
hInstance,
// tunnel the WindowData we need to handle creation message
@ -5408,6 +5420,12 @@ DisplayServer::WindowID DisplayServerWindows::_create_window(WindowMode p_mode,
wd.pre_fs_valid = true;
}
wd.exclusive = p_exclusive;
if (wd_transient_parent) {
wd.transient_parent = p_transient_parent;
wd_transient_parent->transient_children.insert(id);
}
if (is_dark_mode_supported() && dark_title_available) {
BOOL value = is_dark_mode();
::DwmSetWindowAttribute(wd.hWnd, use_legacy_dark_mode_before_20H1 ? DWMWA_USE_IMMERSIVE_DARK_MODE_BEFORE_20H1 : DWMWA_USE_IMMERSIVE_DARK_MODE, &value, sizeof(value));
@ -6036,7 +6054,7 @@ DisplayServerWindows::DisplayServerWindows(const String &p_rendering_driver, Win
window_position = scr_rect.position + (scr_rect.size - p_resolution) / 2;
}
WindowID main_window = _create_window(p_mode, p_vsync_mode, p_flags, Rect2i(window_position, p_resolution));
WindowID main_window = _create_window(p_mode, p_vsync_mode, p_flags, Rect2i(window_position, p_resolution), false, INVALID_WINDOW_ID);
ERR_FAIL_COND_MSG(main_window == INVALID_WINDOW_ID, "Failed to create main window.");
joypad = new JoypadWindows(&windows[MAIN_WINDOW_ID].hWnd);

View File

@ -517,7 +517,7 @@ class DisplayServerWindows : public DisplayServer {
uint64_t time_since_popup = 0;
Ref<Image> icon;
WindowID _create_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect);
WindowID _create_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect, bool p_exclusive, WindowID p_transient_parent);
WindowID window_id_counter = MAIN_WINDOW_ID;
RBMap<WindowID, WindowData> windows;
@ -652,7 +652,7 @@ public:
virtual Vector<DisplayServer::WindowID> get_window_list() const override;
virtual WindowID create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect = Rect2i()) override;
virtual WindowID create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect = Rect2i(), bool p_exclusive = false, WindowID p_transient_parent = INVALID_WINDOW_ID) override;
virtual void show_window(WindowID p_window) override;
virtual void delete_sub_window(WindowID p_window) override;

View File

@ -631,7 +631,7 @@ void Window::_make_window() {
window_rect = Rect2i(DisplayServer::get_singleton()->screen_get_position(DisplayServer::SCREEN_WITH_KEYBOARD_FOCUS) + (DisplayServer::get_singleton()->screen_get_size(DisplayServer::SCREEN_WITH_KEYBOARD_FOCUS) - size) / 2, size);
}
window_id = DisplayServer::get_singleton()->create_sub_window(DisplayServer::WindowMode(mode), vsync_mode, f, window_rect);
window_id = DisplayServer::get_singleton()->create_sub_window(DisplayServer::WindowMode(mode), vsync_mode, f, window_rect, is_in_edited_scene_root() ? false : exclusive, transient_parent ? transient_parent->window_id : DisplayServer::INVALID_WINDOW_ID);
ERR_FAIL_COND(window_id == DisplayServer::INVALID_WINDOW_ID);
DisplayServer::get_singleton()->window_set_max_size(Size2i(), window_id);
DisplayServer::get_singleton()->window_set_min_size(Size2i(), window_id);
@ -639,18 +639,8 @@ void Window::_make_window() {
DisplayServer::get_singleton()->window_set_title(tr_title, window_id);
DisplayServer::get_singleton()->window_attach_instance_id(get_instance_id(), window_id);
if (is_in_edited_scene_root()) {
DisplayServer::get_singleton()->window_set_exclusive(window_id, false);
} else {
DisplayServer::get_singleton()->window_set_exclusive(window_id, exclusive);
}
_update_window_size();
if (transient_parent && transient_parent->window_id != DisplayServer::INVALID_WINDOW_ID) {
DisplayServer::get_singleton()->window_set_transient(window_id, transient_parent->window_id);
}
if (transient_parent) {
for (const Window *E : transient_children) {
if (E->window_id != DisplayServer::INVALID_WINDOW_ID) {

View File

@ -570,7 +570,7 @@ int DisplayServer::get_screen_from_rect(const Rect2 &p_rect) const {
return pos_screen;
}
DisplayServer::WindowID DisplayServer::create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect) {
DisplayServer::WindowID DisplayServer::create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect, bool p_exclusive, WindowID p_transient_parent) {
ERR_FAIL_V_MSG(INVALID_WINDOW_ID, "Sub-windows not supported by this display server.");
}

View File

@ -396,7 +396,7 @@ public:
WINDOW_FLAG_MOUSE_PASSTHROUGH_BIT = (1 << WINDOW_FLAG_MOUSE_PASSTHROUGH),
};
virtual WindowID create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect = Rect2i());
virtual WindowID create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect = Rect2i(), bool p_exclusive = false, WindowID p_transient_parent = INVALID_WINDOW_ID);
virtual void show_window(WindowID p_id);
virtual void delete_sub_window(WindowID p_id);

View File

@ -85,7 +85,7 @@ public:
Vector<DisplayServer::WindowID> get_window_list() const override { return Vector<DisplayServer::WindowID>(); }
WindowID create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect = Rect2i()) override { return 0; }
WindowID create_sub_window(WindowMode p_mode, VSyncMode p_vsync_mode, uint32_t p_flags, const Rect2i &p_rect = Rect2i(), bool p_exclusive = false, WindowID p_transient_parent = INVALID_WINDOW_ID) override { return 0; }
void show_window(WindowID p_id) override {}
void delete_sub_window(WindowID p_id) override {}