Форум программистов, компьютерный форум, киберфорум
C++ Builder
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.95/21: Рейтинг темы: голосов - 21, средняя оценка - 4.95
 Аватар для Kukstyler
1260 / 870 / 268
Регистрация: 02.04.2009
Сообщений: 3,307

Закрытие (уничтожение) дочерней Form

01.08.2013, 01:08. Показов 4777. Ответов 16
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
При закрытии Form методом Close() (вызванной из MainForm) - она скрывается но не уничтожается. Таким образом, на пример данные введённые в Edit1 на этой Form, при её повторном открытии сохраняются и событие FormCreate не происходит каждый раз как вызывается эта Form.

Нашёл на форуме следующие варианты:

C++
1
2
3
SendMessage(this->Handle,WM_CLOSE,NULL,NULL);
 
Perform(WM_CLOSE,NULL,NULL);
Эффект всё тот же. Так, как сделать, что бы Form при закрытии уничтожалась, а не просто скрывалась?

Заранее благодарю за ответы.
0
cpp_developer
Эксперт
20123 / 5690 / 1417
Регистрация: 09.04.2010
Сообщений: 22,546
Блог
01.08.2013, 01:08
Ответы с готовыми решениями:

Закрытие дочерней формы.
Пиплс. Есть проблема. Если в дочерней форме открывается другая форма, то при закрытии дочерней происходит ошибка. Если в дочерней...

Form load у дочерней формы не срабатывает
событие Form_Load у frm2 срабатывает только первый раз, при вызове frm2.Show() из родительской, если закрыть её, и снова вызывать,...

Закрытие дочерней формы возвращает DialogResult.Cancel
Здравствуйте товарищи. Ситуация такая: есть основная форма и с нее вызываю дочернюю FormFontColor f = new...

16
Супер-модератор
Эксперт Pascal/DelphiАвтор FAQ
 Аватар для volvo
33377 / 21501 / 8236
Регистрация: 22.10.2011
Сообщений: 36,896
Записей в блоге: 11
01.08.2013, 01:12
В обработчике OnClose формы параметру Action присвоить значение caFree, потому что дефолтным является caHide, это именно сокрытие формы, без ее уничтожения...
1
 Аватар для Kukstyler
1260 / 870 / 268
Регистрация: 02.04.2009
Сообщений: 3,307
01.08.2013, 01:57  [ТС]
Только что заметил, что код в событии FormCreate от дочернего окна исполняется при открытии (создании) MainForm... А как избавиться от этого? Выходит, все Form которые должны создаваться при их вызове, создаются уже при создании главного окна?!...

Добавлено через 23 минуты
Цитата Сообщение от UI Посмотреть сообщение
В обработчике OnClose формы параметру Action присвоить значение caFree, потому что дефолтным является caHide, это именно сокрытие формы, без ее уничтожения...
Присвоил:

C++
1
2
3
4
void __fastcall TForm3::FormClose(TObject *Sender, TCloseAction &Action)
{
 Action = caFree;
}
Реультат - после первого закрытия Form3, она уже не открывается, ошибка:

"Access Violation at address 5034F0E3 in module 'vcl150.bpl'. Read of address 00000010"

0
Супер-модератор
Эксперт Pascal/DelphiАвтор FAQ
 Аватар для volvo
33377 / 21501 / 8236
Регистрация: 22.10.2011
Сообщений: 36,896
Записей в блоге: 11
01.08.2013, 02:42
Цитата Сообщение от Kukstyler Посмотреть сообщение
Реультат - после первого закрытия Form3, она уже не открывается
Если форма при закрытии разрушается, то перед повторным показом ее надо пересоздать. Я бы вообще убрал дочернюю форму из списка автосоздаваемых (Project -> Options -> Forms), и показывал бы так:

C++
1
2
3
4
5
void __fastcall TForm1::Button1Click(TObject *Sender)
{
    Form3 = new TForm3(Application); // Создаем
    Form3->Show(); // и показываем...
}
, а удаляться форма будет автоматически, из-за caFree...
1
Практикантроп
 Аватар для nick42
