Как сгенерировать событие?

Вопросы программирования и использования среды Lazarus.

Модератор: Модераторы

Re: Как сгенерировать событие?

Сообщение Лекс Айрин » 17.11.2017 19:01:52

Сквозняк писал(а):Вторая обнуляется при событии "создание формы", больше нигде в дополнительной форме не изменяется, и нужна для того, чтобы не обработать окно лишний раз.


На самом деле, окно при создании/закрытии получает несколько сообщений, которые обрабатываются несколькими обработчиками. И вот во время этих пассов руками окно и отображается/скрывается. Никакой второй переменной не нужно т. к. это на самом деле неделимый процесс, в который программист добавляет свои обработчики.
С точки зрения программиста, это получается набор вызывающих друг-друга методов.
Сквозняк писал(а):С Assigned ещё нужно разбираться, что там да как - в лазарусе не оттуда вызовешь функцию и привет - жалуйтесь ассемблеру, а с переменными, взял и написал.

А вот тут разбираться особо нет смысла. Assign это, грубо говоря, оператор присваивания для объекта. И нужен когда надо по быстрому проинициировать объект другим. Особенно хорош он для заполнения списков и подключения файлов.

Добавлено спустя 12 минут 40 секунд:
LearnMagic писал(а):Одному оператору проблематично одновременно вводить несколько документов. Обычно вводится один документ, а потом другой.


О... ты не общался с графоманами... у меня периодически возникает необходимость набора/исправления нескольких документов одновременно. Да и в офисе набор текста на основе отсканированной/напечатанной копии не является чем-то особо выдающимся. Не зря же даже в ворде можно было открыть документ дважды в одной сессии в разделенном окне.
Аватара пользователя
Лекс Айрин
долгожитель
 
Сообщения: 5723
Зарегистрирован: 19.02.2013 16:54:51
Откуда: Волгоград

Re: Как сгенерировать событие?

Сообщение Сквозняк » 17.11.2017 23:25:05

Лекс Айрин писал(а):На самом деле, окно при создании/закрытии получает несколько сообщений, которые обрабатываются несколькими обработчиками. И вот во время этих пассов руками окно и отображается/скрывается. Никакой второй переменной не нужно т. к. это на самом деле неделимый процесс, в который программист добавляет свои обработчики.

У меня после закрытия дочернего окна, в родительском окне ещё за ним и память чистится. 2 раза подряд чистить память не есть хорошо.
Сквозняк
энтузиаст
 
Сообщения: 1123
Зарегистрирован: 29.06.2006 22:08:32

Re: Как сгенерировать событие?

Сообщение Лекс Айрин » 18.11.2017 10:09:41

Сквозняк, а как ты это определил?

Вообще, вполне возможно. Сначала должны удаляться компоненты, а потом уже само окно... так что ничего особо странного нет. Если, конечно, ты правильно понял процесс закрытия окна.
А может быть ты путаешь состояния "окно готовится к закрытию", "окно закрывается", "Окно закрыто" и "уборка следов после закрытия окна"? И это все не считая деструкторов, которые пачкой навешаны на окна. Начиная от TObject.
Аватара пользователя
Лекс Айрин
долгожитель
 
Сообщения: 5723
Зарегистрирован: 19.02.2013 16:54:51
Откуда: Волгоград

Re: Как сгенерировать событие?

Сообщение Сквозняк » 18.11.2017 12:30:48

Лекс Айрин писал(а):а как ты это определил?

Метод отладки при помощи writeln напиханных во все подозрительные места. Смотришь в консоли сколько раз напечатало __________1__, __________2__, qqqq_______1___ и т.д. Поставил в свой обработчик вызывающий free кучу врителнов и колбасил пока перестало делать не так как надо. Для случаев, когда консоль занята и туда выводить отладку нельзя, есть модуль пишущий в файл похожими на write и writeln процедурами.
Код: Выделить всё
{$GOTO ON}

UNIT
OTLADKOFAIL;

INTERFACE
PROCEDURE WRITE_O(S5: ANSISTRING);
PROCEDURE WRITELN_O(S5: ANSISTRING);
PROCEDURE WRITE_VYHOD;
FUNCTION F_STR(Q64: INT64):STRING;
FUNCTION F_STR_V(Q1: EXTENDED):STRING;
IMPLEMENTATION

VAR
F3: BYTE=0;
F7: FILE;


PROCEDURE OTKRYTJ_FAIL;
LABEL
100;
BEGIN
IF F3=1 THEN GOTO 100;
ASSIGN(F7,'fail_otladki.txt');
REWRITE(F7,1);
F3:=1;
100:
END;


PROCEDURE WRITE_VYHOD;
BEGIN
IF F3=1 THEN CLOSE(F7);
END;


