RFR: 8375363: StyleHelper.resetToInitialValues() interrupts animated properties [v4]

Michael Strauß mstrauss at openjdk.org
Sat Jan 17 20:59:31 UTC 2026


> In the following program, resizing the window to be smaller than 300px should start a transition for `-fx-scale-x` from 2 to 1, but instead the value sometimes snaps back to 1 instantly:
> 
> 
> public class InterruptedTransitionBug extends Application {
>     @Override
>     public void start(Stage stage) throws Exception {
>         var root = new StackPane(new Button("My Button"));
>         var scene = new Scene(root, 600, 200);
>         scene.getStylesheets().add("data:text/css;base64," + Base64.getEncoder().encodeToString("""
>             .button {
>                 transition: -fx-scale-x 2s;
>             }
> 
>             @media (width > 300px) {
>                 .button {
>                     -fx-scale-x: 2;
>                 }
>             }
>             """.getBytes(StandardCharsets.UTF_8)));
>         stage.setScene(scene);
>         stage.show();
>     }
> }
> 
> 
> ### Problem
> First, let's look at how `CssStyleHelper` works when the cascading style map for a node changes:
> 1. When the style map for a node has changed, `StyleHelper.createStyleHelper(Node)` determines that the style helper is no longer any good, and a new `CssStyleHelper` for the new style map is created.
> 2. Before the old style helper is discarded, it calls `CssStyleHelper.resetToInitialValues(Styleable)` and resets all properties that were set by this style helper back to their initial values. This ensures that the new style helper has a "clean slate" to work from.
> 3. The next `Node.applyCss()` pass will now set the properties that are specified in the new style map to their new values.
> 
> However, when transitions come into play, this mechanism can break:
> 1. In our example, the `Button` starts with a style map that contains two properties:
>    * `transition: -fx-scale-x 2s`
>    * `-fx-scale-x: 2`
> 2. Due to a changing media query, this is replaced with a style map that only contains a single entry:
>    * `transition: -fx-scale-x 2s`
> 3. Before the new style map is applied, all properties affected by the old style map are reset to their initial values. That means:
>    * `-fx-scale-x` is reset to `1`
>    * `transition` is reset to `null`
> 
> This is where it breaks: if `transition` is reset before `-fx-scale-x`, the latter will see no transition when its value is set back to `1`.
> 
> ### Solution
> Simply resetting all properties back to their initial values when a style map is changed is not necessary. We only need to reset the properties that are set by the old style map, but are no longer set by the new style map. In our example, si...

Michael Strauß has updated the pull request incrementally with one additional commit since the last revision:

  fix detection of sub-properties

-------------

Changes:
  - all: https://git.openjdk.org/jfx/pull/2038/files
  - new: https://git.openjdk.org/jfx/pull/2038/files/a677800e..d8817ad7

Webrevs:
 - full: https://webrevs.openjdk.org/?repo=jfx&pr=2038&range=03
 - incr: https://webrevs.openjdk.org/?repo=jfx&pr=2038&range=02-03

  Stats: 24 lines in 1 file changed: 23 ins; 0 del; 1 mod
  Patch: https://git.openjdk.org/jfx/pull/2038.diff
  Fetch: git fetch https://git.openjdk.org/jfx.git pull/2038/head:pull/2038

PR: https://git.openjdk.org/jfx/pull/2038


More information about the openjfx-dev mailing list