Есть ли способ получить функцию обработчика, которой сопоставлен элемент управления в приложении MFC?

Допустим, у меня есть приложение MFC с кнопкой. Есть ли способ получить эту функцию, которой OON_BN_CLICKED сопоставляет ее? Я знаю, что в CWnd есть функция GetDlgItem, которая возвращает указатель на элемент управления. Есть ли способ получить функцию, которой сопоставлен элемент управления, если у меня есть этот указатель?

Я нашел метод, который, как мне кажется, можно использовать для отправки сообщения элементу Dialog или элементу управления: CWnd :: SendDlgItemMessage (http://msdn.microsoft.com/en-us/library/e2a6czt1.aspx), но я бы хотел знать возможные сообщения.


person Amre    schedule 23.12.2014    source источник
comment
У вас есть исходный код для приложения с рассматриваемым элементом управления или вы хотите проверить внешний элемент управления?   -  person mwigdahl    schedule 23.12.2014


Ответы (1)


В большинстве случаев вы знаете, какие сообщения можно отправлять в окно. Я сильно подозреваю, что вы, возможно, идете неправильным путем для своей задачи. Чего вы на самом деле пытаетесь достичь? Т.е. то, о чем вы спрашиваете, необычно, и настоящая задача, скорее всего, может быть решена другими способами.

В любом случае. Если у вас есть указатель на какой-либо объект, производный от MFC CWnd, все еще можно «реконструировать» его обработчики сообщений MFC, определенные в классе, на который указывает этот CWnd *. MFC определяет все обработчики сообщений на карте, используя BEGIM_MESSAGE_MAP / END_MESSAGE_MAP. На самом деле эти макросы определяют виртуальную функцию GetMessageMap () и массив данных, содержащий структуры, описывающие отображение сообщений. Таким образом, вы можете использовать wnd-> GetMessageMap (), а затем перебирать отображенные обработчики сообщений. Каждая запись содержит информацию об обработчике сообщений и отображаемой функции. Обратите внимание, что GetMessageMap - это защищенная функция, поэтому для доступа к ней извне вам понадобится оболочка. Что-то вроде этого:

struct Accessor : public CWnd
{
    // overwrite protected
    virtual const AFX_MSGMAP* GetMessageMap() const { return CWnd::GetMessageMap(); }
};

Accessor* msg_map_access = (Accessor*) window;
const AFX_MSGMAP* msg_map = msg_map_access->GetMessageMap();

const AFX_MSGMAP_ENTRY* entry = msg_map->lpEntries;
while (entry->nSig != AfxSig_end)
{
    /// do something with the entries
}

Опять же, это не обычная практика; обычно вы никогда этого не делаете. Так что было бы неплохо услышать мотивацию, зачем вам это нужно.

person Nikolay    schedule 23.12.2014
comment
Это именно то, что я пытаюсь сделать. Мотивация этого заключается в том, что существуют приложения, которые позволяют вам делать такие вещи, возможно, предоставляя пользователю доступ к тому, чего он не должен иметь, даже если кнопка была отключена. Я пишу приложение, которое могу использовать для тестирования, поскольку я вношу изменения для защиты от него. - person Amre; 23.12.2014
comment
Хм, если вы хотите защитить свой код от модификации (или внешнего доступа), вероятно, имеет смысл использовать средство защиты программного обеспечения ... Я имею в виду, что на рынке есть некоторые инструменты для защиты программ, такие как Themida / WinLicense, Obsidium и т. Д. . Если вы хотите, чтобы никто не мог щелкнуть отключенную кнопку, отправив сообщения, вам просто нужно проверить в обработчике сообщений, что операция запрещена (в дополнение к отключению кнопки). - person Nikolay; 23.12.2014