change colors of some rows in dbgrid delphi 5 - delphi-5

I have a problem, I have an TStringList object with some numbers and his status in some kind of json text I created, like: {'8987436','Sin documentar.', '0','1'}, {...},...
This file can contain a lot of groups of data. This works really fine, this information I displayed in a DBGrid, only the numbers.
The problem is that when I try to change the color of the rows, only draw the color of the last number added to the dbgrid, and I need that each row with some type of number draw in yellow, other kind in red, other kind in green and all the other let it white. The other problem is that when I click on one row it refresh the dbgrid and paint it again in white.
I created this procedure:
procedure TEmbarqueGeneracionEscaneoFRM.DBValidasDrawColumnCell(
Sender: TObject; const Rect: TRect; DataCol: Integer; Column: TColumn;
State: TGridDrawState);
begin
inherited;
if Pinta then
begin
with (Sender As TDBGrid).Canvas do
begin
brush.Color:=GridColor;
FillRect(Rect);
TextOut(Rect.Left, Rect.Top, Column.Field.AsString);
end;
TDBGrid(sender).DefaultDrawColumnCell(Rect, Datacol, Column, State);
end;
Pinta := false;
end;
Where Pinta is a variable that tell if the number was painted, and GridColor is a TColor variable with the color that will be drawn.
Did you have any idea?
Regards

Related

How to get values of cells in tmsfmxlivegrid hidden columns?

i want to change text color cells in specific column basing on values of other cells in other column using the GetCellLayout event like this.
procedure TForm1.TMSFMXLiveGrid1GetCellLayout(Sender: TObject;
ACol, ARow: Integer; ALayout: TTMSFMXGridCellLayout; ACellState: TCellState);
begin
if ACol = 1 then
if TMSFMXLiveGrid1.Cells[5, ARow] <> '' then
ALayout.FontFill.Color := TAlphaColorRec.Red;
end;
the problem is that when the column 5 is not visible in the screen area(you must scroll to see it) the color still black instead of red, because the column 5 is not loaded;
NB:the grid is binded to a dataset.

delphi dbgrid drawing cell image black background

Problem using image from a TImage list to draw a glyph on to a data cell in DBGrid:
I am putting a bmp image of a "checkmark" in place of the text "Done" in a particular data cell. It works, but there is always black color in the parts of the cell not covered by the image. I have tried enlarging the pixel size of the bmp image to match the cell size, but it always seems to resize the image for me. Using Delphi 10.2, was not problem in D7?
Have tried many combos of setting background colors, pen and brush colors, etc. Here is a simple example of one code attempt:
procedure TFUpRepWS.DBGrid1DrawColumnCell(Sender: TObject; const Rect: TRect;
DataCol: Integer; Column: TColumn; State: TGridDrawState);
begin
with Column do begin
if ((FieldName = 'Done') and (Field.AsString = 'x')) then begin
//below shows black outside of check mark image in the cell
ImageList1.Draw(DBGrid1.Canvas,Rect.Left,Rect.Top,0)
end
else DBGrid1.DefaultDrawColumnCell(Rect,DataCol,Column,State);
end;
end;
Do the default cell painting DefaultDrawColumnCell always. That will ensure the cell will look like the others. Then draw the image. Try this:
procedure TFUpRepWS.DBGrid1DrawColumnCell(Sender: TObject; const Rect: TRect;
DataCol: Integer; Column: TColumn; State: TGridDrawState);
begin
with Column do
begin
DBGrid1.DefaultDrawColumnCell(Rect, DataCol, Column, State);
if ((FieldName = 'Done') and (Field.AsString = 'x')) then
ImageList1.Draw(DBGrid1.Canvas, Rect.Left, Rect.Top, 0);
end;
end;
I guess that what you described happens because there is no code that paints the cell background.

How to highlight a DBGrid cell?