4841 / 2726 / 534
Регистрация: 23.09.2011
Сообщений: 5,798
01.08.2013, 09:21
Цитата Сообщение от Kukstyler Посмотреть сообщение
Реультат - после первого закрытия Form3, она уже не открывается,
Следующая "комбинация" должна помочь (это код в обработчике кнопки открытия 3-й формы): __
C++
1
2
3
   if (!Form3) Application->CreateForm(__classid(TForm3), &Form3);
   Form3->ShowModal();
   delete Form3; Form3=NULL;
2
0 / 0 / 0
Регистрация: 25.01.2014
Сообщений: 14
02.02.2014, 11:28
В учебнике нашел следующую комбинацию, просто стандартная очистка формы при закрытии:
C++
1
2
3
4
5
void __fastcall TForm1::OpForm1(TObject *Sender)
{
    Form2=new TForm2(this);
    if (Form2->ShowModal()==mrCancel) return;
}
0
Эксперт С++
 Аватар для Avazart
8488 / 6155 / 615
Регистрация: 10.12.2010
Сообщений: 28,683
Записей в блоге: 30
02.02.2014, 14:04
Цитата Сообщение от Illogical man Посмотреть сообщение
В учебнике нашел следующую комбинацию, просто стандартная очистка формы при закрытии:
Будет утечка, нужен delete Form2, а лучше применить умный указатель.
0
Супер-модератор
Эксперт Pascal/DelphiАвтор FAQ
 Аватар для volvo
33377 / 21501 / 8236
Регистрация: 22.10.2011
Сообщений: 36,896
Записей в блоге: 11
02.02.2014, 14:09
Цитата Сообщение от Avazart Посмотреть сообщение
Будет утечка
Не будет. При удалении главной формы удалится и указатель, она ж его Owner...
0
Эксперт С++
 Аватар для Avazart
8488 / 6155 / 615
Регистрация: 10.12.2010
Сообщений: 28,683
Записей в блоге: 30
02.02.2014, 14:20
Цитата Сообщение от UI Посмотреть сообщение
Не будет. При удалении главной формы удалится и указатель, она ж его Owner...
Нет будет... ибо приложение может упасть от нехватки памяти еще до того как можно будет закрыть Owner-форму.
А удаление перед закрытием не несет большого смысла, так как скорее всего система итак почистит.
0
 Аватар для S0lexV
21 / 21 / 7
Регистрация: 27.07.2011
Сообщений: 330
09.04.2019, 09:41
Вопрос, пишу примерно тоже в firemonkey:
C++
1
2
3
4
 void __fastcall Twheelsform::FormClose(TObject *Sender, TCloseAction &Action)
{
 TCloseAction::caFree;
}
Результата нет, форма продолжает висеть в памяти
0
Эксперт С++
 Аватар для Avazart
8488 / 6155 / 615
Регистрация: 10.12.2010
Сообщений: 28,683
Записей в блоге: 30
09.04.2019, 09:57
Цитата Сообщение от S0lexV Посмотреть сообщение
Результата нет, форма продолжает висеть в памяти
Откуда вы знаете что она продолжает "висеть в памяти" ? Экстрасенс?
0
 Аватар для S0lexV
21 / 21 / 7
Регистрация: 27.07.2011
Сообщений: 330
09.04.2019, 10:29
Цитата Сообщение от Avazart Посмотреть сообщение
Откуда вы знаете что она продолжает "висеть в памяти" ? Экстрасенс?
Не нужно быть экстрасенсом, достаточно проявить смекалку: после закрытия формы обращаюсь к ней и она снова отображается, хотя должна быть ошибка Access violation. К тому же если посмотреть в диспетчере задач, объем памяти, занимаемый приложением не уменьшается при закрытии формы
0
Супер-модератор
Эксперт Pascal/DelphiАвтор FAQ
 Аватар для volvo
