0

I have altered a D6 stringgrid to allow for left or right justified checkboxes to be displayed in the grid cells. When the stock inplace editor is called the edit box for receiving data starts at the beginning of the cell and its width covers the entire width of the cell (ie it fills the cell completely covering my checkboxes until repainted). How can I implement my own inplace editor and control the starting location of the editor and its width? Thanks in advance to all. Bill

Bill
  • 5
  • 3
  • sifu I started looking into grids.pas and found whgetdialogcode, updatecontents, validate/invalidaterect, etc but could not pick out how the dimensions of the selected cell were being fed to a procedure for formatting the edit box; – Bill Aug 11 '14 at 19:36

1 Answers1

1

TStringGrid does not natively support what you are asking for. The coordinates of the inplace editor are fixed to the entire cell bounds, as it was never designed to take user-defined cell controls into account.

When TStringGrid positions the editor, it calls CellRect() (which is not virtual) and passes the returned TRect to TInplaceEdit.Move() (which is not virtual), which calls TInplaceEditor.InternalMove() (which is private) to move the editor HWND to the specified coordinates and size using the Win32 API SetWindowPos() function.

The only way you will be able to change that logic is to either:

  1. make a copy of Grids.pas and alter TStringGrid's source code, then add the modified file to your project (this only works if Runtime Packages are disabled).

  2. use a hook/detour to redirect TInplaceEdit.Move() to a custom method where you can alter the content of the TRect before passing it to the original implementation.

Update: now that I think more about it, you might be able to derive a class from TInplaceEdit and override its virtual WndProc() method to calculate different position/size information when asked by the WM_GETMINMAXINFO or WM_WINDOWPOSCHANGING message. Or override its virtual BoundsChanged() method to reposition/resize the editor after the grid has positioned/sized the editor where it wants. Either way, you can override the virtual TStringGrid.CreateEditor() method to make the grid create an instance of your editor class.

Remy Lebeau
  • 555,201
  • 31
  • 458
  • 770
  • Remy. Not sure how to conduct a hook/detour of TInplaceEdit.Move. – Bill Aug 11 '14 at 19:43
  • Can you explain? Is this just a cracker class and override of the Move procedure? – Bill Aug 11 '14 at 19:45
  • Remy InplaceEdit.Move is only called by TCustomGrid.UpdateEdit. Would my solution be to cracker class TCustomGrid AND TStringGrid and override the UpdateEdit of the TCustomGrid cracker class to feed the overridden coordinates of my desired TRect edit box downstream? – Bill Aug 11 '14 at 20:01
  • 1
    A cracker class will not work. `UpdateEdit()` is not virtual, so you cannot override it. And `Move()` is called on a `TInplaceEdit` variable, and `Move()` is not virtual either. No, the only way to redirect `Move()` is to use a lower-level VMT hook or detour. – Remy Lebeau Aug 11 '14 at 20:45
  • Remy Thank you for taking the time to explain. I will try your #1 suggestion above about copying Grids.pas and modifying for my needs then come back and look later at #2 just for giggles. Bill – Bill Aug 11 '14 at 20:54