I'm trying to programatically highlight the current cell in a TDBGrid descendant. If I do DBGrid.SetFocus, I get the combo box arrow below, which isn't sufficiently highlighted for me.
EDIT:
I'm already doing DBGrid.SelectedField := DataSource.FieldByName('Name');
To bring the user's attention more to the region in question, I set:
DBGrid.Columns[x].Title.Font.Style := [fsbold, fsunderline];
And I set a timer that after five seconds does:
DBGrid.Columns[x].Title.Font.Style := [];
What's weird is that after the time goes off, the cell becomes blue (as shown below.) That's the highlight I wanted in the first place. But I don't know enough about grids to know how to get that directly.
My question: how to I get a grid cell highlighted as in the blue example below? I've never done anything like this before, so I'm a bit lost. Is this an InPlaceEditor function?
I'm using a descendant of TDBGrid, so I'm not sure if the behavior I'm seeing is intrinsic to TDBGrid, or just in the descendant (in which case I know my question can't be answered here. )
I've been using the following (D2007) using the DBGrid: OnDrawColumnCell event.
procedure TForm1.DBGridDrawColumnCell(Sender: TObject;
const Rect: TRect; DataCol: Integer; Column: TColumn; State: TGridDrawState);
begin
//Make the column blue if the title is bold
if (fsBold in Column.Title.Font.Style) then
TDBGrid(Sender).Canvas.Brush.Color := $00fff0e1;
//Set the selected row to white/bold text on blue background
if (gdSelected in State) then
begin
TDBGrid(Sender).Canvas.Brush.Color := clHighlight;
TDBGrid(Sender).Canvas.Font.Style := Font.Style + [fsBold];
TDBGrid(Sender).Canvas.Font.Color := clHighlightText;
end;
//Update the grid
TDBGrid(Sender).DefaultDrawColumnCell(Rect, DataCol, Column, State);
end;

With TMS TDBAdvGrid, how to color lines with different colors depending on cell values?

All is in the title.
How can we also make an officehint customisable for each row. Mean when mousemove on a row, display the information of this record (from a db query).
Thanks
You can color individual cells using the CellProperties property of the grid. You can use this to color an entire row:
var
RowIndex: Integer;
ColIndex: Integer;
with MyDBAdvGrid do
begin
// you choose the row index; you may want to iterate all rows to
// color each of them
RowIndex := 2;
// now iterate all (non-fixed, visible) cells in the row and color each cell
for ColIndex := FixedCols to ColCount - 1 do
begin
CellProperties[ColIndex, RowIndex].BrushColor := clYellow;
CellProperties[ColIndex, RowIndex].FontColor := clGreen;
end;
end;
To fill your office hint with record data I would suggest updating it when the user moves the mouse. Use the MouseToCell function to get row and column under the mouse, then use MyDBAdvGrid.AllCells[ColIndex, RowIndex] to access the cell content.
An Alternative to Heinrich answer is to use the OnGetCellColor event.
This can be use like so:
procedure TDBAdvGrid.DBGridGetCellColor(Sender: TObject; ARow,
ACol: Integer; AState: TGridDrawState; ABrush: TBrush; AFont: TFont);
begin
if (your condition) then ABrush.Color := clRed;
end;
Similarly for the hint:
procedure TDBAdvGrid.DBGridGridHint(Sender: TObject; ARow, ACol: Integer;
var hintstr: String);
begin
hintstr := 'your hint text';
end;

Setting background color of selected row on TStringGrid

I have a TStringGrid where the selected row (max 1, no multi-select) should always have a different background colo(u)r.
I set the DefaultDrawing property to false, and provide a method for the OnDrawCell event, shown below - but it is not working. I can't even describe exactly how it is not working; I supect that if I could I would already have solved the problem. Suffice it to say that instead of having complete rows all with the same background colour it is a mish-mash. Muliple rows have some cells of the "Selected" colour and not all cells of the cselected row have the selected colour.
Note that I compare the cell's row with the strnggrid's row; I can't check the cell state for selected since only cell of the selected row is selected.
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;
if you are trying of paint the selected row or cell with a different color you must check for the gdSelected value in the state var.
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;
Do you have run-time themes enabled? Run-time themes override any colour scheme you try to enforce for Windows Vista and up.
When a new cell is selected in a stringgrid only the previous and the new selected cell are invalidated. Thus the remaining cells of the previous and new row are not redrawn, giving the effect you describe.
One workaround would be to call InvalidateRow for both affected rows, but this is a protected method and you have to find a way to reach this method from an OnSelectCell event handler. Depending on your Delphi version there are different ways to accomplish that.
The cleanest way would be to derive from TStringGrid, but in most cases this is not feasible. With a newer Delphi version you can use a class helper to achieve this. Otherwise you have to rely on the usual protected hack.
This works for me
procedure TFmain.yourStringGrid(Sender: TObject; ACol, ARow: Integer; Rect: TRect;
State: TGridDrawState);
var
md: integer;
begin
with yourStringGrid do
begin
if yourStringGrid,Row = ARow then
Canvas.Brush.Color:= clYellow //your highlighted color
else begin
md := Arow mod 2;
if md <> 0 then Canvas.Brush.Color:= $00BADCC1 else //your alternate color
Canvas.Brush.Color:= clwhite;
end;
Canvas.FillRect(Rect);
Canvas.TextOut(L, Rect.top + 4, cells[ACol, ARow]);
end;
end;
Refresh the grid
procedure TFmain.yourStringGridClick(Sender: TObject);
begin
yourStringGrid.Refresh;
end;
Note: Has a little latency, but otherwise works great.
(Used in Delphi XE2)

Resources