Fix popupwindow.close() not working for the interpreter when called from other component

The instance passed to close_popup() was not the same as the one passed
to show_popup(), when called from another component. Fix this by
determining the instance in BuiltinFunction::ClosePopupWindow the same
way as in BuiltinFunction::ShowPopupWindow.

This issue was covered by popup_window_close.slint's JS test, but it was
commented out because we used to run the Node.js tests on Linux with Qt,
for which the popup testing doesn't work the same way in terms of
synthetic event delivery.

We decided to change that, also in light of the nodejs binaries we
upload to the NPM registry also being built without Qt support anyway.

This permits running additional popup window tests, providing test
coverage for the interpreter, some of which needed light syntax fixes.

Co-authored-by: Olivier Goffart <olivier.goffart@slint.dev>

Fixes #7318
This commit is contained in:
Simon Hausmann 2025-01-10 15:21:16 +01:00 committed by Simon Hausmann
parent aa332202c5
commit 9504a4f090
6 changed files with 52 additions and 45 deletions

View file

@ -27,7 +27,7 @@ runs:
if: runner.os == 'Linux'
run: |
sudo apt-get update
sudo apt-get install libxcb-shape0-dev libxcb-xfixes0-dev libxkbcommon-dev libudev-dev libinput-dev libfontconfig-dev ${{ inputs.extra-packages }}
sudo apt-get install libxcb-shape0-dev libxcb-xfixes0-dev libxkbcommon-dev libxkbcommon-x11-dev libudev-dev libinput-dev libfontconfig-dev ${{ inputs.extra-packages }}
shell: bash
- name: Install Linux dependencies
if: ${{ runner.os == 'Linux' && (inputs.old-ubuntu != 'true')}}

View file

@ -103,8 +103,6 @@ jobs:
node_test:
env:
DYLD_FRAMEWORK_PATH: /Users/runner/work/slint/Qt/5.15.2/clang_64/lib
QT_QPA_PLATFORM: offscreen
RUSTFLAGS: -D warnings
CARGO_PROFILE_DEV_DEBUG: 0
CARGO_INCREMENTAL: false
@ -118,13 +116,6 @@ jobs:
steps:
- uses: actions/checkout@v4
- uses: ./.github/actions/install-linux-dependencies
- name: Install Qt
if: runner.os == 'Linux'
uses: jurplel/install-qt-action@v4
with:
version: "5.15.2"
setup-python: false
cache: true
- name: Upgrade LLVM for Skia build on Windows
if: runner.os == 'Windows'
run: choco upgrade llvm

View file

