公开绑定属性
属性应该如何暴露?
例如:
class A{ private ObjectProperty objx; } class B{ private ObjectProperty objy; }
我们想将objy
绑定到objx
或者从B
向objx
添加一个监听器。 为objx
做一个吸气剂objx
? 或者有没有办法制作一个包装函数来绑定并公开这个函数?
标准模式是
class A { private final ObjectProperty objx = new SimpleObjectProperty<>(); public ObjectProperty objxProperty() { return objx ; } public final X getObjx() { return objxProperty().get(); } public final void setObjx(X objx) { objxProperty().set(objx); } }
这里的想法是你有一个属性本身的访问器方法(一个“属性访问器”: objxProperty()
),它可以用于绑定和注册监听器,但该属性也显示为常规Java Bean :即那里是标准的get
和set
方法。 一般契约是你应该总是有x.getObjx() == x.objxProperty().get()
,这是通过使Java Bean访问器方法( getObjx()
和setObjx
)最终来强制执行的。
如果您希望能够在内部修改属性,但希望仅公开只读属性(其他代码可以绑定到该属性),请使用ReadOnlyObjectWrapper
:
class A { private final ReadOnlyObjectWrapper objx = new ReadOnlyObjectWrapper<>(); public ReadOnlyObjectProperty objxProperty() { return objx.getReadOnlyProperty(); } public final X getObjx() { return objxProperty().get(); } }
还要看看这个powerpoint演示文稿 ,虽然陈旧,但它显示了许多有用的习惯用法,例如属性的惰性和超级惰性初始化。
以下结构在JavaFX中广泛使用:
class A { // Private inner property private ObjectProperty objx; // Public property accessor method public final ObjectProperty objxProperty() { if (objx == null) objx = new SimpleObjectProperty (DEFAULT_VALUE); return objx; } // Public setter method public final void setObjx(X val) { objxProperty().set(val); } // Public getter method public final X getObjx() {return objx == null ? DEFAULT_VALUE : objx.get();} }
你在这里看到的是懒惰初始化 。 诀窍是私有内部属性在被(真的)被请求之前不会被初始化。
公共属性访问器objxProperty()
将初始化私有内部属性objx
。 此属性访问器方法用于公开绑定和侦听的内部属性。 private内部属性获取“Property”后缀,可以将其视为JavaFX中的约定。
公共setter方法setObjx
使用此属性访问器方法,因此在请求设置此属性的值的情况下,将初始化内部属性。
在公共getter getObjx()
情况下有点不同,就好像内部属性尚未初始化(在属性上没有直接访问请求而之前没有设置请求),直接返回默认值而不初始化内部属性,进一步延迟初始化程序。
例如,对于JavaFX中TextField
的alignmentProperty
,您可以看到此技术。
如果你不想让事情复杂化,James_D在他的回答中解释的“标准模式”实际上是标准(方法命名与此处相同)。