TAnimation有一个动画结束事件,当动画完成后触发这个事件,但是没有提供回调支持,就是在Start一个动画时,就指定动画完成后调用的方法,以取代OnFinish事件。查看QC,有人早在10.2.3就提到了这个需求:
https://quality.embarcadero.com/browse/RSP-20802
遗憾的是,直到现在的Delphi 11.1版本也没有实现,也许是官方觉得不重要吧,不得矣,自己加了一下。
如果你有QC账号,一起去投个票,督促官方解决。
//为TAnimation重载一个Start方法: //++++++++++ by 红鱼儿 procedure Start(AFinishCallback:TFinishCallback);overload; //++++++++++ by 红鱼儿
代码实现:
//++++++++++ by 红鱼儿 procedure TAnimation.Start(AFinishCallback: TFinishCallback); begin FFinishCallback:=AFinishCallback; Start; end; //++++++++++ by 红鱼儿
再修改DoFinish方法:
procedure TAnimation.DoFinish; begin //++++++++++ by 红鱼儿 if Assigned(FFinishCallback) then FFinishCallback(Self) else //++++++++++ by 红鱼儿 if Assigned(FOnFinish) then FOnFinish(Self); end;
OK,现在调用一下:
procedure TCameraForm.PlayFormAnimationOut; var fa: TFloatAnimation; begin fa := Self.FindComponent('FloatAnimation2_') as TFloatAnimation; if fa <> nil then begin fa.Start(procedure(Sender:TObject)//使用回调函数来处理动画完成后的动作 begin Close; end); end end;
上面这段代码,fa.Start启动动画时就指定了完成需要执行的动作,这样,我就不用去用事件来处理了。
万事大吉!
需要代码的同学可以联系我,免得自己再改了。
后记:
盒子上的emailx45告诉我更好的方法,不用修改源码,通过继承实现的方案,直接上代码,测试通过。
TFloatAnimation = class(FMX.Ani.TFloatAnimation) private type TFinishCallback = TProc<TObject>; private FFinishCallback:TFinishCallback; protected procedure DoFinish; override; public procedure Start(FinishCallback:TFinishCallback=nil);reintroduce; end; { TFloatAnimation } procedure TFloatAnimation.DoFinish; begin inherited; if Assigned(FFinishCallback) then FFinishCallback(Self); end; procedure TFloatAnimation.Start(FinishCallback: TFinishCallback); begin FFinishCallback:=FinishCallback; inherited Start; end;