TListItem.Checked 在 Assign() 之后将自身切换为 True

TListItem.Checked switches itself to True after Assign()

我遇到了 TListItem 的一些意外行为。检查以下测试代码:

  var
  Item: TListItem;

  //...

  ListView1.Checkboxes := True;
  with ListView1.Items.Add do
  begin
    Caption := 'old item';
    Checked := False;
  end;

  Item := TListItem.Create(ListView1.Items);
  Item.Caption := 'new item';
  Item.Checked := False;

  ListView1.Items[0].Assign(Item);

  Assert(ListView1.Items[0].Caption = 'new item');
  Assert(ListView1.Items[0].Checked = False); //WTF

发生断言失败,因为 Checked 属性 以某种方式将自身切换为 True。我在帮助文件中没有找到关于此行为的任何评论。

这是错误还是功能?

我正在使用 Delphi 7 进行所有更新。

Delphi自带VCL源码。在 ComCtrls.pas 中查找 TListItemTListView.

的实现

如果您在项目选项中启用 "Use debug DCUs",然后使用调试器单步执行 TListItem 源代码,您会确切地 看到什么是发生。 Item.Checked := False 失败,读取 Item.Checked 总是 returns True,因为 Item.Index 是 -1(因为你绕过了 TListItems.Add())。

TListItem.GetChecked() getter 方法不处理 ListView_GetCheckState() 宏(它是 LVM_GETITEMSTATE 消息的包装器)由于被传递而失败的可能性无效的项目索引。

手动创建 TListItem 对象不足以将项目添加到基础 Win32 ListView 控件。如果您通过 TListItems.Add()TLisItem.Insert() 以外的方式创建 TListItem,则必须调用 TListItems.AddItem()TListitem 插入基础 ListView 控件。