33377 / 21501 / 8236
Регистрация: 22.10.2011
Сообщений: 36,896
Записей в блоге: 11
09.04.2019, 11:21
Цитата Сообщение от S0lexV Посмотреть сообщение
после закрытия формы обращаюсь к ней и она снова отображается, хотя должна быть ошибка Access violation
С чего бы? Ты удалил форму, то есть, пометил память, занимаемую ей, как свободную. Но не обнулил указатель (ну не делает этого caFree, не делает). И тут же, без новых выделений памяти, чтобы что-то эту освобожденную память могло занять, пытаешься обратиться по тому же указателю, который не обнулен. Интересно, что будет? А ничего. Все будет работать точно так же, как и раньше. Пока какая-то функция не выделит память в том куске, где раньше располагалась форма. Вот тогда действительно будет AV.

Цитата Сообщение от S0lexV Посмотреть сообщение
объем памяти, занимаемый приложением не уменьшается при закрытии формы
Да сколько раз повторять можно, что TaskManager вообще лучше всего выкинуть, и никогда на него не полагаться в вопросах об утечках? Минимизируй приложение безо всяких удалений форм, и посмотри, насколько изменится объем занимаемой памяти. Иногда - чуть ли не на порядок. Не тот инструмент, чтобы ему доверять.
0
 Аватар для Lelik-pahan
1703 / 899 / 207
Регистрация: 25.11.2009
Сообщений: 1,848
09.04.2019, 11:31
не
Цитата Сообщение от S0lexV Посмотреть сообщение
void __fastcall Twheelsform::FormClose(TObject *Sender, TCloseAction &Action)
{
TCloseAction::caFree;
}
а
C++
1
2
3
4
void __fastcall Twheelsform::FormClose(TObject *Sender, TCloseAction &Action)
{
    Action = caFree;  //или Action = TCloseAction::caFree;
}
0
 Аватар для S0lexV
21 / 21 / 7
Регистрация: 27.07.2011
Сообщений: 330
09.04.2019, 11:53
Цитата Сообщение от Lelik-pahan Посмотреть сообщение
не


а
C++
1
2
3
4
void __fastcall Twheelsform::FormClose(TObject *Sender, TCloseAction &Action)
{
    Action = caFree;  //или Action = TCloseAction::caFree;
}
C++
1
Action =TCloseAction::caFree;
Вот так работает, и ошибка начала появлятся при повторном обращении, значит память точно очистилась

Добавлено через 10 минут
Цитата Сообщение от volvo Посмотреть сообщение
С чего бы? Ты удалил форму, то есть, пометил память, занимаемую ей, как свободную. Но не обнулил указатель (ну не делает этого caFree, не делает). И тут же, без новых выделений памяти, чтобы что-то эту освобожденную память могло занять, пытаешься обратиться по тому же указателю, который не обнулен. Интересно, что будет? А ничего. Все будет работать точно так же, как и раньше. Пока какая-то функция не выделит память в том куске, где раньше располагалась форма. Вот тогда действительно будет AV.

Да сколько раз повторять можно, что TaskManager вообще лучше всего выкинуть, и никогда на него не полагаться в вопросах об утечках? Минимизируй приложение безо всяких удалений форм, и посмотри, насколько изменится объем занимаемой памяти. Иногда - чуть ли не на порядок. Не тот инструмент, чтобы ему доверять.
Спасибо за содержательный ответ,учту
0
Эксперт С++
 Аватар для Avazart
8488 / 6155 / 615
Регистрация: 10.12.2010
Сообщений: 28,683
Записей в блоге: 30
09.04.2019, 12:00
Цитата Сообщение от S0lexV Посмотреть сообщение
Не нужно быть экстрасенсом, достаточно проявить смекалку: после закрытия формы обращаюсь к ней и она снова отображается, хотя должна быть ошибка Access violation. К тому же если посмотреть в диспетчере задач, объем памяти, занимаемый приложением не уменьшается при закрытии формы
Не должна. Просто так карты легли )))
Учите матчасть.
0
 Аватар для S0lexV
