junit JavaFX手动触发FocusLost事件以测试Slider侦听器

tyg4sfes  于 2023-08-05  发布在  Java
关注(0)|答案(1)|浏览(153)

我在我的窗格上有一个Slider,它的listener on focus属性只在值更改完成并且焦点丢失时执行一些逻辑:

public class MyPane extends GridPane {
    private Slider mySlider;
    public MyPane () {
        this.mySlider= new Slider(...);
        this.mySlider.focusedProperty().addListener(e -> {
            if (!mySlider.isFocused()) {
                doSmth();
            }
        });
    }
}

字符串
它工作得很好,但我不知道如何用单元测试来覆盖这个逻辑。
由于focusProperty是ReadOnly,我不知道如何手动更改它的值以触发单元测试中的侦听器:

@Test
    public void settingsPaneHasRAMSlider() {
        List<Node> sliderList = myPane.getChildren().filtered(node -> node.getClass().equals(Slider.class));
        Assertions.assertEquals(1, sliderList.size());

        Slider slider = (Slider) sliderList.get(0);

        slider.fireEvent(/* FOCUS AND UNFOCUSSED EVENT? */);

        Mockito.verify(myMock).doSmth();
    }


我尝试用鼠标单击并手动更改测试代码中的滑块值,但它不会触发我添加到滑块的focusProperty中的InvalidationListener。后来我也试过slider.requestFocus();myPane.requestFocus(),但由于这是一个单元测试,没有Stage/Scene,因此requestFocus没有做任何事情。
你知道如何模仿焦点的变化吗?

lvjbypge

lvjbypge1#

看来除了利用这里的倒影没有别的办法了。即使在test方法中添加Slider到创建的Scene中,并在稍后调用requestFocus()时,它确实将slider设置为focusOwner,但不会触发focusProperty侦听器。
所以我用下一个代码达到了我想要的:

@Test
    public void myTest() throws NoSuchMethodException, InvocationTargetException, IllegalAccessException {
        List<Node> sliderList = myPane.getChildren().filtered(node -> node.getClass().equals(Slider.class));
        Assertions.assertEquals(1, sliderList.size());

        Slider slider = (Slider) sliderList.get(0);

        Method m = Node.class.getDeclaredMethod("setFocused", boolean.class);
        m.setAccessible(true);
        m.invoke(slider, true);

        double newXmxValue = 2 * slider.getValue(); //double the default value !=0
        slider.setValue(newXmxValue);

        m.invoke(slider, false);

        Mockito.verify(controllerMock).doSmth();
    }

字符串

相关问题