Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Определение ID нажатой кнопки 
:(
    Опции темы
voyageur
Дата 30.3.2010, 10:52 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 17
Регистрация: 23.11.2005

Репутация: нет
Всего: нет



Здравствуйте! Второй день мучаю поисковики, но так и не нашел исчерпывающего ответа...
Ситуация: диалоговый проект MFC. На поле много button'ов у каждой свой ИД, по нажатию любого баттона выполняется _1_ функция OnBnClickedButton1(). В этой функции надо определить, если нажат допустим IDC_BUTTON1 то делать то-то, если IDC_BUTTON2 то то-то. Так вот вопрос, как же определить этот самый ид? Если функцией GetDlgCtrlID( ), как ей пользоваться?
Код

    ON_BN_CLICKED(IDC_BUTTON1, &Cmy_calcDlg::OnBnClickedButton1)
    ON_BN_CLICKED(IDC_BUTTON8, &Cmy_calcDlg::OnBnClickedButton1)
    ON_BN_CLICKED(IDC_BUTTON2, &Cmy_calcDlg::OnBnClickedButton1)
    ON_BN_CLICKED(IDC_BUTTON3, &Cmy_calcDlg::OnBnClickedButton1)
    ON_BN_CLICKED(IDC_BUTTON4, &Cmy_calcDlg::OnBnClickedButton1)
    ON_BN_CLICKED(IDC_BUTTON5, &Cmy_calcDlg::OnBnClickedButton1)
    ON_BN_CLICKED(IDC_BUTTON6, &Cmy_calcDlg::OnBnClickedButton1)
    ON_BN_CLICKED(IDC_BUTTON7, &Cmy_calcDlg::OnBnClickedButton1)
    ON_BN_CLICKED(IDC_BUTTON9, &Cmy_calcDlg::OnBnClickedButton1)
    ON_BN_CLICKED(IDC_BUTTON10, &Cmy_calcDlg::OnBnClickedButton1)

Код

void Cmy_calcDlg::OnBnClickedButton1()
{
    // TODO: добавьте свой код обработчика уведомлений
    if(GetDlgCtrlID()==IDC_BUTTON1)
    {
        my_edit1.SetWindowTextW(L"1");
    }
     else
    {;
    }
}



PM MAIL   Вверх
xTr1m
Дата 30.3.2010, 11:58 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 692
Регистрация: 9.2.2005
Где: Москва

Репутация: нет
Всего: 1



Цитата

ON_BN_CLICKED(IDC_BUTTON1, &Cmy_calcDlg::OnBnClickedButton1)

вот эта строка означает, что при нажатии на кнопку IDC_BUTTON1 будет вызвана функция OnBnClickedButton1.

Цитата

void Cmy_calcDlg::OnBnClickedButton1()
{
    // TODO: добавьте свой код обработчика уведомлений
    if(GetDlgCtrlID()==IDC_BUTTON1)
    {
        my_edit1.SetWindowTextW(L"1");
    }
     else
    {;
    }
}

а тут получается, что эта функция для обработчика события клик кнопки IDC_BUTTON1, то есть других быть не может (в твоем случае).
PM MAIL WWW ICQ   Вверх
586
Дата 30.3.2010, 12:34 (ссылка) |    (голосов:1) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 2243
Регистрация: 8.5.2006

Репутация: 6
Всего: 146



Как вариант, можно перегрузить метод OnCommand.
Код
BOOL Cmy_calcDlg::OnCommand(WPARAM wParam, LPARAM lParam)
{
    switch(LOWORD(wParam))
    {
    case IDC_BUTTON1:
    case IDC_BUTTON2:
    case IDC_BUTTON3:
    case IDC_BUTTON4:
    case IDC_BUTTON5:
    case IDC_BUTTON6:
    case IDC_BUTTON7:
    case IDC_BUTTON8:
    case IDC_BUTTON9:
    case IDC_BUTTON10:
        MessageBox(_T("!!!"));
        return TRUE;
    }
    return CDialog::OnCommand(wParam, lParam);
}

PM   Вверх
voyageur
Дата 30.3.2010, 13:04 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 17
Регистрация: 23.11.2005

Репутация: нет
Всего: нет



xTr1m,  функция обрабатывает все кнопки, т.е. по нажатию любой будет печататься "1", другой вопрос, что значение GetDlgCtrlID() не равно IDC_BUTTON1 (1000), по этому не работает.. Вот мне интересно, что я забыл подставить?
в результате должно получится что по нажатию IDC_BUTTON1 напечатается "1" по IDC_BUTTON2 "2" и тд


586, а как этим пользоваться?
PM MAIL   Вверх
586
Дата 30.3.2010, 13:14 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 2243
Регистрация: 8.5.2006

Репутация: 6
Всего: 146



Цитата(voyageur @  30.3.2010,  13:04 Найти цитируемый пост)
586, а как этим пользоваться? 

Так же, как и обрабатывается сообщение WM_COMMAND.
В LOWORD(wParam) находится идентификатор элемента (кнопки, эдита, или другого контрола), в HIWORD(wParam) передаётся код события (при нажатии кнопки это будет BN_CLICKED), в lParam находится дескриптор контрола, которое отправило сообщение.
PM   Вверх
voyageur
Дата 30.3.2010, 13:22 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 17
Регистрация: 23.11.2005

Репутация: нет
Всего: нет



Код

error C2555: Cmy_calcDlg::OnCommand: возвращаемый тип перегруженной виртуальной функции отличается от 'CWnd::OnCommand' и не является ковариантным
1>        c:\program files\microsoft visual studio 9.0\vc\atlmfc\include\afxwin.h(2666): см. объявление 'CWnd::OnCommand'

вот что мне пишет..
PM MAIL   Вверх
xTr1m
Дата 30.3.2010, 14:01 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 692
Регистрация: 9.2.2005
Где: Москва

Репутация: нет
Всего: 1



Ох, прошу прощения. Тогда можно использовать ON_COMMAND_RANGE.
PM MAIL WWW ICQ   Вверх
586
Дата 30.3.2010, 21:04 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 2243
Регистрация: 8.5.2006

Репутация: 6
Всего: 146



Цитата(voyageur @  30.3.2010,  13:22 Найти цитируемый пост)
Код
error C2555: Cmy_calcDlg::OnCommand: возвращаемый тип перегруженной виртуальной функции отличается от 'CWnd::OnCommand' и не является ковариантным
1>        c:\program files\microsoft visual studio 9.0\vc\atlmfc\include\afxwin.h(2666): см. объявление 'CWnd::OnCommand'

вот что мне пишет.. 

Проверь, правильно ли описан метод OnCommand в прототипе класса Cmy_calcDlg.
проблем быть не должно.
Вот кстати описание CWnd::OnCommand в MSDN: http://msdn.microsoft.com/en-us/library/3t3ddsb9.aspx
PM   Вверх
Albor
Дата 31.3.2010, 06:48 (ссылка) |    (голосов:1) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 589
Регистрация: 28.2.2009

Репутация: 7
Всего: 9



Цитата(voyageur @  30.3.2010,  10:52 Найти цитируемый пост)
Второй день мучаю поисковики, но так и не нашел исчерпывающего ответа...


voyageur, нужно было посмотреть что делает GetDlgCtrlId(). Вызывая его в классе Cmy_calcDlg, данный метод вызывается для объекта этого класса, то есть для диалога. Чтобы получить ID кнопки, нужно вызвать этот метод, например через указатель на кнопку, так pButton->GetDlgCtrlId(); В твоём стартовом топике искать ID нет смысла, так как ты определил обработчик для каждой кнопки и попав в такой обработчик можно быть уверенным в том, что никакой другой ID кроме нажатой кнопки здесь не присутствует. Об этом тебе и говорил xTr1m. 
586 предложил другой подход: обработка всех команд в одном методе. Вот здесь уже нужно проверить от какого контрола и какая пришла команда (но GetDlgCtrlId() здесь не нужен).  В этом случае тебе не нужны те функции нажатия кнопок, которые ты уже определил. Так что не путайся и определись как будешь решать задачу: как делал сначала или через OnCommand.

Это сообщение отредактировал(а) Albor - 31.3.2010, 07:56
PM MAIL ICQ   Вверх
voov
Дата 31.3.2010, 10:22 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Патамушта мы пилоты
**


Профиль
Группа: Участник
Сообщений: 460
Регистрация: 29.11.2007

Репутация: 8
Всего: 8



Цитата(xTr1m @  30.3.2010,  14:01 Найти цитируемый пост)
Тогда можно использовать ON_COMMAND_RANGE

В данном случае это удобнее всего
PM MAIL   Вверх
voyageur
Дата 31.3.2010, 10:36 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 17
Регистрация: 23.11.2005

Репутация: нет
Всего: нет



Все, проект заново создал, просто надо было удалить функции нажатия кнопок, как сказал Albor, и все заработало с OnCommand. 
Я работаю в фотоне QNX, там виджеты и попроще)) Всем спасибо!
PM MAIL   Вверх
Earnest
Дата 31.3.2010, 10:44 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Экс. модератор
Сообщений: 5962
Регистрация: 17.6.2005
Где: Рязань

Репутация: 87
Всего: 183



1) Проще всего, безусловно, как уже сказано , изменить сигнатуру обработчика на void (UINT) и использовать ON_COMMAND_RANGE
2) Если уже переопределять виртуальную обработку коммангд, то уж никак не OnCommand, а OnCmdMsg - она более специализирована... Для переопределения OnCommand должны быть более веские основания. Я бы, кстати, так и сделала... Все эти ON_RANGE, во первых, требуют, чтобы ид-ры были в одном диапазоне, что сложно поддерживать, да и вообще...
3) Для крайних случаев, когда изменить сигнатуру обработчика почему-либо нельзя, есть замечательная функция CWnd::GetCurrentMessage, которая возвращает текущее обрабатываемое сообщение, со всеми его параметрами. Вот в нем-то и можно посмотреть, кого нажали (т.е. WPARAM).


--------------------
...
PM   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | Visual C++/MFC/WTL | Следующая тема »


 




[ Время генерации скрипта: 0.0718 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.