21 / 21 / 7
Регистрация: 27.07.2011
Сообщений: 330
09.04.2019, 16:36
Вообщем вот такой подход будет правильным ?
По необходимости вызываем форму:
C++
1
2
Application->CreateForm(__classid(Twheelsform), &wheelsform);
wheelsform->ShowModal();
Через какую нибудь кнопку закрываем форму:
C++
1
2
3
4
void __fastcall Twheelsform::gggClick(TObject *Sender)
{
wheelsform->Close();
}
В обработчике OnClose:
C++
1
2
3
4
void __fastcall Twheelsform::FormClose(TObject *Sender, TCloseAction &Action)
{
 Action = TCloseAction::caFree; 
}
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
raxper
Эксперт
30234 / 6612 / 1498
Регистрация: 28.12.2010
Сообщений: 21,154
Блог
09.04.2019, 16:36
Помогаю со студенческими работами здесь

Закрытие форм при закрытии дочерней формы
Имеется две формы Form1.h и Form2.h. Как сделать так, чтобы при закрытии второй(дочерней) формы закрывались обе??? Пробовал так не...

Не работает событие при закрытие дочерней формы
Добрый день, не могу решить данную проблему. При закрытии дочерней формы должны оставаться данные которые отображаються в datagridview,...

Закрытие всех Form
Здравствуйте! Как при нажатии кнопки закрыть все открытые формы?

Закрытие Form 1 без причины
Добрый день, может кто помочь, не понимаю в чём проблема. При попытке перехода на Form 1. Форма показывается на 2 секунды и обратно...

Windows Form, открытие и закрытие форм
Здравствуйте, Делаю одну штуку на C# и в Windows Forms возник небольшой вопросик: Что нужно прописать, чтобы при открытии новой формы...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
17
Ответ Создать тему
Новые блоги и статьи
SDL3 для Web (WebAssembly): сборка C/C++ проекта из консоли
8Observer8 31.01.2026
Содержание блога Если вы откроете примеры для начинающих на официальном репозитории SDL3 в папке: examples, то вы увидите, что все примеры используют следующие четыре обязательные функции, а. . .
Установка Emscripten SDK (emsdk) и CMake на Windows для сборки C и C++ приложений в WebAssembly (Wasm)
8Observer8 30.01.2026
Чтобы скачать Emscripten SDK (emsdk) необходимо сначало скачать и уставить Git: Install for Windows. Следуйте стандартной процедуре установки Git через установщик. Система контроля версиями Git. . .
Подключение Box2D v3 к SDL3 для Android: физика и отрисовка коллайдеров
8Observer8 29.01.2026
Содержание блога Box2D - это библиотека для 2D физики для анимаций и игр. С её помощью можно определять были ли коллизии между конкретными объектами. Версия v3 была полностью переписана на Си, в. . .
Инструменты COM: Сохранение данный из VARIANT в файл и загрузка из файла в VARIANT
bedvit 28.01.2026
Сохранение базовых типов COM и массивов (одномерных или двухмерных) любой вложенности (деревья) в файл, с возможностью выбора алгоритмов сжатия и шифрования. Часть библиотеки BedvitCOM Использованы. . .
Загрузка PNG с альфа-каналом на SDL3 для Android: с помощью SDL_LoadPNG (без SDL3_image)
8Observer8 28.01.2026
Содержание блога SDL3 имеет собственные средства для загрузки и отображения PNG-файлов с альфа-каналом и базовой работы с ними. В этой инструкции используется функция SDL_LoadPNG(), которая. . .
Загрузка PNG с альфа-каналом на SDL3 для Android: с помощью SDL3_image
8Observer8 27.01.2026
Содержание блога SDL3_image - это библиотека для загрузки и работы с изображениями. Эта пошаговая инструкция покажет, как загрузить и вывести на экран смартфона картинку с альфа-каналом, то есть с. . .
Влияние грибов на сукцессию
anaschu 26.01.2026
Бифуркационные изменения массы гриба происходят тогда, когда мы уменьшаем массу компоста в 10 раз, а скорость прироста биомассы уменьшаем в три раза. Скорость прироста биомассы может уменьшаться за. . .
Воспроизведение звукового файла с помощью SDL3_mixer при касании экрана Android
8Observer8 26.01.2026
Содержание блога SDL3_mixer - это библиотека я для воспроизведения аудио. В отличие от инструкции по добавлению текста код по проигрыванию звука уже содержится в шаблоне примера. Нужно только. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru