#c #visual-c #mfc #modal-dialog
#c #visual-c #мфц #модальный диалог
Вопрос:
Хорошо, в принципе, у меня есть приложение MFC с множеством диалоговых окон, которые необходимо циклически просматривать. По сути, когда вы нажимаете одну кнопку, чтобы перейти к другому диалоговому окну, я хочу, чтобы предыдущее диалоговое окно закрылось. Прямо сейчас диалоговые окна просто отображаются друг над другом. Как мне закрыть диалоговое окно после открытия нового диалогового окна? Вот несколько примеров кода:
void CMachine2Dlg::OnBnClickedNewmc()
{
NameDlg Dlg;
Dlg.DoModal()
}
Комментарии:
1. Рассматривали ли вы возможность использования таблицы свойств или мастера ? (о боже, я говорю как клиппи!)
Ответ №1:
Что вы можете сделать, это скрыть родительский диалог при DoModal()
создании нового диалога и уничтожить его после завершения нового диалога. Я не тестировал приведенное ShowWindow()
ниже, но вы поняли идею, если оно не скрывает диалоговое окно, найдите другую аналогичную функцию.
void CMachine2Dlg::OnBnClickedNewmc()
{
ShowWindow( SW_HIDE);
NameDlg Dlg;
Dlg.DoModal();
EndDialog( 0 );
}
Ответ №2:
Будет трудно связать эти диалоги в цепочку так, как вы упомянули. Do modal обычно предназначен для реализации именно того, что вы испытываете. Ie: диалоговое окно появляется поверх предыдущего.
Один из способов сделать это — создать последовательность модальных диалоговых окон в классе, который вызывает первое диалоговое окно, и использовать возвращаемое значение предыдущего диалогового окна, чтобы определить, нужно ли показывать второе и так далее.
Для бывших:
// define a bunch of constants, any number would do,
// I would avoid 0 and 1 as they usually mean success/error
// This code can be returned in the EndDialog call in a method of your choice (say button click handler).
const int c_needNextDialog = 101;
dialog1 dlg1;
if( dlg1.DoModal() == c_needNextDialog )
{
dialog2 dlg2;
if( dlg2.DoModal() == c_needNextDialog )
{
... and so forth
}
}
Я уверен, что вы поняли идею…
в вашем диалоговом окне вы возвращаетесь следующим образом (взято непосредственно из msf)
void dialog1::OnSomeAction()
{
// Do something
EndDialog(c_needNextDialog); // This value is returned by DoModal!
// Do something
return; // Dialog closed and DoModal returns only here!
}
Я бы держался подальше от немодального диалога, в конечном итоге у вас возникнет другая проблема, например, как управлять потоком диалога и не позволять людям нажимать на главное окно вашего приложения сзади.
Ответ №3:
Вы могли бы попробовать вызвать
EndDialog(nResult);
Ответ №4:
OnOK()
, OnCancel()
или EndDialog(nResult)
ответит на ваш вопрос заголовка.
Однако, как и предложил @tenfour, вы должны использовать таблицу свойств / мастер. Это также может быть одно диалоговое окно с несколькими дочерними окнами страницы свойств, которые вы показываете или скрываете в зависимости от того, что вы хотите, чтобы было видно.
Для этого вам понадобится:
- 1 диалоговое окно, возможно, с кнопками Prev / Next
- 1 окно с изображением, стиль рамки, не отображается, внутри диалогового окна, в котором вы хотите, чтобы отображались дочерние окна
- n страниц свойств, дочерний стиль, без границ, куда вы помещаете все элементы управления.
Создайте класс для диалогового окна и каждой страницы свойств, добавьте переменную-член каждой страницы свойств в диалоговое окно, создайте страницы свойств и используйте фрейм в качестве ссылки для их размещения. При нажатии кнопки просто покажите / скройте необходимые страницы.
Ответ №5:
Вы можете вызвать onCancel() внутри вашего класса dialog . Нравится: this->OnCancel();
Ответ №6:
@tenfour предлагает хорошие возможные решения, но если это невозможно для вас, вы должны создавать диалоги из одного базового windows / Dlg
Mydialog dlg1
if(dlg1.DoModal() )
{
//do something
}
else
// do something else
Mydialog dlg2
if(dlg2.DoModal() )
{
//do something
}
else
// do something else
и так далее….
Таким образом, у вас нет простого контроля над тем, «что» происходит, и вам не нужно возиться с разными окнами, messageloops.