user3140961
user3140961

Reputation:

Delphi : Avoid editing a column in TDBgrid

I know that using a column's readonly property, i can avoid editing its field value. But this doesn't stop the inplace editor to show itself. I need a way to make the column not only protected but "untouchable". Is there a way, please ?

Upvotes: 2

Views: 3494

Answers (1)

MartynA
MartynA

Reputation: 30715

If I understand what you want correctly, you can do this quite simply, by creating a custom TDBGrid descendant and overriding its CanEditShow method, as this determines whether the grid's InplaceEditor can be created:

type
  TMyDBGrid = class(TDBGrid)
  private
    FROColumn: Integer;
  protected
    function CanEditShow : Boolean; override;
  public
    property ROColumn : Integer read FROColumn write FROColumn;
  end;

function TMyDBGrid.CanEditShow: Boolean;
begin
  Result := Inherited CanEditShow;
  Result := Result and (Col <> ROColumn);
end;

procedure TForm1.FormCreate(Sender: TObject);
begin
  MyDBGrid := TMyDBGrid.Create(Self);
  MyDBGrid.ROColumn := 1;
  MyDBGrid.DataSource := DataSource1;
  MyDBGrid.Parent := Self;
[...]

This minimalist example just defines one grid column by number as being one where the InplaceEditor is not permitted; obviously you could use any mechanism you like to identify the column(s) for which CanEditShow returns False.

Note that the code above doesn't account for the fact that the column numbering of the grid changes if you turn off the Indicator column (i.e. set Options.dgIndicator to False);

Obviously, you get more flexibility for customizing which columns are permitted an InplaceEditor by using an assignable event as in

type

  TAllowGridEditEvent = procedure(Sender : TObject; var AllowEdit : Boolean) of object;

  TMyDBGrid = class(TDBGrid)
  private
    FOnAllowEdit: TAllowGridEditEvent;
  protected
    function CanEditShow : Boolean; override;
    procedure DoAllowEdit(var AllowEdit : Boolean);
  public
    property OnAllowEdit : TAllowGridEditEvent read FOnAllowEdit write FOnAllowEdit;
  end;

function TMyDBGrid.CanEditShow: Boolean;
begin
  Result := Inherited CanEditShow;
  if Result then
    DoAllowEdit(Result);
end;

procedure TMyDBGrid.DoAllowEdit(var AllowEdit: Boolean);
begin
  if Assigned(FOnAllowEdit) then
    FOnAllowEdit(Self, AllowEdit);
end;

procedure TForm1.AllowEdit(Sender: TObject; var AllowEdit: Boolean);
var
  Grid : TMyDBGrid;
begin
  Grid := Sender as TMyDBGrid;
  AllowEdit := Grid.Col <> 1;
end;

procedure TForm1.FormCreate(Sender: TObject);
begin
  MyDBGrid := TMyDBGrid.Create(Self);
  MyDBGrid.ROColumn := 1;
  MyDBGrid.DataSource := DataSource1;
  MyDBGrid.Parent := Self;
  MyDBGrid.OnAllowEdit := AllowEdit;
  [...]

If you don't like creating the grid in code, you could put it in a custom package and install it in the IDE or, if your Delphi version is recent enough, implement the CanEditShow in a class helper.

Upvotes: 1

Related Questions