From 128f09113ccd1013689e0b96c177bb40e1d3de53 Mon Sep 17 00:00:00 2001 From: Stanislav N Mikhailov Date: Wed, 25 Feb 2026 22:40:28 +0300 Subject: [PATCH] Add tray context menu with Exit action --- Puer.exe | Bin 414208 -> 414208 bytes src/Puer.asm | 87 +++++++++++++++++++++++++++++---------------------- 2 files changed, 49 insertions(+), 38 deletions(-) diff --git a/Puer.exe b/Puer.exe index 37f20b396d3a78f9fcb84dc42d4549af23058d3a..a57685a29a8b9a79cfb2dac360575505de141685 100644 GIT binary patch delta 1763 zcmc&!TWl0n7(Tn*v%SvlU^=+H2)nq}nrI^e2BU4Nv^Yj98(XCmqttfk#n@@LJ1I74 zc5CVCX56yPkoaJtLR!NE4;XyGsHw$dg7LzWAqKF0A;Eni_+W#T@%v{^VfEd3l9})S zzyCY`<(%C~FVv(LYVzrp)xgdxi(1cI@pIDg56*oF+;Q!|u>}Vg=UnV|{FjFM1{byY zuWP+y`{sYiJQCW*Sd3w{GS=PfC+nXp?Pp;yD|pp^Fx}vJ*avH6K2lfSl#CxqA~b5Q zdLH!N!_QWD$GzTC*-ZJu%9S8vYL=HmtmdRkTN$&JRr7P-bU>qskvn8#DU;?N9*M|A z&8)Fxy_(AnI)P@QHk?c5EI%xt2rzcNrG&AWsgNf)d&c~eN6Z#~Y3h$Hl>I}5RYN+B zQmVDQ4xOz$OI((pA`bcWI@S6H9g~2iNYLO4-X%enUq&MJ9CoHjWGnAU&OTcYihZ{7 z7pOwDYVmGt@i?il#{Pm;e5B}QJ>qv5n0!F)xoUg*Qcn{vBws;q;Qpb7`7Wa{m z{|*ycl^`cQ=YZ06AN8h@YCgB&i zJGSrRA@cF3VLlvJbp#L2B*e_C6ksmNc61{XImJb78p%K{k_TF=q}<`!uaqI zmmrR@b#r^=y$2`}C3M;7z>% delta 1545 zcmc&!U1$_n6h5=ryT&B5J3*&SHqq|JCD9Unh*4rNMKr<`ti%S<7zl~~DNQMwr6ncq zuFEc6*Nuit@vTD9B2;NXU+hEJB+3w4B?^j&3PK)~Xdgs0Xkq%DnVTA4`_c<@zjMCx z-E+?U*-f6SPM)hio%|$K(fsiGz@CwX--PRTk4ytQXSz;ZbMgF$hr3<>^ZtE@uMdol zg?&!@=>6>KxhPQwVQeDW-4-9F5j2UNd;$+d+hu$j4fP z?}YzyneV92_c|mK{)l-aL}cZ}B8aVme(xh9$Gj!4_*21M9LX1Y9Sn1i+#;e;Vk$jH zgSA$naM%qjV`|=+mKkx-7!49Vee5Gj4_9fS%x(ErL=#U+h_)5@1U^q`k$y~ z*%N4uKDCQ4JjESX(d8*lc#6Lfa!ixCoX9eVCgL@gJpQ(=zVxZUs2ib-|o*x%bpGKpMyVRo0YN_x!+-oCt6vC%Vyk=@77wl#D?WwiBlZOiJ4k1aTD|VB`$(-%%3=mEe=7ek$hIVNsG(X zi&usBF<;1Z;N7|Bl%ICYv*4yC`Mp0+e6Ygn>0^cM3QHAwQKBzm^OlE0Dt=Poj|zWN zIHvGRg^v_IQ~1WiZVITxRSFvwwkq7NutzPtt#DyGPW#z@_VF-@Z}w#bUzvPUR<~}6 zAaZ}pv4O8xLI@QBYx?*14fe&>!SsIq%pGBl=z-i({$Up<;ba~g8yXtgzxNPS{HL;! z)n0}snABWHwDcXfmN^St@g3L99G~iOIbObNJxAw92X85YH@AT6!M0n#eZ7D?7L(g6 z!vFV`t^E&ICR=q|RtD?jmf$vdK4@IFgB!Fnr|Y%vj~iJ-%No9{QIa+MSwsA61UCNz DnZ!r~ diff --git a/src/Puer.asm b/src/Puer.asm index 011da71..a5941c7 100644 --- a/src/Puer.asm +++ b/src/Puer.asm @@ -1,19 +1,17 @@ include template.inc .code entry_point proc - invoke GetModuleHandle, NULL ; Взять хэндл пpогpаммы - mov hInstance,rax ; Под Win32, hmodule==hinstance mov hInstance,eax - - invoke WinMain, hInstance,NULL,CommandLine, SW_SHOWDEFAULT ; вызвать основную функцию - invoke ExitProcess, rax ; Выйти из пpогpаммы. - ; Возвpащаемое значение, помещаемое в eax, беpется из WinMain'а. + invoke GetModuleHandle, NULL + mov hInstance,rax + + invoke WinMain, hInstance,NULL,CommandLine, SW_SHOWDEFAULT + invoke ExitProcess, rax entry_point endp -;______________________________________________________________________________________________________________________________________________________________ + WinMain proc hInst:HINSTANCE,hPrevInst:HINSTANCE,CmdLine:LPSTR,CmdShow:QWORD - ; создание локальных пеpеменных в стеке LOCAL msg:MSG LOCAL hwnd:HWND - ;регистрация оконного класса + push hInstance pop wc.hInstance invoke LoadIcon,wc.hInstance,IDI_ICON @@ -21,33 +19,38 @@ WinMain proc hInst:HINSTANCE,hPrevInst:HINSTANCE,CmdLine:LPSTR,CmdShow:QWORD mov wc.hIconSm,rax invoke LoadCursor,NULL,IDC_ARROW mov wc.hCursor,rax - invoke RegisterClassEx, addr wc ; pегистpация нашего класса окнаW + invoke RegisterClassEx, addr wc invoke CreateWindowEx,NULL,ADDR szClassName,ADDR AppName,WS_OVERLAPPEDWINDOW,282,0,1354,1017,NULL,NULL,hInst,NULL mov hwnd,rax - invoke ShowWindow,hwnd,CmdShow ; отобpазить наше окно на десктопе (вместо CmdShow можно указать свойство 3 - во весь экран) - invoke UpdateWindow, hwnd ; обновить клиентскую область - .while TRUE ; Enter message loop + invoke ShowWindow,hwnd,CmdShow + invoke UpdateWindow, hwnd + + .while TRUE invoke GetMessage, ADDR msg,NULL,0,0 .break .if (rax==0) invoke TranslateMessage, ADDR msg invoke DispatchMessage, ADDR msg .endw - mov rax,msg.wParam ; сохpанение возвpащаемого значения в eax - ret + + mov rax,msg.wParam + ret WinMain endp -;______________________________________________________________________________________________________________________________________________________________ + WndProc proc hWnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM - LOCAL hDC:HDC - .if uMsg==WM_DESTROY ; если пользователь закpывает окно + LOCAL hDC:HDC + LOCAL pt:POINT + + .if uMsg==WM_DESTROY invoke Shell_NotifyIconA,NIM_DELETE,addr note invoke DestroyMenu,hPopupMenu invoke SetThreadExecutionState,ES_CONTINUOUS - invoke PostQuitMessage,NULL ; выходим из пpогpаммы + invoke PostQuitMessage,NULL + .elseif uMsg==WM_CREATE invoke CreatePopupMenu - mov hPopupMenu,rax ;Создаём pop-up меню для взаимодействия через трей - invoke AppendMenuA,hPopupMenu,MF_STRING,IDM_RESTORE,addr RestoreString - invoke AppendMenuA,hPopupMenu,MF_STRING,IDM_EXIT,addr ExitString + mov hPopupMenu,rax + invoke AppendMenuA,hPopupMenu,MF_STRING,IDM_EXIT,addr ExitString + invoke LoadIcon,hInstance,IDI_ICON mov hIcon,rax .if rax==0 @@ -55,16 +58,16 @@ WndProc proc hWnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM mov hIcon,rax .endif mov note.hIcon,rax - ;Запрещаем переход в сон и отключение дисплея + invoke SetThreadExecutionState,ES_CONTINUOUS or ES_SYSTEM_REQUIRED or ES_DISPLAY_REQUIRED - .if rax ==-1 - invoke PostQuitMessage,NULL ; выходим из пpогpаммы + .if rax==-1 + invoke PostQuitMessage,NULL .else mov sleepBlockEnabled,1 mov rax,0 ret .endif - + .elseif uMsg==WM_SIZE .if wParam==SIZE_MINIMIZED mov note.cbSize,SIZEOF TRAYICONDATAA @@ -84,6 +87,7 @@ WndProc proc hWnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM .endif mov rax,0 ret + .elseif uMsg==WM_SHELLNOTIFY .if wParam==IDI_TRAY .if lParam==WM_LBUTTONDBLCLK @@ -110,37 +114,44 @@ WndProc proc hWnd:HWND, uMsg:UINT, wParam:WPARAM, lParam:LPARAM invoke Shell_NotifyIconA,NIM_MODIFY,addr note mov sleepBlockEnabled,1 .endif + + .elseif lParam==WM_RBUTTONUP + invoke SetForegroundWindow,hWnd + invoke GetCursorPos,addr pt + invoke TrackPopupMenu,hPopupMenu,TPM_RIGHTBUTTON,pt.x,pt.y,0,hWnd,NULL .endif .endif mov rax,0 ret + + .elseif uMsg==WM_COMMAND + .if wParam==IDM_EXIT + invoke DestroyWindow,hWnd + .endif + mov rax,0 + ret + .elseif uMsg==WM_PAINT invoke myPaint,hWnd + .elseif uMsg==WM_ERASEBKGND mov rax,TRUE ret - .else - invoke DefWindowProc,hWnd,uMsg,wParam,lParam ; Дефолтная функция обpаботки окна + + .else + invoke DefWindowProc,hWnd,uMsg,wParam,lParam ret .endif - xor rax,rax + xor rax,rax ret WndProc endp -;______________________________________________________________________________________________________________________________________________________________ -;______________________________________________________________________________________________________________________________________________________________ - -;______________________________________________________________________________________________________________________________________________________________ myPaint proc hWndPaint:HWND LOCAL ps:PAINTSTRUCT - invoke BeginPaint,hWndPaint,ptr$(ps) ;тут создаётся контекст устройства окна - - + invoke BeginPaint,hWndPaint,ptr$(ps) invoke EndPaint,hWndPaint,ptr$(ps) ret myPaint endp end - -