Как дождаться уничтожения wxDialog?

Это русская секция форума wxWidjets. В этой секции вы можете обсуждать любые вопросы, связанные с wxWidgets на вашем родном языке.
Post Reply
SamSam
Earned a small fee
Earned a small fee
Posts: 12
Joined: Wed Aug 06, 2008 7:53 am

Как дождаться уничтожения wxDialog?

Post by SamSam » Tue Sep 09, 2008 7:26 am

wxWindow::Destroy запускает отложеное удаление окна и его элементов. Соответственно функция не ждет уничтожения окна. А хотелось бы. Т.к. продолжают приходить сообщения, например wxEVT_KILL_FOCUS, в обработчиках которых используются классы, удаляемые после wxWindow::Destroy. Собственно вопрос: как дождаться гарантированного уничтожения окна?

tan
Moderator
Moderator
Posts: 1471
Joined: Tue Nov 14, 2006 7:58 am
Location: Saint-Petersburg, Russia

Re: Как дождаться уничтожения wxDialo

Post by tan » Tue Sep 09, 2008 8:12 am

Привет.
SamSam wrote:wxWindow::Destroy запускает отложеное удаление окна и его элементов. Соответственно функция не ждет уничтожения окна. А хотелось бы. Т.к. продолжают приходить сообщения, например wxEVT_KILL_FOCUS, в обработчиках которых используются классы, удаляемые после wxWindow::Destroy. Собственно вопрос: как дождаться гарантированного уничтожения окна?
Не понимаю проблемы. Собственно Destroy для того и нужен, что бы безопасно убить окно, если у него еще есть необработанные сообщения в очереди. Если, по каким-то причинам необходимо убить окно без этой лабуды существует delete.
OS: Windows XP Pro
Compiler: MSVC++ 7.1
wxWidgets: 2.8.10

User avatar
T-Rex
Moderator
Moderator
Posts: 1187
Joined: Sat Oct 23, 2004 9:58 am
Location: Zaporizhzhya, Ukraine
Contact:

Post by T-Rex » Tue Sep 09, 2008 8:18 am

Убивать окно через delete нехорошо, в доке по этому поводу вроде было красиво расписано.

tan
Moderator
Moderator
Posts: 1471
Joined: Tue Nov 14, 2006 7:58 am
Location: Saint-Petersburg, Russia

Post by tan » Tue Sep 09, 2008 8:41 am

T-Rex wrote:Убивать окно через delete нехорошо, в доке по этому поводу вроде было красиво расписано.
Оно конечно так, но если очень хочется (и, главное, сам понимаешь, что делаешь), то можно :)
OS: Windows XP Pro
Compiler: MSVC++ 7.1
wxWidgets: 2.8.10

SamSam
Earned a small fee
Earned a small fee
Posts: 12
Joined: Wed Aug 06, 2008 7:53 am

Post by SamSam » Tue Sep 09, 2008 9:25 am

Да не очень-то можно через delete. Ерунда получается. да и обработки сообщений хотелось бы дождаться)))

tan
Moderator
Moderator
Posts: 1471
Joined: Tue Nov 14, 2006 7:58 am
Location: Saint-Petersburg, Russia

Post by tan » Tue Sep 09, 2008 9:53 am

SamSam wrote:Да не очень-то можно через delete. Ерунда получается. да и обработки сообщений хотелось бы дождаться)))
Так а в чем проблема с Destroy()? Поподробней, плз.
OS: Windows XP Pro
Compiler: MSVC++ 7.1
wxWidgets: 2.8.10

SamSam
Earned a small fee
Earned a small fee
Posts: 12
Joined: Wed Aug 06, 2008 7:53 am

Post by SamSam » Tue Sep 09, 2008 9:57 am

