Что нового

Как перенаправить обработку кликов пунктов меню в $WM_MENUCOMMAND

erlik

Продвинутый
Сообщения
317
Репутация
84
Не получается назначить выпадающему подменю стиль $MNS_NOTIFYBYPOS, чтобы при выборе пунктов отрабатывалось $WM_MENUCOMMAND, а не $WM_COMMAND.
Код:
$hRecentFiles = _GUICtrlMenu_CreatePopup(BitOr(32,8));_GUICtrlMenu_CreateMenu(BitOr(32,8))
_GUICtrlMenu_InsertMenuItem($hFileMenu, 7, "Недавние файлы", $idRecentFilesMenu,$hRecentFiles)

В скрипте также используются сообщения $WM_COMMAND -для других пунктов меню.
Но нужно, чтобы от пунктов именно этого выпадающего меню сообщения шли в $WM_MENUCOMMAND.
Проверка назначения стиля _GUICtrlMenu_GetMenuStyle($hRecentFiles) выдает 0.
Пробовал и так: _GUICtrlMenu_SetMenuStyle($hRecentFiles,$MNS_NOTIFYBYPOS).
Функция возвращает 1, то есть вроде как стиль назначает, но в $WM_MENUCOMMAND все равно ничего не передается при клике на пункты.
Вот сама функция для WM_MENUCOMMAND (в GUIRegisterMsg она, конечно, же зарегистрирована.)
Код:
Func WM_MENUCOMMAND($hWnd, $iMsg, $wParam, $lParam)
    ;#forceref $hWnd, $iMsg, $iwParam
	Local $hMenu = $lParam                                ; Дескриптор выбранного пункта меню
	Local $iIdPointMenu        = _WinAPI_LoWord($wParam)  ;ID (ИДЕНТИФИКАТОР) пункта
    Local $iIndexPointMenu     = _WinAPI_HiWord($wParam)  ;	индекс выбранного пункта.
	ConsoleWrite('WM_MENUCOMMAND:' $hMenu & '|'& $iIdPointMenu '|' & $iIndexPointMenu & @CR)
	Switch $hMenu
	    Case $hRecentFiles
			Switch $iIdPointMenu
					Case 20000,20001,20002,20003,20004,20005,20006,20007,20008,20009
					Local $sMenuItem_Text = $aRecentFiles[$iIndexPointMenu]
					Local $aPath = SplitPath($sMenuItem_Text, -1, True)
		            ;ConsoleWrite("Абсолютный путь: " & SplitPath($sMenuItem_Text,2)&@CR)
					If IsArray($aPath) Then
		               LoadOneLib($aPath[1], $aPath[4])
					EndIf
			EndSwitch
	EndSwitch
    Return $GUI_RUNDEFMSG
EndFunc

На данный момент в WM_MENUCOMMAND вообще ничего не передается.
 

firex

AutoIT Гуру
Сообщения
943
Репутация
208
А что мешает получить индекс пункта используя конструкцию следующего типа:

Код:
#include <GuiMenu.au3>
#include <GuiConstantsEx.au3>
#include <WinAPI.au3>
#include <WindowsConstants.au3>

Opt('MustDeclareVars', 1)

Global Enum $idOpen = 1000, $idSave, $idInfo

_Main()

Func _Main()
    Local $hGUI

    $hGUI = GUICreate("Menu", 400, 300)
    GUISetState()

    GUIRegisterMsg($WM_CONTEXTMENU, "WM_CONTEXTMENU")
    Do
    Until GUIGetMsg() = $GUI_EVENT_CLOSE
EndFunc   ;==>_Main

; Handle WM_CONTEXTMENU messages
Func WM_CONTEXTMENU($hWnd, $iMsg, $iwParam, $ilParam)
    Local $hMenu

    $hMenu = _GUICtrlMenu_CreatePopup( 32 )
    _GUICtrlMenu_InsertMenuItem ($hMenu, 0, "Open", $idOpen)
    _GUICtrlMenu_InsertMenuItem ($hMenu, 1, "Save", $idSave)
    _GUICtrlMenu_InsertMenuItem ($hMenu, 3, "", 0)
    _GUICtrlMenu_InsertMenuItem ($hMenu, 3, "Info", $idInfo)
    ConsoleWrite( "Clicked: " & _GUICtrlMenu_TrackPopupMenu ($hMenu, $iwParam, -1, -1, 1, 1, 2 ) & @CRLF )
    _GUICtrlMenu_DestroyMenu ($hMenu)
    Return True
EndFunc   ;==>WM_CONTEXTMENU


И делай вместо ConsoleWrite свой callback с передачей указателя на меню и кликнутый пункт.
 
Автор
E

erlik

Продвинутый
Сообщения
317
Репутация
84
firex
Как то все не слишком понятно. :smile: Для моего меню твоя конструкция сложновато вписывается.
У меня есть основное меню File, в нем есть пункт Недавние файлы, который открывает (или не открывает) подменю со списком файлов и вот индексы этих пунктов при клике мне и нужно получить. Если бы индексы были стабильными - я бы их в дополнительный параметр писал, а потом считывал через _GUICtrlMenu_GetItemData(). Но пункты постояно (при достижениий максимального числа) смещаются по принципу очереди - верхний удаляется, новый пишется в конец, поэтому такой способ работает неправильно.

PS:Должно же как то WM_MENUCOMMAND работать - оно именно для моего случая и предназначено, когда требуется индекс пункта получить. Просто есть здесь какой то нюанс, который я не понимаю.


Добавлено:
Сообщение автоматически объединено:

---------------------------------------
Нда. Для основного меню оказывается все работает. То есть если сделать вот так
Код:
_GUICtrlMenu_SetMenu($hMainWnd, $hMainMenu)
_GUICtrlMenu_SetMenuStyle($hMainMenu,$MNS_NOTIFYBYPOS)

То есть назначить этот стиль основному меню - то WM_MENUCOMMAND отрабатывается.
Но тогда придется переносить обработку кликов всех пунктов сюда же....
 
Верх