我正在尝试从外部对象设置属性:
main() {
A a = A();
print(a.prop.runtimeType); // is 'Null'
MiddleMan().b.assign(a.prop);
print(a.prop.runtimeType); // should be 'B', but is 'Null'
}
class A { B prop; }
class MiddleMan { B b = B(); }
class B {
assign(B property) { property = this; }
}
我设法通过镜子实现了此功能:
import 'dart:mirrors';
main() {
A a = A();
print(a.prop.runtimeType); // is 'Null'
MiddleMan().b.assign(a, 'prop');
print(a.prop.runtimeType); // is 'B'
}
class A { B prop; }
class MiddleMan { B b = B(); }
class B {
assign(dynamic object, String property) {
InstanceMirror reflectee = reflect(object);
reflectee.setField(Symbol(property), this);
}
}
但是后来我意识到在Flutter中禁用了镜像。有什么解决方法吗?
答案 0 :(得分:0)
正如here所述,可以使用包装器类:
main() {
A a = new A();
print(a.prop.value.runtimeType); // is 'Null'
MiddleMan().b.assign(a.prop);
print(a.prop.value.runtimeType); // is 'B'
}
class A {
Wrapper<B> prop = Wrapper(null);
}
class MiddleMan {
B b = B();
}
class B {
assign(Wrapper<B> property) {
property.value = this;
}
}
class Wrapper<T> {
T value;
Wrapper(this.value);
}
但是因为我的意图是编写一个库并使用户易于使用,所以只需一行调用即可:
MiddleMan().b.assign(a.prop);
同时,在分配属性时,我需要可选地处理其他内容,因此,像a.prop = MiddleMan().b;
这样的直接分配,现在我决定在重载&
运算符时使用某种不寻常的语法,其用法如下:
a.prop = MiddleMan().b;
或可选:
a.prop = MiddleMan().b & doAdditionalStuff;
这是实现:
class B {
B operator &(Function doAdditionalStuff) {
if (doAdditionalStuff != null)
doAdditionalStuff();
return this;
}
}
为了更清楚地了解我要实现的目标,我的lib应该与Provider库一起使用。用户代码示例:
class MyStore with ChangeNotifier {
B prop;
MyStore() {
// MiddleMan is Singleton
prop = MiddleMan().b;
// or alternatively
prop = MiddleMan().b & notifyListeners;
}
}
库代码示例:
class B {
List<Function> _reactives = [];
B operator &(Function notifyListenersCallback) {
if (notifyListenersCallback != null)
this._reactives.add(notifyListenersCallback);
return this;
}
// called on each internally triggered change
notifyListeners() {
for (Function reactive in this._reactives) {
if (reactive != null)
reactive();
}
}
}