Наши проекты:
Журнал · Discuz!ML · Wiki · DRKB · Помощь проекту |
||
ПРАВИЛА | FAQ | Помощь | Поиск | Участники | Календарь | Избранное | RSS |
[3.15.218.254] |
|
Сообщ.
#1
,
|
|
|
Делаю визардом стандартное Dialog based приложение. На него леплю CComboBox, связываю с переменной m_Combo. Потом в OnInitDialog() пишу:
m_Combo.AddString("hello"); Все ок! А если я вставляю в текущий диалог новый диалог, КлассВизард предлагает создать новый класс, создаю, леплю туда CComboBox, связываю с переменной m_Combo2, запускаю из основного диалога по нажатию на клавишу. CMydialog MD; MD.m_Combo2.AddString("Hello"); //ERROR! MD.DoModal(); то вылетает ошибка на строку в AfxWin2.inl: { ASSERT(::IsWindow(m_hWnd)); return (int)::SendMessage(m_hWnd, CB_ADDSTRING, 0, (LPARAM)lpszString); } И почему в новом диалоге только две функции: DoDataExchange и констркутор, а где OnInitDialog? |
Сообщ.
#2
,
|
|
|
А это виртуальные функции. InitDialog()
ты должен переопределить, тогда всё будет ОК. В инитдиалог вписываешь добавление строки, потом вызываешь её из основной проги. |
Сообщ.
#3
,
|
|
|
Блин, ну вы даёте. Здесь же всё ясно как день. Вам даже не надо лезть в исходники MFC, отладчик всё показал. Надеюсь, вы в курсе, что оконные классы MFC всего лишь обёртки над API (API wrappers), так что многого от них ждать не приходится. В том числе, следует помнить тупое и понятное правило, что если существует ОБЪЕКТ, то вовсе не факт, что существует ОКНО. А многие API функции, в том числе SendMessage, которую вызывают многие функции оконных классов, требуют передачи корректного дескриптора (handle) окна. Таким образом, инициализацию переменных, не опирающихся на использование оконных API и другие инициализации нужно делать в конструкторе, остальное - в OnInitDialog, в том числе заполнение ComboBox.
Вам ещё повезло, что разработчики MFC навтыкали везде диагностических макросов, помнится, в OWL начинающие долго гадали, почему не работает тот или иной вызов. Надеюсь, shadowbolt понял, что именно строка ASSERT(::IsWindow(m_hWnd)); вызвала ошибку, т.е. окно не было ещё создано. А OnInitDilog, как и многое другое, нужно добавлять самому (щелчок правой кнопкой на имени класса в дереве, Add Windows Message Handler). |
Сообщ.
#4
,
|
|
|
Muran, не мути голову бегиннерам. Виртуальных функций в CWnd не так уж много. Если бы все обработчики сообщений были виртуальными функциями, таблица VTable разрослась бы до невозможности. А вот и:
Цитата Default handlers for standard Windows messages (WM_) are predefined in class CWnd. The class library bases names for these handlers on the message name. For example, the handler for the WM_PAINT message is declared in CWnd as: afx_msg void OnPaint(); The afx_msg keyword suggests the effect of the C++ virtual keyword by distinguishing the handlers from other CWnd member functions. Note, however, that these functions are not actually virtual; they are instead implemented through message maps. Message maps depend solely on standard preprocessor macros, not on any extensions to the C++ language. The afx_msg keyword resolves to white space after preprocessing. |