delphi – FireMonkey控件不能平滑地设置动画
背景
我使用一些FireMonkey控件创建了一个GUI. >某些控件是动画的,其外观会自动更新. 问题 与用户控件的交互可防止更新动画控件,从而导致不稳定的不连续动画. Video of glitchy animation 上面视频中的动画控件由TTimer组件驱动.使用FireMonkey的动画组件时问题仍然存在. 调查 滑块控件在调整时调用Repaint().平滑调整滑块将生成密集的Repaint()调用流,阻止其他控件更新. 该怎么办? 在一个控件不断更新时冻结动画不适合我的应用程序.我的第一个想法是交换Repaint()调用类似于VCL Invalidate()方法,但FireMonkey没有任何可比的AFAIK. 这个问题有一个很好的解决方法吗? 解决方法
我已经创建了一个基于计时器的重绘方法,正如Arnaud Bouchez在上面的评论中所建议的那样.到目前为止似乎有效.
码 unit FmxInvalidateHack; interface uses Fmx.Types; procedure InvalidateControl(aControl : TControl); implementation uses Contnrs; type TInvalidator = class private protected Timer : TTimer; List : TObjectList; procedure Step(Sender : TObject); public constructor Create; destructor Destroy; override; procedure AddToQueue(aControl : TControl); end; var GlobalInvalidator : TInvalidator; procedure InvalidateControl(aControl : TControl); begin if not assigned(GlobalInvalidator) then begin GlobalInvalidator := TInvalidator.Create; end; GlobalInvalidator.AddToQueue(aControl); end; { TInvalidator } constructor TInvalidator.Create; const FrameRate = 30; begin List := TObjectList.Create; List.OwnsObjects := false; Timer := TTimer.Create(nil); Timer.OnTimer := Step; Timer.Interval := round(1000 / FrameRate); Timer.Enabled := true; end; destructor TInvalidator.Destroy; begin Timer.Free; List.Free; inherited; end; procedure TInvalidator.AddToQueue(aControl: TControl); begin if List.IndexOf(aControl) = -1 then begin List.Add(aControl); end; end; procedure TInvalidator.Step(Sender: TObject); var c1: Integer; begin for c1 := 0 to List.Count-1 do begin (List[c1] as TControl).Repaint; end; List.Clear; end; initialization finalization if assigned(GlobalInvalidator) then GlobalInvalidator.Free; end. == 用法 可以通过调用重新绘制控件: InvalidateControl(MyControl); InvalidateControl()过程不会立即重新绘制控件.相反,它将控件添加到列表中.全局计时器稍后检查列表,调用Repaint()并从列表中删除控件.使用此方法,可以根据需要使控件无效,但不会像快速Repaint()调用那样阻止其他控件被更新. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |