我有一个非常肮脏的方式有7个listboxses滚动同步,他们都有完全相同的高度,所以当我移动他们中任何一个的位置,其他6个也应该移动到该位置
我所做的是假设Listbox1被滚动并且**ViewportPositionChange()**被触发我说
Listbox2.ViewportPosition := NewViewportPosition;
Listbox3.ViewportPosition := NewViewportPosition;
这一切都工作,我只是添加这个代码到每个Listboxses ViewportPositionChange()事件,但它的可怕的不稳定和太慢的Andriod,我仍然需要能够滚动从任何一个列表框,但有没有一种方法来提高滚动的性能?
好吧,老实说,它不是很慢,但你可以感觉到它不完全是敏捷的,而且每个列表框可以有很多列表框,每个列表框也可以有一些控件和更多的控件在这些控件,所以很多重绘是做了我认为,这是什么使它不那么敏捷。
示例代码
首先在你的表单上放置一个网格面板布局,添加6列并添加一个列表框到每一列,每个列表框代表一天,其中列表框1是星期一,也对齐这些客户端。
全局变量
private Glistbox : array[0..6] of TListBox;
在表单创建时
Glistbox[0] := ListBox1;
Glistbox[1] := ListBox2;
Glistbox[2] := ListBox3;
Glistbox[3] := ListBox4;
Glistbox[4] := ListBox5;
Glistbox[5] := ListBox6;
Glistbox[6] := ListBox7;
现在在每个列表框上OnViewportPositionChange
//Note that this would be for Listbox1 so for listbox 2 it needs to be changed acordingly
ListBox2.ViewportPosition := NewViewportPosition;
ListBox3.ViewportPosition := NewViewportPosition;
ListBox4.ViewportPosition := NewViewportPosition;
ListBox5.ViewportPosition := NewViewportPosition;
ListBox6.ViewportPosition := NewViewportPosition;
ListBox7.ViewportPosition := NewViewportPosition;
然后使用以下代码添加一个按钮:
var
mainlayout,item1,item2 : Tlayout;
listboxitem : TListBoxItem;
myrec,myrec2 : TRectangle;
lbl1,lbl2 : TLabel;
I: Integer;
begin
for I := 0 to 6 do
begin
listboxitem := TListBoxItem.Create(nil);
mainlayout := TLayout.Create(nil);
mainlayout.Align := TAlignLayout.Client;
mainlayout.Parent:= listboxitem;
item1 := TLayout.Create(nil);
item1.Align:= TAlignLayout.Left;
item1.Parent := mainlayout;
item2 := TLayout.Create(nil);
item2.Align:= TAlignLayout.Right;
item2.Parent := mainlayout;
myrec := TRectangle.Create(nil);
myrec.Align := TAlignLayout.Client;
myrec.Parent := item1;
myrec2 := TRectangle.Create(nil);
myrec2.Align := TAlignLayout.Client;
myrec2.Parent := item2;
lbl1 := TLabel.Create(nil);
lbl1.Align := TAlignLayout.Client;
lbl1.TextAlign := TTextAlign.Center;
lbl1.Text := '1';
myrec.AddObject(lbl1);
lbl2 := TLabel.Create(nil);
lbl2.Align := TAlignLayout.Client;
lbl2.TextAlign := TTextAlign.Center;
lbl2.Text := '2';
myrec2.AddObject(lbl2);
Glistbox[I].AddObject(listboxitem);
item2.Width:= mainlayout.Width/2;
end;
有时可能有更多的控件在一个列表框中,但一般来说,我认为这将是规范,现在添加一些项目,并尝试滚动
2条答案
按热度按时间jmo0nnb31#
FMX TListBox有很多开销,因为每个列表框项基本上都是一个插入滚动框的样式化组件。这有利于灵活性,但不利于速度。
在Windows和OSX中,有一些像ScrollWindowEx或NSView.scrollRect + NSView.setNeedsDisplayInRect这样的函数,它们可以通过滚动窗口的一部分而不发出绘制消息来帮助提高性能。所以你只需要使列表框的一部分无效。我可以想象Android也有类似的功能。但是你可能需要修补FMX才能使用它。这可以提高一点性能。但仍然不是一个获得高性能的神奇开关。类似的方法是将滚动框的内容缓存在位图中,然后在滚动时将部分位图复制到屏幕上。
如果你真的需要很好的列表框性能,那么你需要开发自己的列表框,优化速度。这是我必须做的OSX版本的应用程序,以获得我需要的性能。
vjrehmav2#
此外,还有Firemonkey的TListView,当所有项目共享相同的视觉结构时,它比TListBox更好。Ray Konopka(2014年)的教程解释了每种视图的适用范围:https://www.youtube.com/watch?time_continue=934&v=XHYtwAu5fl4
要调整滚动行为(如果有帮助),请参阅:https://docwiki.embarcadero.com/RADStudio/Alexandria/en/FireMonkey_Layouts_Strategies#Smooth_Inertial_Scrolling