Message handlers are methods, and they therefore must be declared and implemented within the same unit as the class they belong to.
That doesn't stop you from delegating the real work to some other function in another unit, though. There's nothing special about message handlers in that regard. Declare whatever function you like, and pass it whatever parameters it will need in order to accomplish its duties. If all it needs are the contents of the TMessage
record, then so be it. However, it will probably also need to know what form received the message, so pass a reference to that, too. Or maybe it just needs to know the values of some of the form's private fields, so pass those instead.
You could make a unit for handling messages. Its interface section could look like this:
unit MessageHandlers;
interface
uses OtherUnit;
procedure HandleWMInput(Form: FOtherUnit; var Message: TWMInput);
There's nothing to designate that function as handling wm_Input
messages; the message
directive is only for classes.
Then, the implementation section of your form's unit can use that unit and call its functions:
uses MessageHandlers;
procedure FOtherForm.WMInput(var Message: TWMInput);
begin
HandleWMInput(Self, Message);
end;
I've used TWMInput
instead of TMessage
. If Delphi doesn't already declare that type for you (in Messages.pas), then I suggest you declare it yourself. It lets Delphi perform the message-parameter cracking for you. For example, with the declaration below, the raw-input handle has a better type and name than the corresponding field in TMessage
.
type
TWMInput = packed record
Msg: Cardinal;
InputCode: Byte;
Unused: array[0..2] of Byte;
RawInput: HRawInput;
Result: LongInt;
end;