PROCEDURE WRITE_O(S5: ANSISTRING);
VAR
Q2: LONGINT;
BEGIN
IF F3=0 THEN OTKRYTJ_FAIL;
Q2:=LENGTH(S5);
BLOCKWRITE(F7,S5[1],Q2);
END;


PROCEDURE WRITELN_O(S5: ANSISTRING);
BEGIN
S5:=S5+#13#10;
WRITE_O(S5);
END;


FUNCTION F_STR(Q64: INT64):STRING;
BEGIN
STR(Q64,F_STR);
END;


FUNCTION F_STR_V(Q1: EXTENDED):STRING;
VAR
Q64: INT64;
S5: STRING;
Q3: BYTE;
BEGIN
F_STR_V:='';
IF Q1<0 THEN BEGIN
             F_STR_V:='-';
             Q1:=ABS(Q1);
             END;
Q64:=TRUNC(Q1);
STR(Q64,S5);
F_STR_V:=F_STR_V+S5;
Q1:=FRAC(Q1)+1;
STR(Q1,S5);
FOR Q3:=1 TO 17 DO S5[Q3]:=S5[Q3+3];
SETLENGTH(S5,16);
IF S5='0000000000000000' THEN S5:='00';
F_STR_V:=F_STR_V+'.'+S5;
END;



BEGIN
END.


На критической ошибке запись обрывается. Если код не слишком оопэшный, то такой метод работает.
Сквозняк
энтузиаст
 
Сообщения: 1123
Зарегистрирован: 29.06.2006 22:08:32

Re: Как сгенерировать событие?

Сообщение vitaly_l » 18.11.2017 12:39:56

Сквозняк писал(а):PROCEDURE OTKRYTJ_FAIL;
LABEL
100;
BEGIN
IF F3=1 THEN GOTO 100;
ASSIGN(F7,'fail_otladki.txt');
REWRITE(F7,1);
F3:=1;
100:
END;


Я очень люблю оператор GoTo,
но конкретно в Вашем случае - лучше обходиться без него,
и результат будет столь же предсказуем, вот пример:
Код: Выделить всё
PROCEDURE OTKRYTJ_FAIL;
BEGIN
  IF F3 <> 1 THEN begin
    ASSIGN(F7,'fail_otladki.txt');
    REWRITE(F7,1);
    F3:=1;
  end;
END;
Аватара пользователя
vitaly_l
долгожитель
 
Сообщения: 3333
Зарегистрирован: 31.01.2012 16:41:41

Re: Как сгенерировать событие?

Сообщение Лекс Айрин » 18.11.2017 13:01:25

Сквозняк т. е. ты старательно испортил обработчик окна.... и пытаешься добиться стабильной работы? Что ж... а теперь верни все как было и сделай правильно.
Ты понимаешь, что все эти освобождения памяти не зря распиханы в очередь и по разным местам? Есть еще таблицы компонент, окон и пр... которые постепенно зачищаются. Хитрить тут можно только если четко понимаешь,,что происходит в системе. Хочется маленькой и шустрой программы? Переписывай в win/linAPI, но будь готов к тому, что каждый чих придется обрабатывать.
Аватара пользователя
Лекс Айрин
долгожитель
 
Сообщения: 5723
Зарегистрирован: 19.02.2013 16:54:51
Откуда: Волгоград

Re: Как сгенерировать событие?

Сообщение Сквозняк » 18.11.2017 16:51:22

Лекс Айрин писал(а):Сквозняк т. е. ты старательно испортил обработчик окна.... и пытаешься добиться стабильной работы? Что ж... а теперь верни все как было и сделай правильно.Ты понимаешь, что все эти освобождения памяти не зря распиханы в очередь и по разным местам?

Нету там освобождений памяти. Загрузи в форму тяжёлые картинки, включи диспетчер задач и посмотри. Я это освобождение реализовал и не считаю что сделал хуже.
Хитрить тут можно только если четко понимаешь,,что происходит в системе.

Всего и ты не знаешь, иначе не сказал такую глупость.
Хочется маленькой и шустрой программы? Переписывай в win/linAPI, но будь готов к тому, что каждый чих придется обрабатывать.

Так интерфейс и так до ума доведён, в нём только иногда мелкие фичи добавлять можно, или очередную форму, закрытие которой обработает параллельный системному обработчик событий расположенный в будильнике - он у нас системный "ёгурт", а значит код выполняется "в стеке".

Добавлено спустя 5 минут 50 секунд:
vitaly_l писал(а):но конкретно в Вашем случае - лучше обходиться без него,и результат будет столь же предсказуем, вот пример:

А смысл то в чём? Если этот код понадобится включить в проект с жёстким дресскодом, тогда и стоит его переписать и поломать удобство, а так - и так нормально работает, директива разрешающая goto в начале файла поставлена, а значит файл должен скомпилироваться даже если компилятору в командной строке указать собирать проект без goto.
Сквозняк
энтузиаст
 
Сообщения: 1123
Зарегистрирован: 29.06.2006 22:08:32

Re: Как сгенерировать событие?

Сообщение Лекс Айрин » 18.11.2017 17:43:08

Сквозняк писал(а):Так интерфейс и так до ума доведён, в нём только иногда мелкие фичи добавлять можно, или очередную форму, закрытие которой обработает параллельный системному обработчик событий расположенный в будильнике - он у нас системный "ёгурт", а значит код выполняется "в стеке".

Как же он может быть доведенным, если у тебя постоянно в нем то один глюк, то другой? У всех они возникают только если идет смена чего-то серьезного... Переход на динамическое открытие/закрытие, добавление липнущих окон... А если вдруг где-то что-то перестало работать, то значит ищи опечатку.
Сквозняк писал(а):Загрузи в форму тяжёлые картинки, включи диспетчер задач и посмотри. Я это освобождение реализовал и не считаю что сделал хуже.


А зачем ты встраиваешь в код тяжелые картинки? Чисто попонтоваться, что и так можешь? Так это можно сделать проще. Если уж конкретно надо освободить тяжелые картинки, то проще просто сделать это явно в определенном месте. Например, в обработчике onClose (хотя лучше в деструкторе, чтобы уж наверняка.) для этого не надо лезть в дебри. Но вот только это очень плохой стиль -- написание рисованного окна. Хотя иногда, конечно, приходится, не без этого.
Окна обычно не освобождаются для ускорения открытия в следующий раз. Но если тебе это очень надо, то вполне можно и явно закрыть. Но будь готов к постоянным тормозам.


Сквозняк писал(а):а значит файл должен скомпилироваться даже если компилятору в командной строке указать собирать проект без goto.


Я вот, например, понял твой код с третьего раза. Переписанный без goto он понимается в легкую. Проблема его (goto) применения в том, что нарушается последовательность чтения кода, глаз мечется туда/сюда.
Аватара пользователя
Лекс Айрин
долгожитель
 
Сообщения: 5723
Зарегистрирован: 19.02.2013 16:54:51
Откуда: Волгоград

Re: Как сгенерировать событие?

Сообщение Сквозняк » 19.11.2017 02:27:42

Лекс Айрин писал(а):Как же он может быть доведенным, если у тебя постоянно в нем то один глюк, то другой?

Те глюки устранились. Кнопка "сделать зашибись" нажимается нормально!

Лекс Айрин писал(а):Переход на динамическое открытие/закрытие, добавление липнущих окон...

Что значит "липнущих"? Все окна открываются и закрываются нормально, проверил 2 раза.
А зачем ты встраиваешь в код тяжелые картинки?

Экраны сейчас большие, а картинки хорошо поясняют мысль и добавляют кликабельности. Так надо.
Если уж конкретно надо освободить тяжелые картинки, то проще просто сделать это явно в определенном месте. Например, в обработчике onClose (хотя лучше в деструкторе, чтобы уж наверняка.)

Так раньше и делал, пока лучшего способа не знал. Плохо это - кода много, если окно всё равно после этого уничтожается, то что-то из памяти не уничтожается и - здравствуйте утечки! А сейчас один внешний обработчик со всем справляется, может жрёт чуть больше времени, но не критично.
Окна обычно не освобождаются для ускорения открытия в следующий раз. Но если тебе это очень надо, то вполне можно и явно закрыть. Но будь готов к постоянным тормозам.

Так телепаты в отпуске. Я не знаю, какие окна понадобятся повторно в течении сеанса, а какие - нет. Кроме того, приводя память программы в изначальное состояние облегчается отладка другого кода, он выполняется в не мутировавшей среде.
Я вот, например, понял твой код с третьего раза. Переписанный без goto он понимается в легкую. Проблема его (goto) применения в том, что нарушается последовательность чтения кода, глаз мечется туда/сюда.

Дело привычки. Кому-то эти глупые отступы там где не надо и end расположенный не под begin чтение не улучшают.
Сквозняк
энтузиаст
 
Сообщения: 1123
Зарегистрирован: 29.06.2006 22:08:32

Re: Как сгенерировать событие?

Сообщение Лекс Айрин » 20.11.2017 09:37:14

Сквозняк писал(а):Что значит "липнущих"? Все окна открываются и закрываются нормально, проверил 2 раза.

Использующих анхордокинг.

Сквозняк писал(а): а картинки хорошо поясняют мысль и добавляют кликабельности. Так надо.


