我有一个stringgrid,显示了一堆文件和有关这些文件的信息。在单独的面板中显示有关当前所选项目的更多信息。所以,我想知道所选行何时更改以更新面板。 OnSelectCell并不好,因为它会在选择实际移动到新位置之前触发。这就是我的意思:
function TStrGrd.SelectCell(ACol, ARow: Longint): Boolean; {override}
begin
Result:= inherited SelectCell(ACol, ARow);
Mesage('Cur row: '+ IntToStr(row));
Mesage('New row: '+ IntToStr(ARow));
{ My own event }
if Assigned(FCursorChanged)
then FCursorChanged(Self); <-------- user will see the old row
end;
如果选择了最后一行,我单击第一行,我将收到以下消息:
Cur row: 999
New row: 0
如果我创建自己的事件处理程序并将选择即将移动的行传递给它,它将起作用。它应该100%工作,但我对此不太满意,因为用户必须在该事件处理程序中编写一些额外的代码。
我可以拦截所有用户交互(鼠标/按键)以及我以编程方式进行的所有选择更改,但这需要相当多的代码。应该有一个更优雅的方式。
答案 0 :(得分:1)
不是答案。只需将其发布为多行文字。
我认为你的意思是“更新面板”而不是“关于”: - )
仍然无法解决ROW参数的问题。你说“用户必须在该事件处理程序中编写一些额外的代码。”但实际上恰恰相反。
procedure ParamEvent(const grid: TStringGrid; const Row: integer);
begin
..do something with grid.Rows[Row] to update the panel
// ...and if I need, I also already know which Row was selected beforehand!
end;
procedure ParamLessEvent();
var grid: TStringGrid; Row: integer; // <<<<< EXTRA "coding" here
begin
grid := ..... some way to get the needed grid // <<<<< EXTRA coding here
Row := grid.Row; // <<<<< EXTRA coding here
...do something with grid.Rows[Row] to update the panel
// ...and if I would want to know which file just was DE-selected,
// I would have to code persisting of previous selected row
// number somewhere outside the grid
end;
现在,真的,为什么不使用PostMessage?
const WM_Grid_Event = WM_USER + 123; // I hope it is correct? I always mix wm_user and wm_app
type TMyGrid = class (TStringGrid)
....
private
procedure DelayedEvent(var MSG: TMessage); message WM_Grid_Event;
end;
function TMyGrid.SelectCell(ACol, ARow: Longint): Boolean; {override}
begin
Result:= inherited SelectCell(ACol, ARow);
Mesage('Cur row: '+ IntToStr(row));
Mesage('New row: '+ IntToStr(ARow));
PostMessage( Self.Handle, WM_Grid_Event, ARow, 0);
end;
procedure DelayedEvent(var MSG: TMessage);
begin
{ My own event }
if not Assigned(FCursorChanged) then exit;
if Self.Row = MSG.WParam (* changed already? *) then begin
FCursorChanged(Self);
end else begin
if MSG.LParam < 5 then // protection from infinite loop. OTOH I hope we would not EVER got here
PostMessage( Self.Handle, WM_Grid_Event, MSG.WParam, 1 + MSG.LParam);
end;
end;