Date: 16.12.2019 10:02:10
Какой элемент управления вы используете, чтобы отображать текст? В общем случае, вам нужно установить с помощью SetWinEventHook хук на событие появления меню EVENT_SYSTEM_MENUPOPUPSTART и в обработчике этого события добавить в меню элемент через AppendMenu. Вот так будет выглядеть код для стандартного Edit Control:
#include <stdlib.h> #include <stdio.h> #include <windows.h> bool Enabled = false; UINT CurrentItemID; HWND GetMenuOwner(DWORD thid) { //получает владельца активного меню UI-потока GUITHREADINFO info; memset(&info, 0, sizeof(info)); info.cbSize = sizeof(info); GetGUIThreadInfo(thid, &info); if ((info.flags & GUI_POPUPMENUMODE) != 0) { return info.hwndMenuOwner; } else { return NULL; } } //Обработка появления меню void CALLBACK HandleMenuPopup(HWINEVENTHOOK hook, DWORD event, HWND hwnd, LONG idObject, LONG idChild, DWORD dwEventThread, DWORD dwmsEventTime) { HWND hOwner = GetMenuOwner(dwEventThread); //получаем имя класса окна WCHAR buf[100] = L""; GetClassNameW(hOwner, buf, 100); if (wcscmp(buf, L"Edit") == 0) { //если это Edit Control, получаем меню HMENU hMenu = (HMENU)SendMessage(hwnd, MN_GETHMENU, 0, 0); int c = GetMenuItemCount(hMenu); UINT id_max = 0; //найдем максимальный ID элемента... for (int i = 0; i < c; i++) { UINT id = GetMenuItemID(hMenu, i); //Значения больше 10000, видимо, зарезервированы для особых целей - с ними не работает if (id >= 10000) continue; if (id > id_max) id_max = id; } CurrentItemID = id_max + 1; //получаем уникальный ID для нового элемента //добавляем новый элемент Test BOOL res = AppendMenu(hMenu, MF_STRING | MF_POPUP, CurrentItemID, L"Test"); if (res == FALSE) { printf("AppendMenu error %d", GetLastError()); Enabled = false; return; } Enabled = true; } else Enabled = false; } //обработка нажатия элемента void CALLBACK HandleMenuClick(HWINEVENTHOOK hook, DWORD event, HWND hwnd, LONG idObject, LONG idChild, DWORD dwEventThread, DWORD dwmsEventTime) { if (Enabled && idChild == CurrentItemID) { HWND hOwner = GetMenuOwner(dwEventThread); //выполнить необходимые действия... } } void InitializeHook() { CoInitialize(NULL); HWINEVENTHOOK hook = SetWinEventHook( EVENT_SYSTEM_MENUPOPUPSTART, EVENT_SYSTEM_MENUPOPUPSTART, // Range of events NULL, // Handle to DLL. HandleMenuPopup, // The callback. GetCurrentProcessId(), 0, // Process and thread IDs of interest (0 = all) WINEVENT_OUTOFCONTEXT); // Flags. if (hook == 0) printf("SetWinEventHook HandleMenuPopup error %d", GetLastError()); hook = SetWinEventHook( EVENT_OBJECT_INVOKED, EVENT_OBJECT_INVOKED, // Range of events NULL, // Handle to DLL. HandleMenuClick, // The callback. GetCurrentProcessId(), 0, // Process and thread IDs of interest (0 = all) WINEVENT_OUTOFCONTEXT); // Flags. if (hook == 0) printf("SetWinEventHook HandleMenuClick error %d", GetLastError()); }
Основано на ответе https://stackoverflow.com/a/32998022/8674428
Date: 17.12.2019 3:19:02
Текст через сообщение WM_GETTEXT, выделение - через EM_GETSEL.
WCHAR buf[256]=L""; SendMessage(hOwner, WM_GETTEXT, sizeof(buf)/sizeof(WCHAR), (LPARAM)buf); DWORD start, end; SendMessage(hOwner, EM_GETSEL, (WPARAM)&start, (LPARAM)&end); WCHAR selection[256] = L""; wcsncpy_s(selection, sizeof(selection) / sizeof(WCHAR), &(buf[start]), end - start);
Автор: VadimTagil