Если вы не хотите вносить какие-либо изменения в TForm-производный класс, почему бы не попробовать чистый способ Windows API для реализации вашего текущего решения, то есть использовать SetWindowLongPtr () для перехвата WM_INITMENUPOPUP
сообщение.Стиль Delphi VCL для перехвата сообщений на самом деле является просто оболочкой этой функции Windows API.
Для этой цели используйте SetWindowLongPtr()
, чтобы установить новый адрес для оконной процедуры и получитьоригинальный адрес оконной процедуры, как одним ударом.Не забудьте сохранить исходный адрес в переменной LONG_PTR
.В 32-битном Delphi LONG_PTR
был Longint
;предположим, что 64-bit Delphi будет выпущен в будущем, LONG_PTR
должно быть Int64
;вы можете использовать директиву $IFDEF
, чтобы различать их следующим образом:
Type
{$IFDEF WIN32}
PtrInt = Longint;
{$ELSE}
PtrInt = Int64;
{$ENDIF}
LONG_PTR = PtrInt;
Значение параметра nIndex
, которое будет использоваться для этой цели, - GWLP_WNDPROC
.Также передайте новый адрес для оконной процедуры в параметр dwNewLong
, например, LONG_PTR(NewWndProc)
.NewWndProc
- это функция обратного вызова WindowProc , которая обрабатывает сообщения, именно здесь вы устанавливаете критерии перехвата и переопределяете обработку сообщения, которое вы собираетесь перехватить, по умолчанию.Функция обратного вызова может быть любым именем, но параметры должны соответствовать соглашению WindowProc .
Обратите внимание, что необходимо вызвать CallWindowProc () , чтобы передать любые сообщения, не обработанныеновая оконная процедура к исходной оконной процедуре.
Наконец, вам нужно снова вызвать SetWindowLongPtr()
где-нибудь в вашем коде, чтобы установить адрес обработчика модифицированной / новой оконной процедуры обратно в исходныйадрес.Первоначальный адрес был сохранен ранее, как указано выше.
Здесь был пример кода Delphi .Он использовал SetWindowLong()
, но теперь Microsoft рекомендует использовать SetWindowLongPtr()
вместо этого, чтобы сделать его совместимым как с 32-битной, так и с 64-битной версиями Windows.
SetWindowLongPtr()
не существовало в Windows.pas
Delphi до Delphi 2009. Если вы используете более старую версию Delphi, вы должны объявить ее самостоятельно или использовать JwaWinUser
единицу JEDI API Library .