@ -650,10 +650,26 @@ fn call_builtin_function(
if let Expression::ElementReference(popup_window) = &arguments[0] {
let popup_window = popup_window.upgrade().unwrap();
let pop_comp = popup_window.borrow().enclosing_component.upgrade().unwrap();
let parent_component = pop_comp
.parent_element
.upgrade()
.unwrap()
.borrow()
.enclosing_component
.upgrade()
.unwrap();
let popup_list = parent_component.popup_windows.borrow();
let popup =
popup_list.iter().find(|p| Rc::ptr_eq(&p.component, &pop_comp)).unwrap();
generativity::make_guard!(guard);
let enclosing_component =
enclosing_component_for_element(&popup.parent_element, component, guard);
crate::dynamic_item_tree::close_popup(
popup_window,
component,
component.window_adapter(),
enclosing_component,
enclosing_component.window_adapter(),
);
Value::Void

View file

@ -335,7 +335,7 @@ assert_eq(instance.get_click_count(), 3);
assert_eq(instance.get_popup_clicked(), 2001);
```
```disable-because-nodejs-runs-with-qt-and-send-mouse-click-wont-send-to-popup-qwindow
```js
var instance = new slint.TestCase({});
assert.equal(instance.click_count, 0);

View file

@ -442,7 +442,7 @@ slint_testing::send_mouse_click(&instance, 15., 15.);
assert_eq(instance.get_click_count(), 2);
```
```disable-because-nodejs-runs-with-qt-and-send-mouse-click-wont-send-to-popup-qwindow
```js
var instance = new slint.TestCase({});
assert.equal(instance.click_count, 0);
@ -492,41 +492,41 @@ assert.equal(instance.click_count, 3);
// --------- Close outside click popup
instance.set_popup_selector(3);
instance.set_popup_created(false);
instance.set_click_count(0);
instance.popup_selector = 3;
instance.popup_created = false;
instance.click_count = 0;
slintlib.private_api.send_mouse_click(instance, 15., 15.);
assert.equal(instance.get_click_count(), 1);
assert.equal(instance.get_popup_created(), true);
assert.equal(instance.get_popup_clicked(), 2001);
assert.equal(instance.click_count, 1);
assert.equal(instance.popup_created, true);
assert.equal(instance.popup_clicked, 2001);
// click inside
slintlib.private_api.send_mouse_click(instance, 15., 15.);
assert.equal(instance.get_popup_clicked(), 2003);
assert.equal(instance.popup_clicked, 2003);
// Click outside to close
slintlib.private_api.send_mouse_click(instance, 5., 5.);
assert.equal(instance.get_click_count(), 1);
assert.equal(instance.click_count, 1);
// Subsequent click to verify that it was closed
slintlib.private_api.send_mouse_click(instance, 15., 15.);
assert.equal(instance.get_click_count(), 2);
assert.equal(instance.get_popup_clicked(), 2003);
assert.equal(instance.click_count, 2);
assert.equal(instance.popup_clicked, 2003);
// --------- Close outside click popup by esc
instance.set_popup_selector(3);
instance.set_click_count(0);
instance.popup_selector = 3;
instance.click_count = 0;
slintlib.private_api.send_mouse_click(instance, 5., 5.);
assert.equal(instance.get_click_count(), 1);
assert.equal(instance.click_count, 1);
// click inside
slintlib.private_api.send_mouse_click(instance, 15., 15.);
assert.equal(instance.get_popup_clicked(), 2005);
assert.equal(instance.popup_clicked, 2005);
// close by esc
slintlib.private_api.send_keyboard_string_sequence(instance, "\u{001b}");
slintlib.private_api.send_mouse_click(instance, 15., 15.);
assert.equal(instance.get_click_count(), 2);
assert.equal(instance.click_count, 2);
```
*/

View file

@ -458,7 +458,7 @@ slint_testing::send_mouse_click(&instance, 15., 15.);
assert_eq(instance.get_click_count(), 2);
```
```disable-because-nodejs-runs-with-qt-and-send-mouse-click-wont-send-to-popup-qwindow
```js
var instance = new slint.TestCase({});
assert.equal(instance.click_count, 0);
@ -508,41 +508,41 @@ assert.equal(instance.click_count, 3);
// --------- Close outside click popup
instance.set_popup_selector(3);
instance.set_popup_created(false);
instance.set_click_count(0);
instance.popup_selector = 3;
instance.popup_created = false;
instance.click_count = 0;
slintlib.private_api.send_mouse_click(instance, 15., 15.);
assert.equal(instance.get_click_count(), 1);
assert.equal(instance.get_popup_created(), true);
assert.equal(instance.get_popup_clicked(), 2001);
assert.equal(instance.click_count, 1);
assert.equal(instance.popup_created, true);
assert.equal(instance.popup_clicked, 2001);
// click inside
slintlib.private_api.send_mouse_click(instance, 15., 15.);
assert.equal(instance.get_popup_clicked(), 2003);
assert.equal(instance.popup_clicked, 2003);
// Click outside to close
slintlib.private_api.send_mouse_click(instance, 5., 5.);
assert.equal(instance.get_click_count(), 1);
assert.equal(instance.click_count, 1);
// Subsequent click to verify that it was closed
slintlib.private_api.send_mouse_click(instance, 15., 15.);
assert.equal(instance.get_click_count(), 2);
assert.equal(instance.get_popup_clicked(), 2003);
assert.equal(instance.click_count, 2);
assert.equal(instance.popup_clicked, 2003);
// --------- Close outside click popup by esc
instance.set_popup_selector(3);
instance.set_click_count(0);
instance.popup_selector = 3;
instance.click_count = 0;
slintlib.private_api.send_mouse_click(instance, 5., 5.);
assert.equal(instance.get_click_count(), 1);
assert.equal(instance.click_count, 1);
// click inside
slintlib.private_api.send_mouse_click(instance, 15., 15.);
assert.equal(instance.get_popup_clicked(), 2005);
assert.equal(instance.popup_clicked, 2005);
// close by esc
slintlib.private_api.send_keyboard_string_sequence(instance, "\u{001b}");
slintlib.private_api.send_mouse_click(instance, 15., 15.);
assert.equal(instance.get_click_count(), 2);
assert.equal(instance.click_count, 2);
```
*/