2

OnColumnDraggedevent ofTListView具有简单的TNotifyEvent类型,因此没有直接的方法可以找到实际将哪一列拖到新位置。

如何找到已拖动的列?

4

2 回答 2

2

在插入类的帮助下,您可能会在消息处理程序中捕获HDN_ENDDRAG通知代码。WM_NOTIFY

HDN_ENDDRAG通知在lParam参数中返回结构,该结构NMHEADER包含有关被拖动的标题项的信息。这是代码示例;您也可以关注commented version帖子的:

uses
  ComCtrls, CommCtrl;

type
  TListView = class(ComCtrls.TListView)
  private
    procedure WMNotify(var AMessage: TWMNotify); message WM_NOTIFY;
  end;

implementation

{ TListView }

procedure TListView.WMNotify(var AMessage: TWMNotify);
var
  HeaderHandle: HWND;
begin
  inherited;
  if (AMessage.NMHdr^.code = HDN_ENDDRAG) then
  begin
    HeaderHandle := ListView_GetHeader(Handle);
    if (AMessage.NMHdr^.hWndFrom = HeaderHandle) then
    ShowMessage(
      'The header with index ' +
      IntToStr(TWMNotifyHC(AMessage).HDNotify^.Item) + ' ' +
      'has been dragged to the position with index ' +
      IntToStr(TWMNotifyHC(AMessage).HDNotify^.PItem^.iOrder) + '. ' +
      'Columns are not updated yet!');
  end;
end;
于 2012-08-02T10:51:50.587 回答
1

您没有任何迹象表明哪一列已被移动。确实发生的是列表视图Columns列表中的项目被重新排列以匹配列表视图中列的新顺序。只要您可以唯一地标识每一列,而不是使用列在列表中的位置,那么您就可以推断出列的顺序。

一种可能的方法是给每一列一个不同的Tag值。然后你可以做这样的事情:

procedure TForm1.ListView1ColumnDragged(Sender: TObject);
var
  i: Integer;
  s: string;
begin
  s := '';
  for i := 0 to ListView1.Columns.Count-1 do begin
    s := s + IntToStr(ListView1.Columns[i].Tag) + ' ';
  end;
  Caption := Trim(s);
end;

当然,您会想做一些比这更有用的事情,但我相信它会传达这个想法。

于 2012-08-02T10:34:41.477 回答