Reputation: 710
Consider the following method in my Map
class:
@XYLiteralDecorator
setCenter(xy: XY | XYLiteral): void {
this.mapI.centerAt((<XY>xy).projectToPoint(3978));
}
This is the @XYLiteralDecorator
decorator used above:
function XYLiteralDecorator(target: Object, propertyKey: string, descriptor: TypedPropertyDescriptor<any>) {
const originalMethod = descriptor.value;
descriptor.value = function(maybeXY: XY | XYLiteral): XY {
return originalMethod.apply(this, [isXYLiteral(maybeXY) ? new XY(maybeXY[0], maybeXY[1]) : maybeXY]);
};
return descriptor;
}
You'll notice in the setCenter
method I need to force xy
to be of type XY
since TS will complain xy
can be either XY
or XYLiteral
otherwise. However my decorator will always ensure xy
is of type XY
.
Is it possible for TS to know xy
can only be of type XY
while at the same time allowing both XY
or XYLiteral
types to be passed as parameters (without forcing types like I'm doing above)?
Upvotes: 2
Views: 507
Reputation: 249486
You can add an overload that contains the union type parameter and have the implementation have the actual parameter type:
setCenter(xy: XY | XYLiteral): void;
@XYLiteralDecorator
setCenter(xy: XY ): void {
console.log(xy.getX());
}
This works as expected, you can call with either type and the implementation will know the actual type:
dds.setCenter(new XY(0,0));
dds.setCenter([1, 1]);
Full sample here
Upvotes: 2