How to automate row size in TVirtualStringTree?

I have a simple VirtualStringTree (VST) example with 4 columns, and in the second or third column I can have more text corresponding to the default column width. I have hoAutoSpanColumns , so the large text will overlap other columns if they are empty. It works well. The problem is that the text in the second or third column should cover the entire length of the VST. In this case, large columns extend only to the end of the last (fourth) column.

Here's how the 2nd column in row 3 covers only the 3rd and 4th columns, and then stops at the width of the 4th column:

enter image description here

If I use AutoFitColumns to automatically size the second column:

VST1.Header.AutoFitColumns(false, smaUseColumnOption,1,1);

3- 4- , :

enter image description here

, 3- 4- , :

enter image description here

2- , 3- 4- , ?

+4
1

. , , ( node). , VT RTL- ( ):

type
  TVirtualStringTree = class(VirtualTrees.TVirtualStringTree)
  protected
    function GetSpanColumn(Node: PVirtualNode): TColumnIndex; virtual;
  public
    procedure AutoFitSpanColumn(DestColumn: TColumnIndex; Node: PVirtualNode);
  end;

implementation

{ TVirtualStringTree }

function TVirtualStringTree.GetSpanColumn(Node: PVirtualNode): TColumnIndex;
begin
  { this returns visible span column for the given node, InvalidColumn otherwise }
  Result := Header.Columns.GetLastVisibleColumn;
  while ColumnIsEmpty(Node, Result) and (Result <> InvalidColumn) do
    Result := Header.Columns.GetPreviousVisibleColumn(Result);
end;

procedure TVirtualStringTree.AutoFitSpanColumn(DestColumn: TColumnIndex; Node: PVirtualNode);
var
  ColsWidth: Integer;
  SpanWidth: Integer;
  SpanOffset: Integer;
  SpanColumn: TColumnIndex;
begin
  SpanColumn := GetSpanColumn(Node);

  if SpanColumn <> InvalidColumn then
  begin
    { get the total width of the header }
    ColsWidth := Header.Columns.TotalWidth;
    { get the width of the span text cell as it would be autosized }
    SpanWidth := DoGetNodeWidth(Node, SpanColumn) + DoGetNodeExtraWidth(Node, SpanColumn) +
      DoGetCellContentMargin(Node, SpanColumn).X + Margin;
    { and get the left position of the span cell column in header }
    SpanOffset := Header.Columns[SpanColumn].GetRect.Left;
    { now, the width of the autosized column we increase by the subtraction of the fully
      visible span cell width and all columns width increased by offset of the span cell
      column; in other words, we'll just increase or decrease width of the DestColumn to
      the difference of width needed for the span column to be fully visible, or "fit" }
    Header.Columns[DestColumn].Width := Header.Columns[DestColumn].Width +
      SpanWidth - ColsWidth + SpanOffset;
  end;
end;
+3

Source: https://habr.com/ru/post/1686081/


All Articles