How to move the cursor position in the Delphi StringGrid cell?

advertisements

When you have a TStringGrid with the goEditing option set and a cell has several lines of text in it, when you go to edit that cell by clicking on it, the cursor will be at the very end of that text. How can you move the cursor to another position? My particular problem is that if the text has a carriage return at the end, the user thinks the cell is empty. I'd like to move the cursor before any carriage returns.


Assuming you are using the VCL, InplaceEditor is a property of TCustomGrid. It is of type TInplaceEdit which descents from TCustomEdit. You can move the cursor inside of it Just like a TEdit.

If you are using the automatic way of editing the content of the cell, you can use the following way to move the cursor. I have tested it and it works for me. (I am using Berlin in Windows 10)

unit Main;

interface

uses
  Winapi.Windows, Winapi.Messages, System.SysUtils, System.Variants, System.Classes, Vcl.Graphics,
  Vcl.Controls, Vcl.Forms, Vcl.Dialogs, Vcl.Grids;

const
  WM_MY_MESSAGE = WM_USER + 1;

type
  TStringGridEx = class helper for TStringGrid
  public
    function GetInplaceEditor(): TInplaceEdit;
  end;

  TForm1 = class(TForm)
    aGrid: TStringGrid;
    procedure FormCreate(Sender: TObject);
    procedure aGridGetEditText(Sender: TObject; ACol, ARow: Integer; var Value: string);
  private
    procedure OnMyMessage(var Msg: TMessage); message WM_MY_MESSAGE;
  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

procedure TForm1.aGridGetEditText(Sender: TObject; ACol, ARow: Integer; var Value: string);
begin
  PostMessage(Handle, WM_MY_MESSAGE, 0, 0);
end;

procedure TForm1.FormCreate(Sender: TObject);
var
  y: Integer;
  x: Integer;
begin
  for y := 0 to aGrid.RowCount do
  begin
    for x := 0 to aGrid.ColCount do // fill the grid
      aGrid.Cells[x, y] := Format('Col %d, Row %d'#13#10, [x, y]);
  end;
end;

procedure TForm1.OnMyMessage(var Msg: TMessage);
var
  pInplaceEdit: TInplaceEdit;
begin
  pInplaceEdit := aGrid.GetInplaceEditor();
  if Assigned(pInplaceEdit) then
  begin
    pInplaceEdit.SelStart := pInplaceEdit.EditText.TrimRight.Length;
    pInplaceEdit.SelLength := 0;
  end;
end;

{ TStringGridEx }

function TStringGridEx.GetInplaceEditor: TInplaceEdit;
begin
  Result := InplaceEditor; // get access to InplaceEditor
end;

end.

Sam