![]() |
Модераторы: feodorv, GremlinProg, xvr, Fixin |
![]() ![]() ![]() |
|
semibug |
|
|||
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 323 Регистрация: 27.3.2009 Репутация: нет Всего: нет |
Каким образом лучше организовать перехват события закрытия консольного окна пользователем (клик по крестику).
|
|||
|
||||
azesmcar |
|
|||
![]() uploading... ![]() ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 6291 Регистрация: 12.11.2004 Где: Армения Репутация: 5 Всего: 211 |
|
|||
|
||||
semibug |
|
|||
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 323 Регистрация: 27.3.2009 Репутация: нет Всего: нет |
Срабатывает при нормальном завершении приложения (окончании функции main),
если же закрывать мышкой по крестику - не входит в atexit_handler. Сама консоль создаётся в оконном приложении (VS2005 C++) сразу после запуска. Попробовал создать глобальный объект, с бряком в деструкторе. При нормальном завершении программы деструктор отрабатывает как положено, при закрытии по крестику нет. |
|||
|
||||
azesmcar |
|
|||
![]() uploading... ![]() ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 6291 Регистрация: 12.11.2004 Где: Армения Репутация: 5 Всего: 211 |
||||
|
||||
semibug |
|
|||
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 323 Регистрация: 27.3.2009 Репутация: нет Всего: нет |
Дело в том, что специально я не обрабатываю никак закрытие консольного окна по клику на крестик. Программа просто terminate-тится. По Alt-F4 ничего не происходит. Вот и думаю, где же вставить обработчик, для события, когда юзер закроет окошко мышью (сбрасываю некоторые данные на диск перед завершением проги). |
|||
|
||||
azesmcar |
|
|||
![]() uploading... ![]() ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 6291 Регистрация: 12.11.2004 Где: Армения Репутация: 5 Всего: 211 |
||||
|
||||
semibug |
|
|||
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 323 Регистрация: 27.3.2009 Репутация: нет Всего: нет |
Ну тогда скажем так: как отучить Windows терминэйтить программы без предупреждения по нажатию крестика. ( при этом консоль не зависла, никаких предупреждений о принудительном закрытии процесса винда не показывает) |
|||
|
||||
azesmcar |
|
|||
![]() uploading... ![]() ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 6291 Регистрация: 12.11.2004 Где: Армения Репутация: 5 Всего: 211 |
проверьте этот код
У меня работает. Это сообщение отредактировал(а) azesmcar - 30.5.2009, 17:47 |
|||
|
||||
semibug |
|
|||
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 323 Регистрация: 27.3.2009 Репутация: нет Всего: нет |
||||
|
||||
azesmcar |
|
|||
![]() uploading... ![]() ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 6291 Регистрация: 12.11.2004 Где: Армения Репутация: 5 Всего: 211 |
Ну...работает..вы проверили этот код? вот что говорит MSDN по этой функции.
Это сообщение отредактировал(а) azesmcar - 30.5.2009, 19:10 |
|||
|
||||
semibug |
|
|||
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 323 Регистрация: 27.3.2009 Репутация: нет Всего: нет |
c Runtime Library Multi-threaded Debug atexit не срабатывает. (с Runtime Library Multi-threaded Debug DLL) работает нормально. Visual Studio 2005.
|
|||
|
||||
azesmcar |
|
||||
![]() uploading... ![]() ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 6291 Регистрация: 12.11.2004 Где: Армения Репутация: 5 Всего: 211 |
Не нашел отличий. Добавлено через 1 минуту и 40 секунд У меня так и стоит (VS2008) и работает. Вот опции проекта.
Добавлено через 2 минуты и 5 секунд Скиньте проект куда нибудь, гляну. |
||||
|
|||||
semibug |
|
|||
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 323 Регистрация: 27.3.2009 Репутация: нет Всего: нет |
Странно. В моем случае стоит переключить на Runtime Library Multi-threaded Debug как перестаёт работать.
Попробую собрать проект на другой системе.. Это сообщение отредактировал(а) semibug - 30.5.2009, 19:35 Присоединённый файл ( Кол-во скачиваний: 4 ) ![]() |
|||
|
||||
azesmcar |
|
|||
![]() uploading... ![]() ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 6291 Регистрация: 12.11.2004 Где: Армения Репутация: 5 Всего: 211 |
semibug
Проверил, действительно не работает. Создал новый проект Win32 с дефолт настройками, проверил - работает. Я не знаю что вы там в настройках проекта изменили. Надо проверить, но по дефолту стоит Runtime Library Multi-threaded Debug DLL и работает..проверьте, я посмотрю разницу в настройках. Интересно в чем дело. |
|||
|
||||
semibug |
|
|||
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 323 Регистрация: 27.3.2009 Репутация: нет Всего: нет |
azesmcar,
Так же создал новый проект, из настроек поменял только Runtime Library (стояло DLL, поставил без ). После чего перестал срабатывать atexit (до изменения работал). Под перестал работать имею ввиду что не срабатывает, когда окно закрываем щелчком по крестику. Это сообщение отредактировал(а) semibug - 30.5.2009, 20:25 |
|||
|
||||
azesmcar |
|
|||
![]() uploading... ![]() ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 6291 Регистрация: 12.11.2004 Где: Армения Репутация: 5 Всего: 211 |
semibug
я и не замечал что там изменено..вроде то же самое, DLL слово маленькое, практически незаметное ![]() А зачем это надо если не секрет? Добавлено через 1 минуту и 20 секунд MSDN по этому поводу говорит вот что
при статической линковке может и не сработать. Тут C++ не виноват..зачем статически линковать CRT? |
|||
|
||||
jonie |
|
|||
Эксперт ![]() ![]() ![]() ![]() Профиль Группа: Завсегдатай Сообщений: 5613 Регистрация: 21.8.2005 Где: Владимир Репутация: 7 Всего: 118 |
т.к. винда то читайте про SetConsoleCtrlHandler и SetConsoleMode наверно...
-------------------- Что-то не поняли? -> Напейтесь до зеленых человечков... эта сверхцивилизация Вам поможет... |
|||
|
||||
azesmcar |
|
|||
![]() uploading... ![]() ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 6291 Регистрация: 12.11.2004 Где: Армения Репутация: 5 Всего: 211 |
есть еще microsoft extension _onexit, но я сомневаюсь что он сработает. При статической линковке надо подумать какие могут возникать проблемы и от чего, насчет atexit, _onexit MSDN ничего не говорит, но какие-то проблемы он предполагает.
Добавлено через 10 секунд http://msdn.microsoft.com/en-us/library/abx4dbyh(VS.80).aspx |
|||
|
||||
azesmcar |
|
||||
![]() uploading... ![]() ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 6291 Регистрация: 12.11.2004 Где: Армения Репутация: 5 Всего: 211 |
кстати да! Это идея semibug вот ваш код.
|
||||
|
|||||
semibug |
|
|||
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 323 Регистрация: 27.3.2009 Репутация: нет Всего: нет |
В проекте, где наткнулся на эту особенность уже и не вспомню кто и когда переключил тип линковки CRT (надо ещё в svn поковыряться). Для нового проекта - чисто из академических соображений переключил, ибо в дефолтовых условиях все работало ). Преогромнейшее спасибо. Работает. |
|||
|
||||
semibug |
|
|||
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 323 Регистрация: 27.3.2009 Репутация: нет Всего: нет |
В выше приведенном способе c SetConsoleCtrlHandler, Windows все равно убивает процесс через 5 секунд после нажатия на крестик (если вернуть TRUE в обработчике) . В принципе этого достаточно чтобы сохранить данные приложения на диск (не 100 процентов случаев) . Но на всякий случай отключил совсем действия крестика:
hm = GetSystemMenu( hWnd, FALSE ); DeleteMenu( hm, SC_CLOSE , MF_BYCOMMAND ); где hWnd- хэндл окна консольного приложения. |
|||
|
||||
azesmcar |
|
|||
![]() uploading... ![]() ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 6291 Регистрация: 12.11.2004 Где: Армения Репутация: 5 Всего: 211 |
msdn почитайте. Там же написано. Если вы сами обрабатываете команду - возвращайте TRUE, если нет - FALSE чтобы виндоуз передал команду следующему обработчику. Обработать команду не значит удалить свое меню а значит завешить свою программу так как указано в параметре. Просто делайте то что вам надо и всегда возвращайте FALSE. |
|||
|
||||
semibug |
|
|||
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 323 Регистрация: 27.3.2009 Репутация: нет Всего: нет |
azesmcar,
Дело в том, что если я не успеваю выполнить необходимые действия, Windows убивает процесс не дожидаясь завершения обработчика (либо выводит табличку о том, что прога зависла и предложит убить её). А отключение крестика, конечно не в обработчик закрытия вставил. А сразу после создания консоли. При этом необходимость обрабатывать закрытие окна отпадает. Это сообщение отредактировал(а) semibug - 31.5.2009, 17:18 |
|||
|
||||
azesmcar |
|
|||
![]() uploading... ![]() ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 6291 Регистрация: 12.11.2004 Где: Армения Репутация: 5 Всего: 211 |
Да..если долго думать виндоуз подумает что ваше приложение зависло..а чего вы так долго делаете то в обработчике? |
|||
|
||||
semibug |
|
|||
Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 323 Регистрация: 27.3.2009 Репутация: нет Всего: нет |
Да в общем то ничего особенного, сохраняю некоторые данные на диск. Это конечно много времени не занимает, но всяко разно. У меня, например, подключен к компу внешний диск WD MyBook, так он, если его не трогать отключается, а при попытки доступа к нему разгоняется долго. Хотелось однозначно завершить операцию. Рассматривал вариант с запуском небольшого отдельного процесса, который после смерти основного приложения займется работой по сохранению, но, сами понимаете, выглядит некультурно. Поэтому и остановился на полном запрещении отрубать прогу крестиком (для нормальнго завершения предусмотрены штатные средства в самом приложении). |
|||
|
||||
azesmcar |
|
|||
![]() uploading... ![]() ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 6291 Регистрация: 12.11.2004 Где: Армения Репутация: 5 Всего: 211 |
semibug
Вам надо подумать в сторону отмены закрытия приложения и закрытся самому как только все завершите Еще как вариант, просто закрыть консоль но не сам процесс. Это сообщение отредактировал(а) azesmcar - 31.5.2009, 17:45 |
|||
|
||||
GremlinProg |
|
|||
Эксперт ![]() ![]() ![]() ![]() Профиль Группа: Комодератор Сообщений: 2706 Регистрация: 9.8.2005 Где: Тюмень Репутация: 99 Всего: 106 |
попробуй поиграться с SetProcessShutdownParameters и флагом SHUTDOWN_NORETRY окошко показываться не должно, а вот на счет самоотмирания процесса, тут можно с первым параметром поработать тогда и Close затенять не придется (прикрыт процесс может быть не обязательно с кнопки) -------------------- "Гений всегда разумнее, чем умнее. Ум — это машина, разум — водитель этой машины." |
|||
|
||||
![]() ![]() ![]() |
Правила форума "C/C++: Системное программирование и WinAPI" | |
|
На данный раздел распространяются Правила форума и Правила раздела С++:Общие вопросы . Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Chipset, Step, Fixin, GremlinProg, xvr. feodorv. |
1 Пользователей читают эту тему (1 Гостей и 0 Скрытых Пользователей) | |
0 Пользователей: | |
« Предыдущая тема | C/C++: Системное программирование и WinAPI | Следующая тема » |
|
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности Powered by Invision Power Board(R) 1.3 © 2003 IPS, Inc. |