Текущий архив: 2009.06.14;
Скачать: CL | DM;
Вниз
Это баг в формах? Найти похожие ветки
← →
Internal Tracking (2009-04-02 22:17) [0]Запостил тут бяку одну на саппорт. Форма не закрывается при вызове Close. Я уверен что это баг, но возможно я ошибаюсь? Посмотрите pls
http://qc.embarcadero.com/wc/qcmain.aspx?d=72693
← →
Internal Tracking (2009-04-02 22:18) [1]D2009
← →
boa_kaa © (2009-04-02 22:44) [2]верни свою бяку обратно и не трепли нервы саппорту по причине неумения работать с хелпом
← →
KilkennyCat © (2009-04-02 22:47) [3]
> верни свою бяку обратно
любопытно, с точки зрения копрофагии...
← →
Internal Tracking (2009-04-02 23:29) [4]
> верни свою бяку обратно и не трепли нервы саппорту по причине
> неумения работать с хелпом
А почему это я не могу юзать подобную конструкцию?
Я работаю в главном потоке.
Я запускаю вторую форму, в ней в OnShow отображаю Processing и вызываю свою функцию.. После окончания функции, я опять выхожу в OnShow и вызываю Close формы. что тут не правильного? А как тогда правильно?
← →
Internal Tracking (2009-04-02 23:36) [5]Далее, смотрим в хелп OnShow - написано:
Occurs when the form is shown (that is, when its Visible property is set to true).
Use OnShow to perform special processing when the form is shown (that is, when the form"s Visible property is set to true).
Где тут написано подобное про Close или ModalResult ?
Если вы правы, тогда объясните, чтобы не быть голословным.
Вторая форма в данном случае, без заголовка, на ней только Label для отображения текста "Processing".
← →
Internal Tracking (2009-04-02 23:40) [6]
> по причине неумения работать с хелпом
Так, также посмотрел хелп по ModalResult и Close. Ничего подобного не написано.
← →
wicked © (2009-04-02 23:51) [7]это баг в твоем коде - так делать нельзя
ембаркадеры не обязаны править баги в коде пользователя
← →
turbouser © (2009-04-02 23:58) [8]
> Internal Tracking (02.04.09 23:40) [6]
Попробуй закрыть закрытую дверь.
← →
жж (2009-04-03 00:00) [9]как сделать правильно:
после того, как в OnShow сделал что надо, отправляй сам себе сообщение "закройся", на Self.Handle, тока обязательно с помощью PostMessage.
а вообще паттер дурной весьма - закрывать в OnShow
← →
Internal Tracking (2009-04-03 00:07) [10]
> после того, как в OnShow сделал что надо, отправляй сам
> себе сообщение "закройся", на Self.Handle, тока обязательно
> с помощью PostMessage.
> а вообще паттер дурной весьма - закрывать в OnShow
Да почему ж дурной!? Почему? Ведь фактически я ведь ставлю ModalResult. Разве его (ModalResult) нельзя менять в OnShow?
Т.е. отправлять WM_CLOSE я могу, а вот менять ModalResult нет . Ну не глупо ли?
>
> > wicked © (02.04.09 23:51) [7]
>
> это баг в твоем коде - так делать нельзя
Елки палки, дык объясните почему!
← →
Internal Tracking (2009-04-03 00:21) [11]
> wicked © (02.04.09 23:51) [7]
Просто объясните почему.
1. В техническом плане - это не опасно (Ни AV, ни ошибок синхронизации итп). и даже не предсказывается, при работе с основным потоком.
2. Этические соображения (грязный или непонятный код, путанница, итп) - также не не то.. Здесь все на ладони.
Расскажите тогда, в чем проблема этого кода, и почему это не баг?
← →
жж (2009-04-03 00:25) [12]
>
> Т.е. отправлять WM_CLOSE я могу, а вот менять ModalResult
> нет . Ну не глупо ли?
>
Нет, и то, и то - дурной тон, просто в одном случае работает, а в другом нет
← →
жж (2009-04-03 00:28) [13]
> Да почему ж дурной!? Почему?
потому, что "форма прогресса" должна показывать результаты какого - то процесса, а не выполнять сам процесс.
А что касается того, почему борланд не сделал - вопрос философский. Не сделал, это данность. И не сделает
← →
Кто б сомневался © (2009-04-03 00:42) [14]C точки зренимя правильности - это явный баг.
ModalResult программист действительно может изменить в OnShow, мало ли.
Я еще понимаю в OnCreate это делать нельзя, - можно понять, но в OnShow..
> Не сделал, это данность. И не сделает
Кстати, там всего то нужно перетащить "ModalResult := 0" на 4 строчки вверх, до вызова Show. Не знаю как в других Delphi, сейчас посмотреть не могу, у меня тоже 2009.
> что "форма прогресса" должна показывать результаты какого
> - то процесса
Да ну? Серьезно? Это что конструктор форм, или а-ля скрипт в Word"e?
← →
Германн © (2009-04-03 00:51) [15]
> Кто б сомневался © (03.04.09 00:42) [14]
>
> C точки зренимя правильности - это явный баг.
> ModalResult программист действительно может изменить в OnShow,
> мало ли.
Нормальный программист понимает, что модальное окно - суть диалог с пользователем. И не станет "сваливать" на "мало ли что".
А пример с использованием Splash поставляется ещё со времен Д1.
← →
Internal Tracking (2009-04-03 00:53) [16]
> потому, что "форма прогресса" должна показывать результаты
> какого - то процесса, а не выполнять сам процесс.
Форма ничего не выполняет.
Я ж объяснил. В OnShow формы вызывается метод другого класса.
Но т.к. это все выполняется в одном потоке, - т.е. главном, - по окончании этого метода, опять возвращаемся в OnShow,
N/е.
procedure TForm2.FormShow(Sender: TObject);
begin
MyLabel.Caption := "Processing"
OtherClass.ProcessSomth; // около 3-8 сек
ModalResult := mrOk. // ну или другое, - это для примера
end;
← →
turbouser © (2009-04-03 01:04) [17]
> Internal Tracking (03.04.09 00:53) [16]
> Форма ничего не выполняет.
На кой она вообще тогда нужна?
> odalResult := mrOk. // ну или другое, - это для примера
>
См.
> turbouser © (02.04.09 23:58) [8]
> Кто б сомневался © (03.04.09 00:42) [14]
>
> C точки зренимя правильности - это явный баг.
Баг заключается в том, что иде не ругается на Close и ModalResult := ... etc
← →
Кто б сомневался © (2009-04-03 01:18) [18]
> Нормальный программист понимает, что модальное окно - суть
> диалог с пользователем. И не станет "сваливать" на "мало
> ли что".
Да ну ладно рассказывать.
Допустим есть варианты - т.е. отображается текст мол "работаю..." и там пару кнопок. И все делается в одном потоке (бывает что операция не занимает много времени). Юзер может нажать на копку, а может и не нажать. Что ж сваливать весь код на главную форму со всеми событиями и оттуда выставлять Caption второй формы? Туповато как-то.
ИМХО логичнее разгруппировать - меньше путанницы. Второй форме передать нужный класс и вперед. Я пойму еще если там нужно только отображать текст Processing - как у автора, но если там больше действий.
Кстати, причину почему так нельзя делать, кроме как "так сказал Аллах Всевышний (мир ему и благословение)", так никто и не назвал.
← →
Германн © (2009-04-03 01:26) [19]
> Кто б сомневался © (03.04.09 01:18) [18]
>
>
> > Нормальный программист понимает, что модальное окно -
> суть
> > диалог с пользователем. И не станет "сваливать" на "мало
> > ли что".
>
>
> Да ну ладно рассказывать.
> Допустим есть варианты - т.е. отображается текст мол "работаю.
> .." и там пару кнопок. И все делается в одном потоке (бывает
> что операция не занимает много времени). Юзер может нажать
> на копку, а может и не нажать.
Да ну ладно придумывать всякую чушь оправдывающую "криворукость".
← →
Германн © (2009-04-03 01:29) [20]
> Кто б сомневался © (03.04.09 01:18) [18]
>
> Кстати, причину почему так нельзя делать, кроме как "так
> сказал Аллах Всевышний (мир ему и благословение)", так никто
> и не назвал.
>
Тогда я назову.
Потому что нормальные люди думают нормально. А все бредовые идеи предусмотреть просто не реально.
← →
Германн © (2009-04-03 01:41) [21]Кстати.
А о чём тут спор?
Обратите внимание на то, как автор описал Reproduce:
procedure TForm1.FormShow(Sender: TObject);
begin
form2 := TForm2.Create(Application);
Form2.ShowModal;
end;
И не упомянул при этом, что TForm2 он убрал из списка "Автосоздание"!
← →
Кто б сомневался © (2009-04-03 02:10) [22]
Германн ©
> Да ну ладно придумывать всякую чушь оправдывающую "криворукость".
Ну какие же они бредовые еклм?
Берем вариант афтара, - форма с label, но добавляем туда кнопку.
Все крутится в одном потоке. Обновляется через Application.ProcessMesages.
В OnShow стартуем. Жмем на кнопку, и опа, а закрыться то мы не можем легально, т.к. ModalResult не работает корректно - он обнуляется после выхода в OnShow.
Прежде чем кричать, предожите не бредовый вариант, я посмотрю..
Один поток конечно, - основной, не забывайте.
← →
Кто б сомневался © (2009-04-03 02:14) [23]
> И не упомянул при этом, что TForm2 он убрал из списка "Автосоздание"!
Боже, да причем здесь автосоздание. Ведь ModalResult обнуляется после выхода с OnShow, что с автосозданием, что без него.
← →
AndreyV © (2009-04-03 08:26) [24]> [18] Кто б сомневался © (03.04.09 01:18)
> ИМХО логичнее разгруппировать - меньше путанницы. Второй
> форме передать нужный класс и вперед.
Создать экземпляр нужного класса вызваеть его метод, а уж он, если ему надо, создаёт вторую форму "Прогресс", показывает её немодально и занимается с ней. По нажатию кномки вторая форма не закрывается сама, а выставляет флаг КнопкаБылаНажата, который проверяется создавшим её и форма закрывается им же.
← →
KSergey © (2009-04-03 10:00) [25]Нужно понимать, что те или иные обработчики событий не предназначены для запихивания в них любого кода, пропускаемого компилятором. Есть правила использования, и это нормально, а отнюдь не ограничение свобод личности, гы гы.
Для решения задачи автора есть другие методы, упирать на этот - совершенно нет смысла. Данный обработчик вовсе не про то. И так было всегда в дельфи, из ShowModal вызывать Close нельзя. И аллах тут ни при чем, есть интерфейс.
← →
KSergey © (2009-04-03 10:03) [26]Я, кстати, сильно пдозреваю, что борланды данный код написали не от балды. Наверняка соотв. сообщение Windows (от которого в итоге этот обработчк и растёт) другого просто не допускает, так что тем, кто предлагает патчи к генофонду есть смысл попробовать сработает ли такое решение. Это не сложно. (может и сработает, конечно, я не проверял)
← →
clickmaker © (2009-04-03 11:42) [27]> procedure TForm2.FormShow(Sender: TObject);
> begin
> MyLabel.Caption := "Processing"
> OtherClass.ProcessSomth; // около 3-8 сек
>
> ModalResult := mrOk. // ну или другое, - это для примера
>
> end;
Form2 := TForm2.Create(Application);
try
Form2.MyLabel.Caption := "Processing";
Form2.Show;
OtherClass.ProcessSomth;
finally
Form2.Free;
end;
почему бы не быть проще? чтоб к тебе потянулись люди
← →
Кто б сомневался © (2009-04-03 14:13) [28]
> Создать экземпляр нужного класса вызваеть его метод, а уж
> он, если ему надо, создаёт вторую форму "Прогресс", показывает
> её немодально и занимается с ней.
Это уже обход ошибки. Кстати, так лучше не делать - не надо перемешивать рабочие классы, с формами. Формы должны вызывать методы классов, а не наоборот.
> clickmaker © (03.04.09 11:42) [27]
The same.
> Я, кстати, сильно пдозреваю, что борланды данный код написали
> не от балды.
На деле если перенести ModalResult := 0 выше Show ничего не изменится.
Так что никакой балды здесь я не вижу.
И вообще не пойму почему программист не может менять ModalResult в OnShow?
>
> анный обработчик вовсе не про то. И так было всегда в дельфи,
> из ShowModal вызывать Close нельзя.
Обычно если нельзя, пишут в хелпе, чего там нет.
← →
test © (2009-04-03 14:17) [29]clickmaker © (03.04.09 11:42) [27]
Form2.Show; == Form2.ShowModal;?
А то чревато ошибками, пользователь будет за окном гоняться.
← →
clickmaker © (2009-04-03 14:28) [30]> И вообще не пойму почему программист не может менять ModalResult
> в OnShow?
загляни в Forms.pas - ShowModal
Show;
try
SendMessage(Handle, CM_ACTIVATE, 0, 0);
ModalResult := 0;
repeat
...
until ModalResult <> 0;
← →
AndreyV © (2009-04-03 14:38) [31]> [28] Кто б сомневался © (03.04.09 14:13)
>
> > Создать экземпляр нужного класса вызваеть его метод, а уж
> > он, если ему надо, создаёт вторую форму "Прогресс", показывает
> > её немодально и занимается с ней.
>
> Кстати, так лучше не делать - не надо
> перемешивать рабочие классы, с формами. Формы должны вызывать
> методы классов, а не наоборот.
Никакой класс, кроме "рабочего", не знает что и когда отображать на форме, работать с экземплярами класса которой могут и должны все подобные этому. Это о форме типа "Прогресс бар", смене её заколовка, изменении позиции индикатора, через методы типа StepIt() и подобные.
← →
Anatoly Podgoretsky © (2009-04-03 14:56) [32]> clickmaker (03.04.2009 14:28:30) [30]
Все прекрасно и правильно написано. Все логично.
← →
Кто б сомневался © (2009-04-03 14:58) [33]
> clickmaker © (03.04.09 14:28) [30]
>
> > И вообще не пойму почему программист не может менять ModalResult
>
> > в OnShow?
>
> загляни в Forms.pas - ShowModal
Здрасьте, этот код еще автор в начале написал (в ссылке). в этом то и баг. Проснулся... :)
> AndreyV © (03.04.09 14:38) [31]
> Никакой класс, кроме "рабочего", не знает что и когда отображать
> на форме, работать с экземплярами класса которой могут и
> должны все подобные этому. Это о форме типа "Прогресс бар",
> смене её заколовка, изменении позиции индикатора, через
> методы типа StepIt() и подобные.
Это делается при помощи событий. Т.е. клас возбужает событие, которое перехватывает форма. - типа MyClass.OnChangeItem итп. Так как вы предложили, не делается - по очевидным соображением (путанница, грязный код, класс заточен только под форму итп..).
← →
Кто б сомневался © (2009-04-03 15:03) [34]
> Anatoly Podgoretsky © (03.04.09 14:56) [32]
Кто б сомневался © (03.04.09 02:10) [22] =
не работает - хотя вариант вполне легальный и правильный.
Вобщем я понял. Раз Borland и CodeGear не исправили этот баг, значит он автоматом становиться фичей (мысль стандартного программиста - ну куда уж мне давать советы самому Borland\CodeGear - ведь там сидять киборги которые никогда не ошибаются... Поэтому буду как вся масса говорить - да нету там бага, "Все прекрасно и правильно написано. Все логично.").
И причину никто пока не объяснил, хотя вот уже вторая страница пошла. Зато все говорят [32]
← →
clickmaker © (2009-04-03 15:05) [35]> Здрасьте, этот код еще автор в начале написал (в ссылке)
> .
мне иногда лениво по ссылкам тыцать )
и что, было лучше, если б там так было:
ModalResult := 0;
Show;
if ModalResult <> 0 then CloseModal;
try
if ModalResult = 0 then
SendMessage(Handle, CM_ACTIVATE, 0, 0);
if ModalResult <> 0 then CloseModal;
while ModalResult = 0 do begin
...
не слишком ли много проверок?
← →
AndreyV © (2009-04-03 15:05) [36]> [33] Кто б сомневался © (03.04.09 14:58)
> Так как вы предложили, не делается - по очевидным соображением
> (путанница, грязный код, класс заточен только под форму
> итп..).
Наверно, мы говорим о разном.
Класс ПрогрессБар один для всех, все знают о способах работы с ним.
← →
Кто б сомневался © (2009-04-03 15:34) [37]
> clickmaker © (03.04.09 15:05) [35]
> и что, было лучше, если б там так было:
Ох, представляю какой код вы пишите...
Вот оригинальный код:
Show;
try
SendMessage(Handle, CM_ACTIVATE, 0, 0);
ModalResult := 0;
repeat
Application.HandleMessage;
if Application.Terminated then ModalResult := mrCancel
else
if ModalResult <> 0 then CloseModal;
until ModalResult <> 0;
Result := ModalResult;
Простое перемещение
ModalResult := 0;
Show;
try
SendMessage(Handle, CM_ACTIVATE, 0, 0);
repeat
Application.HandleMessage;
if Application.Terminated then ModalResult := mrCancel
else
if ModalResult <> 0 then CloseModal;
until ModalResult <> 0;
Result := ModalResult;
Т.е. просто переносим ModalResult и ставим перед Show. Абсолютно никаких побочек, изменений в старых программах, в новых втч. итд. И баг исправлен.
← →
clickmaker © (2009-04-03 15:41) [38]> Т.е. просто переносим ModalResult и ставим перед Show
а если мы в OnShow его изменили?
Зачем тогда SendMessage(Handle, CM_ACTIVATE, 0, 0), вход в цикл, Application.HandleMessage ?
← →
Кто б сомневался © (2009-04-03 15:44) [39]
> AndreyV © (03.04.09 15:05) [36]
>
> > [33] Кто б сомневался © (03.04.09 14:58)
> > Так как вы предложили, не делается - по очевидным соображением
>
> > (путанница, грязный код, класс заточен только под форму
>
> > итп..).
>
> Наверно, мы говорим о разном.
> Класс ПрогрессБар один для всех, все знают о способах работы
> с ним.
Ну насколько я понял, вы предлагаете из какого то класса, запускать форму и из класса ставить значения форме (а не из формы запускать класс, а затем реагировать на события класса, которые устанавливают значения в форме).
Вот я об этом. А с прогресс баром я работаю как и все - т.е. просто устанавливаю Position и все.
← →
Кто б сомневался © (2009-04-03 15:46) [40]
> Зачем тогда SendMessage(Handle, CM_ACTIVATE, 0, 0), вход
> в цикл, Application.HandleMessage ?
Для того чтобы гарантированно отработали другие события - типа OnActivate и то что в очереди сообщений итп.
← →
clickmaker © (2009-04-03 15:52) [41]> чтобы гарантированно отработали другие события - типа OnActivate
а не кажется, что логика хромает? форма практически одной ногой в могиле, а мы вызываем событие активации
← →
Кто б сомневался © (2009-04-03 16:01) [42]
> а не кажется, что логика хромает? форма практически одной
> ногой в могиле, а мы вызываем событие активации
нет, все вполне логично, вариант, который есть правильный - в [22] работает.
Тогда в оригинальном коде, по вашей логике давайте уберем и эту строку:
ModalResult := 0;
repeat
Application.HandleMessage; << "ведь может быть уже в могиле форма"
if Application.Terminated then ModalResult := mrCancel
else
if ModalResult <> 0 then CloseModal;
until ModalResult <> 0;
Result := ModalResult;
Не пойму почему вас так смущает изменение ModalResult в OnShow?
← →
clickmaker © (2009-04-03 16:05) [43]> Не пойму почему вас так смущает изменение ModalResult в
> OnShow?
потому что нарушается жизненный цикл формы, на котором может быть построена логика другого кода.
Форма должна пройти Oncreate-OnShow-OnActivate-OnPaint
а вот потом - все что угодно
Вообще проблема высосана из пальца. Есть более изящные решения, в т.ч. и с отдельным потоком.
← →
Кто б сомневался © (2009-04-03 16:09) [44]
> Есть более изящные решения, в т.ч. и с отдельным потоком.
Ну приведите мне, хоть одно. Только с одним потоком. И модальной формой (чтобы с другой формой нельзя было работать.).
> потому что нарушается жизненный цикл формы, на котором может
> быть построена логика другого кода.
С чего вы взяли, ничего не нарушается.
← →
clickmaker © (2009-04-03 16:23) [45]с кодом [16] мы вообще рискуем увидеть мелькающую форму на мгновение. И не успеем даже прочитать, что у нас там Processing. И ModalResult особого смысла там не имеет вообще.
А все из-за того, что вторглись в жизненный цикл формы, и не дав ей до конца появиться, запустили некую модальную задачу.
← →
Кто б сомневался © (2009-04-03 16:36) [46]
> с кодом [16] мы вообще рискуем увидеть мелькающую форму
> на мгновение. И не успеем даже прочитать, что у нас там
> Processing.
Слушайте, вы уже начинаете выдумывать.
Причем здесь длительность Processing?
Мигнет она, при условии что операция обработки будет недолгая, а если она будет секунд 10-50? - Ведь это все будет крутиться в OnShow. И только по окончании обработки мы выходим с OnShow.
Ксати, форма также мелькнет и в оригинальном варианте, если ее сразу закрыть.. Тут все зависит от того, сколько времени занимает обработка.
← →
Anatoly Podgoretsky © (2009-04-03 16:42) [47]> Кто б сомневался (03.04.2009 16:36:46) [46]
Зачем нужна форма?
← →
clickmaker © (2009-04-03 16:47) [48]> Мигнет она, при условии что операция обработки будет недолгая,
> а если она будет секунд 10-50?
10-50 секунд юзер будет тупо втыкать в как бы зависшую программу, потом на мгновение мелькнет форма с надписью Processing.
Если у юзера орлинный глаз - таки да, может, он и успеет прочитать о том, что оказывается что-то там было Processing
← →
Кто б сомневался © (2009-04-03 16:58) [49]
> 10-50 секунд юзер будет тупо втыкать в как бы зависшую программу,
> потом на мгновение мелькнет форма с надписью Processing.
>
Application.processmessages там будет, ясен пень...
> Зачем нужна форма?
Это уже к ТЗ.
Но это часто бывает нужно. К примеру если обработка небольшая, к примеру секунд 10-30. и нужно написать "Подождите" или Processing... Wait x. Форма конечно без заголовка - bsNone.
← →
clickmaker © (2009-04-03 17:04) [50]> Application.processmessages там будет, ясен пень...
ага. Открываются новые подробности. То есть какой-то метод некоего класса (причем, может быть, из чужой DLL, да еще написанной на С, к примеру) должен еще знать, что ему периодически надо пинать какую-то форму путем Application.processmessages...
← →
clickmaker © (2009-04-03 17:15) [51]> путем Application.processmessages...
которая, кстати, и не поможет
Потому что мы вызовом модального метода именно в OnShow перекрыли поток остальных сообщений.
Нечего будет processmessages
← →
Кто б сомневался © (2009-04-03 17:17) [52]
> ага. Открываются новые подробности. То есть какой-то метод
> некоего класса (причем, может быть, из чужой DLL, да еще
> написанной на С, к примеру) должен еще знать, что ему периодически
> надо пинать какую-то форму путем Application.processmessages.
> ..
Если закончились аргументы, лучше молчите. А лучше ответьте на [44].
Во первых всегда идет какое то событие прогресса, - изменение прогресса, изменение текущего элемента итп. Если же нет (кстати это уже корректно), то можно просто раз вызвать processmessages до вызова обработки. Тогда обработка должна быть короткой, до 10 сек.
Я еще раз повторяю, это не для длительного процесса.
Для длительного прогресс бар, и поток.
← →
clickmaker © (2009-04-03 17:19) [53]> А лучше ответьте
procedure TForm2.FormActivate(Sender: TObject);
begin
Label1.Caption := "Processing...";
Update;
OtherClass.ProcessSomth;
PostMessage(Handle, WM_SYSCOMMAND, SC_CLOSE, 0);
end;
что-то более красивое недосуг писать. Я бы в потоке сделал
← →
Кто б сомневался © (2009-04-03 17:20) [54]
> Если же нет (кстати это уже корректно), то можно просто
> раз вызвать processmessages до вызова обработки
Опять же здесь лучше второй поток. Условия разные понимаете? Я про Фому, а мне опять про Ярему.
← →
Кто б сомневался © (2009-04-03 17:26) [55]
> clickmaker © (03.04.09 17:19) [53]
>
> > А лучше ответьте
>
> procedure TForm2.FormActivate(Sender: TObject);
> begin
> Label1.Caption := "Processing...";
> Update;
> OtherClass.ProcessSomth;
> PostMessage(Handle, WM_SYSCOMMAND, SC_CLOSE, 0);
> end;
>
> что-то более красивое недосуг писать. Я бы в потоке сделал
ну вот вы и подвердили то что надо было.
Обошли баг отсылкой сообщения.
В потоке - ну вот например мне надо было запустить 3-5 программ, я пишу "подождите" и запускаю их. Я знаю что это займет около 3-5 секунд. Ну не серьезно это переносить на второй поток. Не серьезно и не практично.
← →
Кто б сомневался © (2009-04-03 17:28) [56]
> [55]
Кстати, опять же здесь лучше OnShow, а не OnActivate по понятной причине.
← →
clickmaker © (2009-04-03 17:32) [57]> опять же здесь лучше OnShow
не заработает. Форма не отобразится, хоть 10 Application.processmessages вставь
← →
Кто б сомневался © (2009-04-03 17:32) [58]В [52] ошибка. Отметил жирным.
Если же нет (кстати это уже не корректно- т.е. не отдавать текущий прогерсс), то можно просто раз вызвать processmessages до вызова обработки.
← →
clickmaker © (2009-04-03 17:39) [59]можно еще метод вызвать по таймеру.
Можно в обработчике своего WM_CALL_SOME_METHOD, посланного путем PostMessage
можно просто панель положить невидимую, если заголовок не нужен, и показывать на время работы
можно в заголовке или в статус-баре основной формы писать Processing. Если прогресс нафиг не нужен, то так часто делают
варианты есть, поэтому я упорно продолжаю считать, что проблема, которой автор напряг QC, высосана из пальца )
← →
Кто б сомневался © (2009-04-03 17:48) [60]
> не заработает. Форма не отобразится, хоть 10 Application.
> processmessages вставь
Я думал что по OnShow ее уже видно.
Суть не меняется. OnActivate и close по тому варианту не выполнишь также, т.к. обнуляется уже после активации. Корректный вариант методами VCL - это только второй поток. ИМХО баг остается.
← →
Кто б сомневался © (2009-04-03 17:53) [61]
> можно еще метод вызвать по таймеру.
>>WM_CALL_SOME_METHOD
Можно, но это все варианты обхода официального метода - close, который здесь не работает. C таймером - это мудреж, честно говоря,.
← →
Кто б сомневался © (2009-04-03 18:01) [62]
> варианты есть, поэтому я упорно продолжаю считать, что проблема,
> которой автор напряг QC, высосана из пальца )
Слушайте, какие варианты? вы предлагаете варианта обхода этого бага.
Цель - закрыть форму processing как только закончиться обработка.
Вы ее и закрываете теми самыми вариантами, вместо корректного close
решение - второй поток. Но он здесь не нужен, т.к. обработка в пределах нескольких секунд. Вариант отображать где то на главной форме, не удачный, т.к. юзер должен сразу увидеть что начался процесс обработки.
← →
clickmaker © (2009-04-03 18:18) [63]procedure CallMethodWithSimpleProgressForm(AOwnerForm: TForm);
var
PrForm: TSimpleProgressForm;
p: pointer;
begin
p := DisableTaskWindows(0);
PrForm := TSimpleProgressForm.Create(AOwnerForm);
try
PrForm.Show;
PrForm.Update;
DoSomething;
finally
PrForm.Free;
EnableTaskWindows(p);
BringToFront;
end;
end;
сильно упрощенная имитация ShowModal для однопоточного вызова метода. Для 3-5 секунд вполне подойдет )
← →
clickmaker © (2009-04-03 18:21) [64]> Вариант отображать где то на главной форме, не удачный,
> т.к. юзер должен сразу увидеть что начался процесс обработки.
эээ... а какая связь?
← →
clickmaker © (2009-04-03 18:22) [65]> BringToFront;
вернее, SetActiveWindow(AOwnerForm.Handle);
← →
Кто б сомневался © (2009-04-03 18:31) [66]
> [63]
Короче напомню, - мы спорим о том баг это или не баг.
Вы говорите что это не баг, но предлагаете все время варианты обхода этого бага. Понимаете?
То таймер, то отсылка сообщения, теперь вот иммитация ShowModal.
Так просто согласитесь что это баг, да и все!
Должна быть возможность изменения ModalResult во время активации формы (и соответственно закрытие формы там же). Ладно уже OnShow пропустим, т.к. форма не отображается там.
← →
clickmaker © (2009-04-03 19:11) [67]> Так просто согласитесь что это баг
да можете считать это багом.
Мне лично это не мешает -)
← →
Кто б сомневался © (2009-04-03 19:21) [68]
> да можете считать это багом.
> Мне лично это не мешает -)
Мне то это тоже не мешает, взять отправить WM_CLOSE не сложно.
Кстати, имхо его никто не исправит. Т.к. там проблема глубже.
procedure TCustomForm.CMShowingChanged(var Message: TMessage);
if not (csDesigning in ComponentState) and (fsShowing in FFormState)
raise EInvalidOperation.Create(SVisibleChanged);
← →
Кто б сомневался © (2009-04-03 19:22) [69]
> if not (csDesigning in ComponentState) and (fsShowing in
> FFormState)
Хм, и это в OnActivate когда OnShow уже прошел..
← →
clickmaker © (2009-04-03 19:29) [70]так много можно подобных "багов" найти.
Авторы VCL не могли угодить всем, желающим странного
← →
Кто б сомневался © (2009-04-03 21:21) [71]
> так много можно подобных "багов" найти.
> Авторы VCL не могли угодить всем, желающим странного
Здесь ничего нет странного. Простешая форма, простешее ТЗ из 5 строк.
Но я все таки думаю что это баг. В OnActivate должны были сделать возможность менять ModalResult.
← →
Игорь Шевченко © (2009-04-03 21:25) [72]
> В OnActivate должны были сделать возможность менять ModalResult.
это как ? Активировал форму (допустим мышью), а она mrCancel вернула и закрылась ?
Ты извини, я всю ветку не читал, потому не могу понять, чего тебе надо :)
← →
Кто б сомневался © (2009-04-03 21:39) [73]
> это как ? Активировал форму (допустим мышью), а она mrCancel
> вернула и закрылась ?
Именно.
← →
clickmaker © (2009-04-03 23:36) [74]> не могу понять, чего тебе надо :)
ему надо странного. За что в древнем Китае отрубали руки o)
← →
Игорь Шевченко © (2009-04-03 23:58) [75]
> За что в древнем Китае отрубали руки o)
Вообще-то голову. Желают странного именно головой.
Я просто никак не могу понять, зачем может понадобиться такое поведение формы, которая показывается себе где-то на десктопе. А потом при ее активации закрывается, возвращая (или не возвращая) некий результат.
Я могу понять желание закрыть форму в обработчике события OnCreate, если при ее создании обнаружилось нечто несовместимое с жизнью формы, а вот зачем закрывать на OnActivate - не могу понять.
← →
Кто б сомневался © (2009-04-04 12:13) [76]
> а вот зачем закрывать на OnActivate - не могу понять.
Модальная форма без заголовка - bsNone, служит для того, чтобы отобразить юзеру - текст "подождите" (ну знаете как в инсталляторах). Все работает в одном потоке, т.к. задача на несколько секунд (3-5) поэтому стартуем в OnActivate, делаем все и закрываемся (возможно может быть кнопка "стоп"). Так вот в этом случае мы не закроемся легальным методом Close и кнопка не сработает - т.к. ModalResult обнуляется - причины почему он должен обнуляться, как сейчас, именно после Activate нет.
Поэтому я и считаю это багом, - т.к. это простешее ТЗ, которое довольно часто встречается, и которое нельзя выполнить методами VCL.
← →
Кто б сомневался © (2009-04-04 12:14) [77]
> методами VCL.
Скажем так:
Соответствующими методами VCL
← →
clickmaker © (2009-04-04 16:04) [78]> которое нельзя выполнить методами VCL.
не надо впадать в крайности.
Если есть некая задача, которую нельзя выполнить методами некоего фреймворка, то зачем сразу впадать в ступор и писать гневные письма в саппорт?
Есть API, есть OC - все вполне доступно.
Извините, конечно, но плохому танцору - знаете, что мешает
← →
Кто б сомневался © (2009-04-04 17:29) [79]
> Есть API, есть OC - все вполне доступно.
Вот елки. Который раз уже говорю что это обход официального метода. Close должен работать корректно в OnActivate.
← →
turbouser © (2009-04-04 17:31) [80]
> Кто б сомневался © (04.04.09 17:29) [79]
> Close должен работать корректно в OnActivate.
Он так и работает. Корректно.
← →
Кто б сомневался © (2009-04-04 21:09) [81]
> Он так и работает. Корректно.
Он не работает. О чем мы уже успешно говорим в 80 десяти постах.
← →
turbouser © (2009-04-04 23:28) [82]
>
> Он не работает. О чем мы уже успешно говорим в 80 десяти
> постах.
Смешно :)
← →
Кто б сомневался © (2009-04-05 12:39) [83]
> Смешно :)
Просто обхохочешся.
ТЗ - две формы, вторая модальная. Вот там и проверяй OnActivate, а не на главной форме.
← →
boa_kaa © (2009-04-05 13:31) [84]
> Кто б сомневался © (05.04.09 12:39) [83]
неумение обращаться с инструментом - это проблема не инструмента, а того, кто с ним обращается
если ты взял в руки ружье за спусковой крючок, а оно убило соседа, то это баг не ружья, а твой. И нефик потом в суде доказывать, что ружье должно предусматривать такой случай
← →
Кто б сомневался © (2009-04-05 13:42) [85]
> boa_kaa © (05.04.09 13:31) [84]
не надо мне рассказывать что я умею. я и сам знаю. Опытом хвастаться не люблю, но он не маленький. То что это можно сделать кучей других методов (n/е. варианты работы с инструментом), я знаю, но то что это нельзя сделать специально предназначенным методом Close - вот о речь.
← →
Игорь Шевченко © (2009-04-05 14:22) [86]
> Модальная форма без заголовка - bsNone, служит для того,
> чтобы отобразить юзеру - текст "подождите" (ну знаете как
> в инсталляторах). Все работает в одном потоке, т.к. задача
> на несколько секунд (3-5) поэтому стартуем в OnActivate,
> делаем все и закрываемся (возможно может быть кнопка "стоп").
>
А зачем, собственно, модальная ?
Первой формой создаем немодальную "подождите" и показываем ее Show, затем делаем свое черное дело и закрываем ее нафиг. Можно даже кнопку Стоп предусмотреть и проверять состояние этой кнопки во время черных дел. Такое делалось не раз, в том числе и сама среда так стартует, причем отображая прогресс старта. Правда кнопки Стоп нету, в Борланде не предвидели такой возможности, что кто-то будет закрывать среду во время инициализации, а зря. Иногда хочется.
← →
Кто б сомневался © (2009-04-08 22:16) [87]to all
Баг в статусе Reported, а не Pending или Closed - значит это все таки баг, как я и говорил, кто б там не спорил.
http://qc.embarcadero.com/wc/qcmain.aspx?d=72727
Страницы: 1 2 3 вся ветка
Текущий архив: 2009.06.14;
Скачать: CL | DM;
Память: 0.74 MB
Время: 0.014 c