slint-ui / slint

Slint is a declarative GUI toolkit to build native user interfaces for Rust, C++, or JavaScript apps.
https://slint.dev
Other
17.67k stars 611 forks source link

Position and rendering of right-aligned `Text` depends on element `width` #6739

Open Enyium opened 2 weeks ago

Enyium commented 2 weeks ago

Consider this SlintPad demo:

export component AppWindow inherits Window {
    width: 200px;
    height: 70px;

    Timer {
        interval: 1.5s;
        running: true;

        property <int> num-digits: 0;

        triggered => {
            self.num-digits = (self.num-digits + 1).mod(20);
            if self.num-digits == 0 {
                t1.text = "";
                t2.text = "";
            } else {
                t1.text = t1.text + "0";
                t2.text = t2.text + "0";
            }
        }
    }

    VerticalLayout {
        alignment: start;

        t1 := Text {
            text: "";
            horizontal-alignment: right;
        }

        HorizontalLayout {
            alignment: end;

            t2 := Text {
                text: "";
                horizontal-alignment: right;
            }
        }

        HorizontalLayout {
            alignment: end;

            t3 := Text {
                text: "000";
                horizontal-alignment: right;

                width: ta.has-hover ? 60px : 50px;
                animate width {
                    duration: 2s;
                }

                ta := TouchArea {}
            }
        }
    }
}

At least for me, it isn't so obvious in SlintPad, which uses FemtoVG. But this local Skia rendering clearly shows it (Rust lib feature renderer-skia-opengl; washed out black and blurriness seems to come from video compression):

https://github.com/user-attachments/assets/b4045800-fdd9-44e0-9ca8-128c9bc8d786

In the first line, the Text stays at one width. The other right-aligned Texts should effectively get the same x + width position, but, for some reason, change their texts' position and rendering when the element width changes, either by adding text, or by animating width.