防止delphi重绘列

use*_*470 1 delphi colors

我有一个字符串网格,用户可以在其中更改列的颜色.我将颜色存储在一个字符串中,它看起来像是:columnToColor:= '1;233,233,233'1是列233; 233; 233是rgb颜色; 每次我必须改变颜色时我都会改变这个字符串.它永远不会包含多个列和一种颜色

在我的绘画中,我这样做:

color := Explode(';',columnToColor); //this will return an array
if (length(color)-1 >= 0) then
begin
  if TryStrToInt(color[0], val) then
  begin
    if aCol = StrToInt(color[0]) then
    begin
      cellText := grid.Cells[aCol,aRow];
      grid.Canvas.Brush.Color := TColor(RGB(StrToInt(color[1]),StrToInt(color[2]),StrToInt(color[3])));
      rec := grid.CellRect(aCol,aRow);
      grid.Canvas.FillRect(rec);
      grid.Canvas.TextOut(rec.Left,rec.top,cellText);
    end;
  end;
end;
Run Code Online (Sandbox Code Playgroud)

我正在使用被攻击的StringGrid类从另一个过程调用invalidateCol:

With TCustomStringGrid(grid) do
  InvalidateCol(grid.col)
Run Code Online (Sandbox Code Playgroud)

当我只更改一种列颜色时,这种方法有效.我可以自由地滚动网格,它仍然会有良好的列颜色.但是当我改变另一列的颜色时,颜色会在它们仍然可见时显示出来.一旦我水平滚动并返回列,只有最后一个彩色列被着色,其他颜色被设置为默认颜色.颜色仅保留在最后一个彩色列上.因此,如果我为2列着色并单击第一列,则单元格的颜色将设置为默认值.我水平滚动整列1设置为默认颜色.只有第二列才能保持其颜色.

我该如何解决这个问题?

Dav*_*nan 5

对我来说,这可能会变得更加清晰.问题是您希望网格控件以单独的颜色绘制每个列.虽然您的columnToColor字符串仅指定单个列的颜色,但您希望每个列可能具有不同的颜色.滚动网格并重新绘制列时,只有指定的列columnToColor具有所需的颜色.

所有这一切都在发生,因为Windows控件需要能够随时完全重新绘制自己.绘制控件后,控件不会记住其状态.如果它变为无效(控制拖动,滚动等),则控件必须能够完全重新绘制自身.

您的代码无法执行此操作.由于它只记住最近修改过的列的颜色,因此当需要绘制其他列时,它们会获得默认颜色.您的方法无法成功,因为控件仅跟踪单个列颜色.

解决方案很简单.您需要记住每列的颜色.一个显而易见的方法是将颜色保存在数组中:

FColumnColor: array of TColor;
Run Code Online (Sandbox Code Playgroud)

要么

FColumnColor: TArray<TColor>;
Run Code Online (Sandbox Code Playgroud)

在更现代的德尔福.或者甚至是TList<TColor>.

当您需要更改列的颜色时,请通过修改来实现FColumnColor[ColIndex].同样,无论何时需要绘画,都要阅读颜色FColumnColor[ColIndex].