I have the following code (assigned to DrawGrid1.OnDrawCell event):
procedure TForm1.DrawGrid1DrawCell(Sender: TObject; ACol, ARow: Integer;
Rect: TRect; State: TGridDrawState);
begin
DrawGrid1.Canvas.Brush.Style:= bsFDiagonal;
DrawGrid1.Canvas.Brush.Color:= clSkyBlue;
DrawGrid1.Canvas.FillRect(Rect);
end;
It always draws black background even if the DrawGrid1.Color properties has been set to clRed. I also tried to change the Pen and Font properties, no luck.
What did I miss here?
ps: I have checked this code: Diagonal brush style gives me black area.
I have failed to see what is the difference between the question and the answer (apart from the commented line) and that code not working for me, as I mentioned, I already tried to change Pen properties without any result.
All I want is red background with sky blue diagonal lines.
Solved, have to add SetBKColor() before FillRect:
DrawGrid1.Canvas.Brush.Style:= bsFDiagonal;
DrawGrid1.Canvas.Brush.Color:= clSkyBlue;
SetBkColor(DrawGrid1.Canvas.Handle, ColorToRGB(clRed));
DrawGrid1.Canvas.FillRect(Rect);
I still don't know why, but it's working.
Related
I am following examples to put a checkbox in a delphi column cell. I can place a checkbox image in a cell. But the underlying boolean value is longer than the image so the checkmark is over the first two letters of "True" or "False". How can I clear the rectangle in the column cell? I tried printing the original "True" or "False" in no color, or white on white, but the text is always Black no matter what choice I make.
Sample of my code:
procedure TFUpdtLists.TreatGridDrawColumnCell(Sender: TObject;
const Rect: TRect; DataCol: Integer; Column: TColumn; State:
TGridDrawState);
begin
with Column do begin
// TreatGrid.DefaultDrawColumnCell(Rect, DataCol, Column, State); ???
if FieldName = 'Repro' then begin
Canvas.Brush.Color:= TreatGrid.Color;
Canvas.FillRect(Rect);//fails to clear cell, clears another area??
if Field.Value = True then
//#7 a checkmark and # 5 a blank image in the image list:
MainView.ImageList1.Draw(TreatGrid.Canvas,Rect.Left,Rect.Top,7)
else
MainView.ImageList1.Draw(TreatGrid.Canvas,Rect.Left,Rect.Top,5);
TreatGrid.DefaultDrawColumnCell(Rect, DataCol, Column, State);//??
end;
end;
end;
Thanks in advance!
Pay attention to the Canvas you refer to in the code when you paint the background. Since there is no argument called Canvas and also Column doesn't have a Canvas it refers to the Canvas of the TFUpdtLists executing the code.
You have already corrected the code for the mageList1.Draw() methods and added the grids reference (TreatGrid). Do the same for the bg painting.
It appears you have tried calling DefaultDrawColumnCell() in different ways, but you should call it only for the columns that you don't draw yourself.
Let me also suggest that you quit using with ... because it prevents code completion from working and it makes debugging harder as well as increases significantly the risc of coding errors.
With the above mentioned changes the OnDrawColumnCell() procedure looks like this;
procedure TForm19.TreatGridDrawColumnCell(Sender: TObject; const Rect: TRect;
DataCol: Integer; Column: TColumn; State: TGridDrawState);
begin
if Column.FieldName = 'Repro' then
begin
TreatGrid.Canvas.Brush.Color:= TreatGrid.Color;
TreatGrid.Canvas.FillRect(Rect);
if Column.Field.Value then
//#7 a checkmark and # 5 a blank image in the image list:
Form19.ImageList1.Draw(TreatGrid.Canvas,Rect.Left,Rect.Top,1)
else
Form19.ImageList1.Draw(TreatGrid.Canvas,Rect.Left,Rect.Top,0);
end
else
TreatGrid.DefaultDrawColumnCell(Rect, DataCol, Column, State);
end;
You will want to correct the image indexes, which I changed to suit my imagelist in my test.
FillRect doesn't paint the complete TStringGrid cell in Delphi XE2. There is a gap of 3 pixels on the left side in the default color (with BiDiMode set to bdLeftToRight). This problem doesn't exist in Delphi 6 which I used before.
procedure TShapeline.StringGrid1DrawCell(Sender: TObject; ACol, ARow: Integer;
Rect: TRect; State: TGridDrawState);
begin
Stringgrid1.Canvas.Brush.Color:=$00FF80FF;
StringGrid1.Canvas.FillRect(Rect);
end;
I tried to change all properties (including the DrawingStyle) and different brush styles, the painted rectangle doesn't fill the complete cell.
This is expected behaviour in XE2 when DefaultDrawing = true and themes are enabled (I'm not going to argue about good or bad here - as you might have noticed, the behaviour is different for RigthToLeft mode...).
A workaround is to check for this condition and decrement Rect.Left by 4 pixel before calling FillRect.
You can use the StringGrid1.CellRect(ACol, ARow) that returns the actual TRect of the cell instead of using the parameter Rect.
Turn off the first 4 options in TStringGrid:
goFixedVertLine
goFixedHorizLine
goVertLine
goHorizLine
Then it won't paint the grid lines, and your grid cells will paint right to the edges. Just tried it with XE.
Since you're drawing the grid cell yourself then just turn off the grid property DefaultDrawing, set it to false.
Since XE2, there are several themes that can be used for your application. E.g. Carbon that changes the background color of the TListView to gray besides other things.
Is there any way to get this color?
TListView.Color returns white altough the background is some kind of gray.
I tried using StyleServices.GetElementDetails with a snippet like this:
var lColor: TColor;
lDetails: TThemedElementDetails;
if StyleServices.Enabled then
begin
lDetails := StyleServices.GetElementDetails(tlListviewRoot);
StyleServices.GetElementColor(lDetails, ecFillColor, lColor);
end;
But GetElementColorfails and returns false. Am I using the wrong parameter? Or is my approach just wrong.
The possible parameters can be found here:
TThemedListView
TElementColor
Thank you.
P.S.: I also read this post but the answer didn't help me so far.
To get the background color of the TListView that has a StyleHook implemented :
uses Vcl.Themes;
var Color : TColor;
Color := StyleServices.GetStyleColor(scListView);
I want to extend DbGrid functionality to add colors on odd and even rows. So i wrote this
procedure TGridx.DrawCell(ACol, ARow: Longint; ARect: TRect; AState: TGridDrawState);
var
row : Integer;
begin
inherited;
row := Self.DataSource.DataSet.RecNo;
if (row mod 2 = 0) then
Self.Canvas.Brush.Color := FColor1 //some color
else
Self.Canvas.Brush.Color := FColor2; //some color
end;
What i am doing wrong ?
The event you want is called DBGridDrawColumnCell, and you need to decide whether to turn the DefaultDrawing property on or off, and the way you handle DBGridDrawColumnCell changes accordingly. For your case, you just set the colors, but leave DefaultDrawing true, and don't do any other canvas.Text or GDI drawing.
A recent question I asked here showed that in later Delphi versions (2010,Xe,Xe2) you ALSO sometimes need to call Canvas.Refresh for both TDBGRID and TListView, when changing canvas properties in ownerdraw events but that doesn't apply to delphi 7.
you should try also 3d party solution which are free, and extends already a lot the DBGrid, like the ones provided by the Jedi project
Opc0de, may be you should override not the "DrawCell" method but "DrawCellBackground"?
Try drawing the cell as well after the brush color is defined:
Self.Canvas.FillRect(ARect);
I have taken the advice, or at least I think I have, that I got in my previous question.
To summarize, I replaced the THTMLTreeList from TMS with a TTreeList and made two columns in it. I set the first column to 150 pixels and I overrode the AdvancedCustomDrawItem event with this code:
procedure TForm1.trXMLAdvancedCustomDrawItem(Sender: TCustomTreeView;
Node: TTreeNode; State: TCustomDrawState; Stage: TCustomDrawStage;
var PaintImages, DefaultDraw: Boolean);
var hContext: HDC;
s: PChar;
iLength: Integer;
uRect: TRect;
begin
DefaultDraw := False;
hContext := trXML.Canvas.Handle;
s := PChar(Node.Text);
iLength := Length(Node.Text);
uRect := Node.DisplayRect(True);
DrawText(hContext, s, iLength, uRect, DT_END_ELLIPSIS);
end;
I got the result I expected, that is, when I draw the tree, the text in the first column is clipped. And when I change the size of the first column, the text is appropriately clipped. But when the TreeList is not wide enough and has a scroll bar on the bottom and I scroll to the right, the text now extends into the second column by the same amount as the scroll bar has been moved. It's like the text is drawn relative to the client area of the TreeList rather than the partially hidden first column so it always extends 150 pixels into the TreeList.
It seems to me that I am using the wrong thing for the device context handle or the TRect but I do very little graphic type programming so I don't know what to change. Any help would be appreciated.
I just checked TMS's source code and
TTreeList already uses the DT_END_ELLIPSIS flag
and does per-column clipping of drawn text when the DefaultDraw parameter is set to True, so you don't need to draw the text yourself manually.