Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    primarykey
    data
    text
    <p>Unlike VCL, FireMonkey does not dispatch raw window messages to FMX controls for custom processing (that would defeat the purpose of a cross-platform framework). FireMonkey has a single <code>WndProc()</code> function implemented in the <code>FMX.Platform.Win</code> unit that is used for all <code>HWND</code> windows that FireMonkey creates. That implementation processes certain window messages that it needs to process, triggering various control methods accordingly (<code>WMPaint()</code>, <code>KeyUp/Down()</code>, <code>MouseUp/Down()</code>, etc), and then passes unprocessed messages directly to <code>DefWindowProc()</code> for OS processing, without letting controls see the messages at all.</p> <p>So, the only way you are going to gain access to the raw messages is to either:</p> <ol> <li><p>create your own windows, such as with <code>AllocateHWnd()</code>, or <code>CreateWindow/Ex()</code> directly.</p></li> <li><p>hook into FireMonkey's <code>HWND</code> windows directly via <code>Get/SetWindowLong/Ptr()</code>. Since FireMonkey is a cross-platform framework, and <code>HWND</code> windows are a platform-specific implementation detail, I would suggest avoiding this approach.</p></li> <li><p>use thread-specific message hooks via <code>SetWindowsHookEx()</code>. By making them thread-specific, you avoid having to write a DLL to implement the hook.</p></li> </ol> <p>In this particular situation, #1 is your best choice. Tray icons are a Windows-specific feature, so you really should use Windows-specific code that is not tied to FireMonkey to handle them. You can use <code>AllocateHWnd()</code> to use a method of your Form class (or any class, for that matter) as the <code>WndProc()</code> for receiving the tray messages while still allowing the Form class to process them. For example:</p> <pre><code>type TForm2 = class(TForm) Button1: TButton; procedure FormCreate(Sender: TObject); procedure FormDestroy(Sender: TObject); procedure Button1Click(Sender: TObject); private {$IFDEF MSWINDOWS} TrayWnd: HWND; TrayIconData: TNotifyIconData; TrayIconAdded: Boolean; procedure TrayWndProc(var Message: TMessage); {$ENDIF} public { Public declarations } end; </code></pre> <p></p> <pre><code>{$IFDEF MSWINDOWS} const WM_ICONTRAY = WM_USER + 1; {$ENDIF} procedure TForm2.FormCreate(Sender: TObject); begin {$IFDEF MSWINDOWS} TrayWnd := AllocateHWnd(TrayWndProc); with TrayIconData do begin cbSize := SizeOf(TrayIconData); Wnd := TrayWnd; uID := 1; uFlags := NIF_MESSAGE or NIF_ICON or NIF_TIP; uCallbackMessage := WM_ICONTRAY; hIcon := ... StrPCopy(szTip, 'testapp'); end; {$ENDIF} end; procedure TForm2.FormDestroy(Sender: TObject); begin {$IFDEF MSWINDOWS} if TrayIconAdded then Shell_NotifyIcon(NIM_DELETE, @TrayIconData); DeallocateHWnd(TrayWnd); {$ENDIF} end; procedure TForm2.Button1Click(Sender: TObject); begin {$IFDEF MSWINDOWS} if not TrayIconAdded then TrayIconAdded := Shell_NotifyIcon(NIM_ADD, @TrayIconData); {$ENDIF} end; {$IFDEF MSWINDOWS} procedure TForm2.TrayWndProc(var Message: TMessage); begin if Message.MSG = WM_ICONTRAY then begin ... else Message.Result := DefWindowProc(TrayWnd, Message.Msg, Message.WParam, Message.LParam); end; {$ENDIF} </code></pre>
    singulars
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. VO
      singulars
      1. This table or related slice is empty.
    2. VO
      singulars
      1. This table or related slice is empty.
    3. VO
      singulars
      1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload