我一直在玩TListBox控件,绘制图像和更改字体样式等.我想稍微加强它,并尝试使用缩进和多级缩进来操作项目.
看看这张图片可以获得更好的想法:

我们的想法是,列表中位于开始和结束项目之间的项目应相应缩进.
所以,为了给出一个想法我在Paint中编辑了截图,所以它看起来像这样:

接近这个的方法是什么?我的想法是遍历列表框并在2个单独的变量中返回开始和结束项目的数量,然后以某种方式确定其他项目的位置以及它们之间是否适合 - 但我的逻辑从未如此好:(
为了便于使用,我在下面提供了代码,以显示我如何绘制图像和样式:
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls, ImgList, ComCtrls;
type
TForm1 = class(TForm)
ImageList1: TImageList;
PageControl1: TPageControl;
TabSheet1: TTabSheet;
ListBox1: TListBox;
TabSheet2: TTabSheet;
ListBox2: TListBox;
TabSheet3: TTabSheet;
ListBox3: TListBox;
procedure FormCreate(Sender: TObject);
procedure ListBox1MeasureItem(Control: TWinControl; Index: Integer;
var Height: Integer);
procedure ListBox1DrawItem(Control: TWinControl; Index: Integer;
Rect: TRect; State: TOwnerDrawState);
procedure ListBox2MeasureItem(Control: TWinControl; Index: Integer;
var Height: Integer);
procedure ListBox2DrawItem(Control: TWinControl; Index: Integer;
Rect: TRect; State: …Run Code Online (Sandbox Code Playgroud) 以下代码很好地动画将新字符串添加到ListBox的末尾
procedure TForm6.AddItem(s: string);
var
l : TListBoxItem;
OldHeight : Single;
begin
l := TListBoxItem.Create(Self);
l.Text := s;
OldHeight := l.Height;
l.Height := 0;
l.Parent := ListBox1;
l.Opacity := 0;
l.AnimateFloat('height', OldHeight, 0.5);
l.AnimateFloat('Opacity', 1, 0.5);
end;
Run Code Online (Sandbox Code Playgroud)
该项扩展并淡入.但是我希望能够将字符串添加到ListBox中的任意位置 - 实际上是在当前的ItemIndex中.有谁知道如何做到这一点?
它工作正常(对于我写的所有代码),按预期显示内容(我甚至轻松添加了一个水平滚动条),但我想我已经达到了垂直滚动条的某种限制.
也就是说,当我从顶部向底部滚动垂直条时,它不会将内容滚动到列表的末尾,而只会滚动到某个限制.
你知道有没有摆脱这个限制的可能性?我试过SetScrollInfo,但它没有工作,因为限制听起来不在滚动条中,而是在TListBox自身中.
我知道创建专用的解决方案TCustomControl:在这种情况下,SetScrollInfo将按预期工作.但有人知道仍然使用的解决方案/技巧TListBox吗?
编辑:说清楚 - 我不要求(第三方)组件解决方案,但要知道是否有一些低级GDI消息要发送到标准TListBox以覆盖此限制.如果没有,我将转到专用TCustomControl解决方案.
这是使用TSCROLLINFO的代码:
procedure ScrollVertHuge(Handle: HWND; count: integer);
var Scroll: TSCROLLINFO;
begin
Scroll.cbSize:= sizeof(Scroll);
Scroll.fMask := SIF_DISABLENOSCROLL or SIF_RANGE;
Scroll.nMin := 0;
Scroll.nMax := count;
SetScrollInfo(Handle,SB_VERT,Scroll,false);
end;
Run Code Online (Sandbox Code Playgroud)
要精确地解决这个问题:添加和绘制两个工作当然(我的工具按预期工作),但不起作用的是垂直滚动条拖动.我重命名了问题的标题,并删除了令人困惑的已弃用的MSDN文章.
使用TListBox获取"OnChange"类型的功能有诀窍吗?我可以子类化组件并添加属性等,然后只有在索引更改时才执行OnClick代码...我也可以使用表单级变量来存储当前索引,但只是想知道我是否忽略了之前的我走了一路或另一路.

有人可以指导我正确的方向吗?我正在尝试使用 Delphi XE4 为 iOS 应用程序创建自定义 ListboxItem。我的目标输出将类似于上面的照片,因为我目前被困在这里(下图)。

我已成功动态生成 ListBoxItem 并插入 TLabel 对象,但是,我无法将 TLabel 的“fontColor”属性更改为所需的颜色。我可以编码
TLabel.Fontcolor := ClaBlue;
但颜色又恢复为黑色。我希望它看起来就像我给出的示例一样。我在更改插入的 TLabel 的字体颜色以及向每个列表框项添加渐变背景时遇到问题。我不知道是否需要使用“样式编辑器”,甚至不知道如何使用。是的,我已经查看了 Delphi/RAD Studio 中包含的示例,下面是我当前的编码:
while XMLNode<>nil do begin
HeaderText := 'Part#: ' + XMLNode.ChildNodes['PARTNUM'].Text + Chr(9) + XMLNode.ChildNodes['VENDPARTNUM'].Text;
DetailText := '$' + XMLNode.ChildNodes['MD1_SELL_PRICE'].Text + ' /' + XMLNode.ChildNodes['UM1_PRICE_NAME'].Text + sLineBreak + 'Min: ' + XMLNode.ChildNodes['md2_from.MD2_MIN_QTY'].text + Chr(9) + 'On Hand: ' + XMLNode.ChildNodes['md2_from.MD2_ON_HAND_QTY'].text + Chr(9) + Label1.text ;
Form6.ListBox1.Items.Add(DetailText);
ListBoxItem:=Form6.ListBox1.ListItems[Form6.ListBox1.Items.Count-1];
ListBoxItem.StyleLookup:='listboxitembottomdetail';
ListBoxItem.WordWrap:=True;
ListBoxItem.Font.Size:= 8;
ListBoxItem.Height := 120;
TestLabel := TLabel.Create(self);
TestLabel.Text …Run Code Online (Sandbox Code Playgroud) 我正尝试使用以下格式从列表框中的RSS显示新闻,如下图所示.屏幕截图中的应用程序是通过设置列表框样式在firemonkey中开发的.我需要在我的VCL应用程序中显示相同内容.
这种布局的要求是:
我的代码到目前为止:
procedure TfrmDatePicker.ListBox1DrawItem(Control: TWinControl; Index: Integer;
Rect: TRect; State: TOwnerDrawState);
var
R: TRect;
begin
ListBox1.Canvas.Font.Color := clBlack;
ListBox1.Canvas.Font.Style := [fsBold];
ListBox1.Canvas.Font.Size := 9;
if Odd(Index) then ListBox1.Canvas.Brush.Color := clWhite
else ListBox1.Canvas.Brush.Color := clBtnFace;
ListBox1.Canvas.FillRect (Rect);
ListBox1.Canvas.Pen.Color := clHighlight;
if(odSelected in State) then
begin
ListBox1.Canvas.Font.Color := clHighlightText;
ListBox1.Canvas.Brush.Color := clHighlight;
ListBox1.Canvas.Rectangle(Rect.Left, Rect.Top, Rect.Right, Rect.Bottom);
if(odFocused in State) then DrawFocusRect(ListBox1.Canvas.Handle, Rect);
end;
ImageList1.Draw(ListBox1.Canvas, Rect.Left + 2,
Rect.top + (ListBox1.ItemHeight - ImageList1.Height) div 2, Index, true);
ListBox1.Canvas.TextOut(Rect.Left …Run Code Online (Sandbox Code Playgroud) 我有一个TListBox,其中包含一个位置列表(每个位置都有一个名称和距当前位置的距离).我想让用户选择按位置名称(即按字母顺序)或与当前位置的距离对列表进行排序.位置名称存储为项目的ItemData.Text值,距当前位置的距离存储为ItemData.Detail值.问题是常规TListBox排序方法在排序时不使用ItemData.Detail属性(只是ItemData.Text属性).是否可以向TListBox添加自定义排序方法,根据每个项目的ItemData.Detail值进行排序?
我尝试了以下,但它不起作用:
procedure TFrmSelect.btnSortLocationClick(Sender: TObject);
var Compare: TFMXObjectSortCompare;
begin
btnSortLocation.Enabled := False;
btnSortAlpha.Enabled := True;
Compare := function(item1, item2: TFmxObject): Integer
begin
Result := TListBoxItem(item1).ItemData.Detail.CompareTo(TListBoxItem(item2).ItemData.Detail);
end;
self.ListBox.Sort(Compare);
self.ListBox.Sorted := False;
self.ListBox.Sorted := True;
end;
Run Code Online (Sandbox Code Playgroud)
以下是要排序的示例列表的图像:
简短版本:是否可以单独控制或修改LisBox项目?例如,将其Visible 属性分别设置为False。在搜索时,我在Fire Monkey中找到了一个TListBoxItem类,但我不想使用Fire Monkey,而又希望在VCL中使用它。
详细版本:我尝试使用两个TStringList和一个Edit过滤ListBox,一个StringList是全局的,以保留原始列表(list_files_global),另一个StringList是帮助过滤过程的(list_files_filter),而我的主要文件列表是ListBox(list_files)。我在onCreate程序开始存储原始列表时在事件中创建了全局StringList :
procedure Tfrm_main.FormCreate(Sender: TObject);
Begin
list_files_global := TStringList.Create;
list_files_global.Assign(list_files.Items);
End;
Run Code Online (Sandbox Code Playgroud)
并使用Edit onChange事件进行过滤:
procedure Tfrm_main.edit_files_filterChange(Sender: TObject);
Var
list_files_filter: TStringList;
i: Integer;
Begin
list_files_filter := TStringList.Create;
list_files_filter.Assign(list_files.Items);
list_files.Clear;
for i := 0 to list_files_filter.Count - 1 do
if pos(edit_files_filter.text, list_files_filter[i]) > 0 then
list_files.Items.Add(list_files_filter[i]);
End;
Run Code Online (Sandbox Code Playgroud)
而要关闭过滤器,只需从我最初创建的全局列表中恢复列表即可:
list_files.Items := list_files_global;
Run Code Online (Sandbox Code Playgroud)
到目前为止,一切正常,但是问题是当我尝试编辑/重命名/删除过滤列表中的项目时,例如,我更改了一个项目:
list_files.Items[i] := '-- Changed Item --';
Run Code Online (Sandbox Code Playgroud)
列表将被编辑,但是当我关闭过滤器时,原始列表将返回,所有更改都将丢失。所以我想知道是否有解决此问题的适当方法?诸如单独隐藏项目或更改项目可见性等之类的东西,因此我可以更改过滤算法并摆脱所有多余的列表。我上网搜索了整整一天的Delphi帮助文件,没有发现有用的信息。
如何在 ListBoxDrawItem 上绘制抗锯齿三角形?
ListBox.Canvas.Polygon
Run Code Online (Sandbox Code Playgroud)
绘制有锯齿。
谢谢!!!
所以我想垂直居中TListBox(非TListView)项目.
我可以使用TopIndex属性,但我如何做整件事.
如果项目较少,因此滚动条不会出现,则不需要居中,只选择默认项目就可以了.
像这样的东西:
delphi ×10
tlistbox ×10
firemonkey ×2
listbox ×2
animation ×1
antialiasing ×1
centering ×1
delphi-xe4 ×1
delphi-xe8 ×1
draw ×1
drawtext ×1
onchange ×1
onclick ×1
sorting ×1
subclass ×1
vcl ×1
winapi ×1