Да ладно...

Сквозняк писал(а): если окно всё равно после этого уничтожается, то что-то из памяти не уничтожается и - здравствуйте утечки!


Для этого есть проверка на утечки. И, сколько раз убеждался, если она есть, то я просто написал небрежный код.

Сквозняк писал(а):Так телепаты в отпуске. Я не знаю, какие окна понадобятся повторно в течении сеанса, а какие - нет.


А это как ты построишь программу. Хорошо, когда есть возможность погонять ее длительное время.

Сквозняк писал(а):он выполняется в не мутировавшей среде.


У тебя изначально мутировавшая среда.
Аватара пользователя
Лекс Айрин
долгожитель
 
Сообщения: 5723
Зарегистрирован: 19.02.2013 16:54:51
Откуда: Волгоград

Re: Как сгенерировать событие?

Сообщение Сквозняк » 23.11.2017 19:42:49

Лекс Айрин писал(а):Использующих анхордокинг.

Пока не надо. В другой раз, может быть.
Да ладно...

Точно тебе говорю. Слова для многих - ничто.
Для этого есть проверка на утечки.

Без понятия про неё.
У тебя изначально мутировавшая среда.

Как бы не очень. Если баг можно воспроизводить при нескольких попытках, то это наверно не плохой результат повторяемости.
Сквозняк
энтузиаст
 
Сообщения: 1123
Зарегистрирован: 29.06.2006 22:08:32

Re: Как сгенерировать событие?

Сообщение Лекс Айрин » 23.11.2017 20:06:12

Сквозняк писал(а):ока не надо. В другой раз, может быть.


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

Сквозняк писал(а):Точно тебе говорю. Слова для многих - ничто.


Убрал из программы большую часть картинок, так как они засоряли окна. Надо будет сделать нестандартные кнопки, но внешний их вид постараюсь изменить другими методами. И уж точно большие картинки буду загружать только как документ (для редактирования). Ну или если делать чисто мультимедийную прогу, типа игры/AR-компонента.

Сквозняк писал(а):Без понятия про неё.


В настройках проекта отмечаешь одну галочку и пересобираешь Лазарус в режиме отладки.... а потом ужасаешься сколько ошибок обнаружишь в уже "отлаженной" программе. Спасибо Zub-у, что подсказал и уломал (это важнее) все это дело включить.

Сквозняк писал(а): Если баг можно воспроизводить при нескольких попытках, то это наверно не плохой результат повторяемости.


Это не говорит о мутированности или нет. Если ты вмешиваешься в стандартную обработку окна, то ты уже служишь как мутаген. И ты должен понимать как все изменения сделанные тобой оставить в твоем коде. У тебя же окно пытается освободить компоненты, а их нет. Так что правильнее придерживаться правила, что созданное автоматически уничтожается автоматически, а созданное руками, вручную.
Аватара пользователя
Лекс Айрин
долгожитель
 
Сообщения: 5723
Зарегистрирован: 19.02.2013 16:54:51
Откуда: Волгоград

Re: Как сгенерировать событие?

Сообщение Сквозняк » 23.11.2017 21:55:40

Лекс Айрин писал(а):Это не говорит о мутированности или нет. Если ты вмешиваешься в стандартную обработку окна, то ты уже служишь как мутаген. И ты должен понимать как все изменения сделанные тобой оставить в твоем коде. У тебя же окно пытается освободить компоненты, а их нет. Так что правильнее придерживаться правила, что созданное автоматически уничтожается автоматически, а созданное руками, вручную.

А ещё можно интерфейс к программе сбоку прицепить. К сожалению форма в лазарусе криво написана и требует чтобы её в главном потоке запускали - как будто он резиновый.
Сквозняк
энтузиаст
 
Сообщения: 1123
Зарегистрирован: 29.06.2006 22:08:32

Re: Как сгенерировать событие?

Сообщение sign » 24.11.2017 07:51:06

Сквозняк писал(а):
Лекс Айрин писал(а):Для этого есть проверка на утечки.

Без понятия про неё.

1.jpg
У вас нет необходимых прав для просмотра вложений в этом сообщении.
sign
энтузиаст
 
Сообщения: 1131
Зарегистрирован: 30.08.2009 09:20:53

Re: Как сгенерировать событие?

Сообщение Сквозняк » 09.11.2024 23:45:45

7 лет прошло а вопрос всё тот же: как в лазарусном говноменю при запуске на любой платформе определить какой ширины должно быть окно, чтобы все пункты меню были гарантированно видны.
Сквозняк
энтузиаст
 
Сообщения: 1123
Зарегистрирован: 29.06.2006 22:08:32

Пред.След.

Вернуться в Lazarus

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 20

Рейтинг@Mail.ru