3

選択された行 (最大 1、複数選択なし) が常に異なる背景色 (u)r を持つ必要がある TStringGrid があります。

DefaultDrawing プロパティを false に設定し、以下に示す OnDrawCell イベントのメソッドを提供しましたが、機能しません。それがどのように機能していないかを正確に説明することさえできません。できれば、すでに問題を解決していると思います。すべて同じ背景色の完全な行を持つ代わりに、それはごちゃまぜであると言えば十分です。複数の行には「選択された」色のセルがいくつかあり、選択された行のすべてのセルが選択された色を持つわけではありません。

セルの行を strnggrid の行と比較していることに注意してください。選択した行のセルのみが選択されているため、選択したセルの状態を確認できません。

procedure TForm1.DatabaseNamesStringGridDrawCell(Sender: TObject;
                                                 ACol, ARow: Integer;
                                                 Rect: TRect;
                                                 State: TGridDrawState);

  var cellText :String;
begin
   if gdFixed in State then
      DatabaseNamesStringGrid.Canvas.Brush.Color := clBtnFace
   else
   if ARow = DatabaseNamesStringGrid.Row then
      DatabaseNamesStringGrid.Canvas.Brush.Color := clAqua
   else
      DatabaseNamesStringGrid.Canvas.Brush.Color := clWhite;

   DatabaseNamesStringGrid.Canvas.FillRect(Rect);
   cellText := DatabaseNamesStringGrid.Cells[ACol, ARow];
   DatabaseNamesStringGrid.Canvas.TextOut(Rect.Left + 2, Rect.Top + 2, cellText);
end;
4

4 に答える 4

6

選択した行またはセルを別の色でペイントしようとしているgdSelected場合は、変数の値を確認する必要がありますstate

procedure TForm1.DatabaseNamesStringGridDrawCell(Sender: TObject;
                                                 ACol, ARow: Integer;
                                                 Rect: TRect;
                                                 State: TGridDrawState);
var
  AGrid : TStringGrid;
begin
   AGrid:=TStringGrid(Sender);

   if gdFixed in State then //if is fixed use the clBtnFace color
      AGrid.Canvas.Brush.Color := clBtnFace
   else
   if gdSelected in State then //if is selected use the clAqua color
      AGrid.Canvas.Brush.Color := clAqua
   else
      AGrid.Canvas.Brush.Color := clWindow;

   AGrid.Canvas.FillRect(Rect);
   AGrid.Canvas.TextOut(Rect.Left + 2, Rect.Top + 2, AGrid.Cells[ACol, ARow]);
end;
于 2011-04-07T05:06:53.677 に答える
2

stringgrid で新しいセルが選択されると、以前に選択されたセルと新しく選択されたセルのみが無効になります。したがって、前の行と新しい行の残りのセルは再描画されず、説明した効果が得られます。

1 つの回避策は、影響を受ける両方の行に対して InvalidateRow を呼び出すことですが、これは保護されたメソッドであり、OnSelectCell イベント ハンドラーからこのメソッドに到達する方法を見つける必要があります。Delphi のバージョンに応じて、それを実現するさまざまな方法があります。

最もクリーンな方法は TStringGrid から派生させることですが、ほとんどの場合、これは実行できません。Delphi の新しいバージョンでは、クラス ヘルパーを使用してこれを実現できます。それ以外の場合は、通常の保護されたハックに頼る必要があります。

于 2011-04-07T08:45:55.237 に答える
2

ランタイム テーマを有効にしていますか? ランタイム テーマは、Windows Vista 以降で強制しようとするすべての配色をオーバーライドします。

于 2011-04-07T04:02:43.257 に答える