On Thu, 22 Jan 2026 16:53:09 GMT, Michael Strauß <[email protected]> wrote:
>> Implementation of [enhanced property >> metadata](https://gist.github.com/mstr2/2fec0303fc440b8eaeb126befc76eb5c). >> >> ### New API >> This PR includes the following API additions: >> >> 1. `ReadOnlyProperty.getDeclaringClass()` and its default implementation. >> 2. The `javafx.beans.property.AttachedProperty` interface. >> 3. New constructors for all `Simple<*>Property` and `ReadOnly<*>Wrapper` >> classes, accepting the declaring class of the property. >> >> The declaring class is stored in a new field in the `Simple<*>Property` >> classes. If a legacy constructor is used that doesn't specify the declaring >> class, the `ReadOnlyProperty.getDeclaringClass()` default implementation is >> called the first time the `Simple<*>Property.getDeclaringClass()` method is >> called, and its result is stored for future retrieval. >> >> ### Testing >> For testing, this PR also includes the >> `test.util.property.PropertyMetadataVerifier` tool. It systematically tests >> all public and protected properties of a class, and ensures conformance to >> the following rules: >> * `ReadOnlyProperty.getBean()` returns the object instance of the enclosing >> class, or the target object instance if the property is an attached property. >> * `ReadOnlyProperty.getName()` returns the name of the property, which must >> correspond to the name of the property getter (excluding the word >> "Property"). >> * `ReadOnlyProperty.getDeclaringClass()` returns the enclosing class of the >> property getter. >> * The declaring class of a `Simple<*>Property` or `ReadOnly<*>Wrapper` must >> be specified in the constructor, not resolved at runtime. >> * `getBean()`, `getName()`, and `getDeclaringClass()` must not be overridden >> in subclasses of `Simple<*>Property` or `ReadOnly<*>Wrapper`. >> * An instance property does not implement `AttachedProperty`. >> * An instance property has a parameterless property getter. >> * An attached property implements `AttachedProperty`. >> * An attached property has a static single-argument property getter that >> accepts the target object. >> * `AttachedProperty.getTargetClass()` returns the class of the single >> parameter of the static property getter. >> * A property getter does not return an instance of `ReadOnly<*>Wrapper`, it >> returns the result of calling `ReadOnly<*>Wrapper.getReadOnlyProperty()`. >> >> Many properties in existing JavaFX classes violate the >> `PropertyMetadataVerifier` rules in some way or shape. This PR won't address >> these issues, this will be done in a future cleanup PR. > > Michael Strauß has updated the pull request with a new target base due to a > merge or a rebase. The incremental webrev excludes the unrelated changes > brought in by the merge/rebase. The pull request contains five additional > commits since the last revision: > > - Merge branch 'master' into feature/property-metadata > - review changes > - ReadOnlyProperty.getDeclaringClass() tests > - doc > - Enhanced property metadata I've run into another scenario where having first-class styleable attached properties would make life _much_ easier. I've placed a `TabPane` such that its tabs overlap a `HeaderBar`. In order for the header bar to work correctly, I need to set the `HeaderBar.dragType` property on the tab pane and on its tabs (which are produced by a skin and not easily accessible from JavaFX code). Actually getting hold of the tabs of a `TabPane` is complicated by the fact that they only exist after the skin has been inflated by CSS; they don't exist after I've typed `var tabPane = new TabPane()` in code. So I need to manually inflate the skin, or defer configuration to the next pulse. After that, I need to use `Node.lookupAll(".tab")` to get the nodes that represent the tabs, or I need to traverse the children of the tab pane until I've found the tabs. Only then can I set the `HeaderBar.dragType` property on those nodes. If we had styleable attached properties, I could just provide a stylesheet for my tab pane: .tab-pane { -fx-headerbar-dragtype: transparent-subtree; } .tab-pane .tab { -fx-headerbar-dragtype: none; } ------------- PR Comment: https://git.openjdk.org/jfx/pull/2015#issuecomment-3863351123
