copy_with_extension
copy_with_extension copied to clipboard
Allow overriding copyWith
trafficstars
If copyWith of the base class that is overridden by the subclass is called, copyWith of the subclass should be called. However, since extension will not be overridden in dart, copyWith of the base class will be called.
@CopyWith()
class Base {
int x;
Base({required this.x});
Base copyWith2({int? x}) => Base(x: x ?? this.x);
}
@CopyWith()
class Extended extends Base {
int y;
Extended({required super.x, required this.y});
@override
Extended copyWith2({int? x, int? y}) => Extended(x: x ?? this.x, y: y ?? this.y);
}
void main() {
final Base base = Extended(x: 1, y: 2);
print(base.copyWith()); // flutter: Instance of 'Base' <-- should be Extended
print(base.copyWith2()); // flutter: Instance of 'Extended'
}
Also, in such a design, Base may be abstract, in which case copy_with_extension generates code that cannot be compiled.
I have researched about this and found this solution:
- Delete
_$BaseCWProxyImpland$BaseCopyWith. (which are implementations for an abstract class). - Change
_$ExtendedCWProxyextends_$BaseCWProxy. - Change copyWith in
$ExtendedCopyWithprivate. (Optional)
Then, this can be achived as below:
@CopyWith()
abstract class Base {
int x;
Base({required this.x});
_$BaseCWProxy get copyWith;
}
@CopyWith()
class Extended extends Base {
int y;
Extended({required super.x, required this.y});
@override
_$ExtendedCWProxy get copyWith => _copyWith;
}
void main() {
final Base base = Extended(x: 1, y: 2);
print(base.copyWith()); // flutter: Instance of 'Extended'
}
Could you add options for this? Or is there any better way to do this?
i was just looking for this exact feature, would be great 🙏
A workaround I found is to define factory constructor in the base class.
factory BaseClass.copyWith(
BaseClass oldInstance, {
...args
}) {
if (oldInstance is ExtendedClass) {
return ExtendedClass(
...args
);
}
}