Есть класс который создает и уничтожает диалог. Есть объекты неких классов, которые используются в обработчиках сообщений контролов диалога. Диалог уничтожается в диструкторе класа. Далее уничтожаются доп. объекты, но прикол в том что в это время может проскочить каккой-нить event и все испортить(((

tan
Moderator
Moderator
Posts: 1471
Joined: Tue Nov 14, 2006 7:58 am
Location: Saint-Petersburg, Russia

Post by tan » Tue Sep 09, 2008 12:20 pm

SamSam wrote:Есть класс который создает и уничтожает диалог. Есть объекты неких классов, которые используются в обработчиках сообщений контролов диалога. Диалог уничтожается в диструкторе класа. Далее уничтожаются доп. объекты, но прикол в том что в это время может проскочить каккой-нить event и все испортить(((
Ну типа того, что ли:

Code: Select all

...
    dialog->Destroy();
    delete some_object;
...
и some_object где-то в диалоге употребляется. Так?

Ну это просто дизайн корявый, можно же как-то иначе это делать, ну, например убивать some_object не в деструкторе класса, а в деструкторе самого диалога. Конкретно сказать трудно, вся конструкция неизвестна. Самый простой (не очень элегантный) способ - обнулять указатель на some_object при его удалении (хотя это как посмотреть, может у тебя в диалоге используется некоторая локальная копия указателя на этот объект) и в обработчике диалога проверять его на NULL.
Короче, лучше это просто переделать, что бы диалог не юзал объекты которыми он не владеет и состояния которых он не знает.
OS: Windows XP Pro
Compiler: MSVC++ 7.1
wxWidgets: 2.8.10

SamSam
Earned a small fee
Earned a small fee
Posts: 12
Joined: Wed Aug 06, 2008 7:53 am

Post by SamSam » Tue Sep 09, 2008 1:17 pm

Сам понимаю что корявый дизайн. Не я его придумал. Вот сейчас и стараюсь как-нибудь разделить мух и котлеты, да чтоб еще и всю структуру не переделывать.

SamSam
Earned a small fee
Earned a small fee
Posts: 12
Joined: Wed Aug 06, 2008 7:53 am

Post by SamSam » Wed Sep 10, 2008 8:39 am

Вообще есть свои странности в wxWidgets. Ибо если при уничтожении wxDialog мы сначала заходим в деструктор, а потом в обработчик wxWindowDestroyEvent, то это, IMHO, баг)))

tan
Moderator
Moderator
Posts: 1471
Joined: Tue Nov 14, 2006 7:58 am
Location: Saint-Petersburg, Russia

Post by tan » Wed Sep 10, 2008 9:03 am

SamSam wrote:Вообще есть свои странности в wxWidgets. Ибо если при уничтожении wxDialog мы сначала заходим в деструктор, а потом в обработчик wxWindowDestroyEvent, то это, IMHO, баг)))
Не, в WX все правильно. Деструктор диалога вызывается последним. Поэтому самый безопасный способ - удалять объекты, которые юзаются в диалоге, (да это к любому окну относится) в деструкторе самого диалога (ну, либо не удалять их вовсе, если они вообще для диалога внешние, например, глобальные). А у тебя как раз не так :(
OS: Windows XP Pro
Compiler: MSVC++ 7.1
wxWidgets: 2.8.10

SamSam
Earned a small fee
Earned a small fee
Posts: 12
Joined: Wed Aug 06, 2008 7:53 am

Post by SamSam » Wed Sep 10, 2008 10:15 am

tan wrote: Не, в WX все правильно. Деструктор диалога вызывается последним. Поэтому самый безопасный способ - удалять объекты, которые юзаются в диалоге, (да это к любому окну относится) в деструкторе самого диалога (ну, либо не удалять их вовсе, если они вообще для диалога внешние, например, глобальные). А у тебя как раз не так :(
Вчера породил класс от wxDialog, внедрил в иерархию, проблема практически решилась. В отладке деструктор класса вызывается раньше, чем обработчик wxWindowDestroyEvent. В винде, во всяком случае. Сомневаешься - проверь ;-) Глюк отладчика допускаю.

Post Reply