Вопросы по LCL

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

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

Ответить
zub
долгожитель
Сообщения: 2889
Зарегистрирован: 14.11.2005 22:51:26
Контактная информация:

Вопросы по LCL

Сообщение zub »

переделываю приложение с winapi на LCL.
ни c LCL, ни с VCL не знаком, поэтому есть глупые вопросы))

1)

Код: Выделить всё

procedure TAboutWnd.FormClose(Sender: TObject; var CloseAction: TCloseAction);
begin
  CloseAction:=caFree;
end;

форма ни то что не уничтожантся, она даже не закрывается. почему?
форма создается динамически, и единственная lcl`ная в проекте, остальные winapi

2)
я не использую визуальных фич lazalus`а, как мне для закрытия с уничтожением обойтись без событий?

3) пункт 1 видимо изза того что в программе нет LCL`ного Application.run;, если поставить то работает. Но тогда не работает мой аналог Application.run. Хотел постепенно переделать - форма за формой, так не получится?
Последний раз редактировалось zub 09.06.2010 12:30:50, всего редактировалось 1 раз.
Odyssey
энтузиаст
Сообщения: 580
Зарегистрирован: 29.11.2007 16:32:24

Re: Закрытие формы

Сообщение Odyssey »

Говорят, в IT ничего невозможного нет, вопрос только в затраченных человеко-часах. Поэтому заставить половину приложения работать на LCL, а вторую на WinAPI наверное можно, но:
* LCL не расчитана на совместное использование с продвинутым WinAPI, поэтому проблемы будут.
* Я не знаю никого, кто бы поступал подобным образом, поэтому вероятно, что проблемы придётся решать вам самому.
Я бы портировал такую программу не совмещая код прямой работы с WinAPI и работу с LCL. Т.е. создал бы новый проект, сделал там болванки форм и постепенно переносил логику. Если требуется, можно предварительно порефакторить WinAPI приложение, выделяя логику получше, чтобы потом её проще было перенести.
zub
долгожитель
Сообщения: 2889
Зарегистрирован: 14.11.2005 22:51:26
Контактная информация:

Re: Закрытие формы

Сообщение zub »

>>Я бы портировал такую программу не совмещая код прямой работы с WinAPI и работу с LCL
так оно и получится - несколько главных форм придется портировать разом, они "хитро" связаны.

>>* LCL не расчитана на совместное использование с продвинутым WinAPI, поэтому проблемы будут.
ниче продвинутого нет, простая обертка над основными сообщениями.

LCL я не знаю, поэтому хочется потренироваться на второстепенных формах, запускаемых не модально, паралельно рефакторя главные формы. + не хочется глубоко терять работоспособность программы, чтоб если че отказаться от перехода и вернуть всё как было. Вроде получается просто заменить мой аналог Application.run на LCLный, сообщения моим окнам приходят, глюков нет.

Добавлено спустя 10 часов 12 минут 34 секунды:
1,3 пункты снимаются - разобрался.

остается 2. Что перекрывать в наследниках, чтобы не использовать события onВсякаяХрень. и вообще наверно стоит наследоваться не от TForm?
Что можно почитать чтоб разобраться в логике и назначении методов class`ов LCL?

Добавлено спустя 3 часа 20 минут 6 секунд:
Re: Вопросы по LCL
4. Стоит ли использовать визуальные возможности лазаря?
программа планируется с минимумом интерфейса, для реализации логики программы (выполнения функций) предусмотрено несколько вариантов, например нажатие кнопки (или нескольких на разных панелях), выбор пункта меню, ввод названия команды в командную строку.
т.е. мои обертки (используемые сейчас, без LCL) кнопок, пунктов меню и т.д. хранят в себе название своих команд и при нажатии-выборе передают их "менеджеру команд" для выполнения. как вписать такую логику в стандартные визуальные компоненты LCL, не погрязнув в разных onСlick для каждой кнопки-пункта меню?
Аватара пользователя
Brainenjii
энтузиаст
Сообщения: 1351
Зарегистрирован: 10.05.2007 00:04:46

Re: Вопросы по LCL

Сообщение Brainenjii »

Использовать ActionList?
zub
долгожитель
Сообщения: 2889
Зарегистрирован: 14.11.2005 22:51:26
Контактная информация:

Re: Вопросы по LCL

Сообщение zub »

>>Использовать ActionList?
Да, похоже. век живи век учись))
ActionList поддерживает вложенное исполнение Action`ов?
т.е. запустили команду "копировать",
пока команда "копировать" ждет чтобы юзер указал что копировать,
юзер подумал и запустилил "ВыбратьВсё" - всё выбралось,
команда "копировать" продолжила свою работу понимая что ей придется потрудится копируя всё иждет пока пользователь укажет куда
Аватара пользователя
hinst
энтузиаст
Сообщения: 781
Зарегистрирован: 12.04.2008 18:32:38
Контактная информация:

Re: Вопросы по LCL

Сообщение hinst »

что-то я немножко не врубаюсь, причём тут визуальный редактор и назначение обработчиков на события. что, без инспектора объектов и визуального дизайна нельзя в коде назначить обработчик события?? :shock:
zub
долгожитель
Сообщения: 2889
Зарегистрирован: 14.11.2005 22:51:26
Контактная информация:

Re: Вопросы по LCL

Сообщение zub »

>>что, без инспектора объектов и визуального дизайна нельзя в коде назначить обработчик события??

можно. но мне кажется проще наследоваться от тбуттона добавить название команды, переопределить метод при нажатии (забыл как называется) - будет один класс для всех моих кнопок избавленный от "лишних" движений с назначениям событий onЧтотоТам. Но в дизайнере такие кнопки можно использовать как я понял только сделав их компонентом и пересобрав лазарь, что мне кажется лишним. Вот и хочу решить какой метод подойдет больше - стандартные+дизайнер, стандартные без дизайнера, свои с дизайнером, свои без дизайнера.
Аватара пользователя
hinst
энтузиаст
Сообщения: 781
Зарегистрирован: 12.04.2008 18:32:38
Контактная информация:

Re: Вопросы по LCL

Сообщение hinst »

что мне кажется лишним

а вам, наверное, надо, чтобы и не пересобирать, и в дизайнере были? :twisted:
вам кажется лишним, а вот разработчикам среды такой метод показался единственно приемлемым. понятно, что всем хочется, чтобы делать как можно меньше. нажать "пересобрать" - уже лишнее.
zub
долгожитель
Сообщения: 2889
Зарегистрирован: 14.11.2005 22:51:26
Контактная информация:

Re: Вопросы по LCL

Сообщение zub »

>>а вам, наверное, надо, чтобы и не пересобирать, и в дизайнере были?
>>вам кажется лишним, а вот разработчикам среды такой метод показался единственно приемлемым.

что за обвинения, видимо правда тут на форуме гдето написано что русские разработчики лазаря злые))
лишним мне кажется потому что на компонент это не тянет, а не потому что нехочу\неумею пересобирать
мне какраз проще всё сделать в рантайме, сечас у меня всё так и сделано. Хочу понять как ЛУЧШЕ где какие плюсы-минусы. Пока в дизайнере вижу только минусы
Аватара пользователя
hinst
энтузиаст
Сообщения: 781
Зарегистрирован: 12.04.2008 18:32:38
Контактная информация:

Re: Вопросы по LCL

Сообщение hinst »

следственно,
свои без дизайнера

Перекрывать можно конструктор. И в нём назначить на все нужные события методы того же класса TMyButton
тогда не придётся лезть в реализацию LCL и смотреть, что там нужно перекрыть, да ещё и с риском того, что может потом криво заработать
zub
долгожитель
Сообщения: 2889
Зарегистрирован: 14.11.2005 22:51:26
Контактная информация:

Re: Вопросы по LCL

Сообщение zub »

>>Перекрывать можно конструктор
т.е. лучше использовать onЧтомнеНадо и не лазить по методам.
>>да ещё и с риском того, что может потом криво заработать
логично. но имхо некрасиво - много лишних действий обусловленных наличием неиспользуемого дизайнера.

Еще меня мучает вопросик - где для формы производить инициализацию дочерних контролов? в конструкторе или в AfterConstruction?
Odyssey
энтузиаст
Сообщения: 580
Зарегистрирован: 29.11.2007 16:32:24

Re: Закрытие формы

Сообщение Odyssey »

zub писал(а):остается 2. Что перекрывать в наследниках, чтобы не использовать события onВсякаяХрень. и вообще наверно стоит наследоваться не от TForm?

Переопределить можно наверное TCustomForm.DoClose. Вообще, по традиции, для каждого OnВсякаяХрень в классе (или его предках) есть метод DoВсякаяХрень, который проверяет, назначен ли обработчик и запускает его.
zub писал(а):Что можно почитать чтоб разобраться в логике и назначении методов class`ов LCL?

С такими нетривиальными требованиями могу предложить только исходники LCL :) В Lazarus IDE есть куча полезных фич, облегчающих чтение. Если нажать Ctrl и ткнуть мышкой на идентификатор, можно увидеть его декларацию. Так можно посмотреть на что способны стандартные классы и компоненты из RTL, FCL и LCL. Ctrl+Shift+Up/Down -- переход от декларации к реализации и обратно. Ещё поиск по коду, в том числе быстрый (Ctrl+E) и переход вперёд/назад по истории просмотров (есть в меню Поиск, плюс горячие клавиши настраиваются). Именно так я только что нашёл TCustomForm.DoClose.
zub писал(а):4. Стоит ли использовать визуальные возможности лазаря?
программа планируется с минимумом интерфейса, для реализации логики программы (выполнения функций) предусмотрено несколько вариантов, например нажатие кнопки (или нескольких на разных панелях), выбор пункта меню, ввод названия команды в командную строку.
т.е. мои обертки (используемые сейчас, без LCL) кнопок, пунктов меню и т.д. хранят в себе название своих команд и при нажатии-выборе передают их "менеджеру команд" для выполнения. как вписать такую логику в стандартные визуальные компоненты LCL, не погрязнув в разных onСlick для каждой кнопки-пункта меню?

В таком случае ActionList тут имхо не совсем то. По сути, ActionList делает то же самое что у вас уже есть, но обращение к командам там происходит не по строковым именам, а по ссылкам на компоненты. Т.е. каждая команда -- это самостоятельный компонент TAction, с названием, горячей клавишей и (ненавистным :)) обработчиком, OnExecute.

В описанном вами случае, я бы посмотрел на другой вариант. Если писать свои компоненты со свойством "команда", для визуального проектирования GUI придётся пересобирать IDE, это действительно не айс. Поэтому можно просто связать уже имеющиеся компоненты с командами. Например:

Код: Выделить всё

TCommandDispatcher = class
private
  procedure ButtonClickHandler(Sender: TObject);
  procedure XXXHandler(Sender: TObject; XXXParams: TXXXParams);
  procedure ExecCommandForComponent(AComponent: TComponent);
public
  procedure SetupComponent(AComponent: TComponent; const ACommand: String);
end;

Класс мог бы содержать список соответствий между командами и компонентами. Они могут быть построены как угодно -- (экземпляр компонента;имя команды), (имя компонента;имя команды); (тег копонента, соответсвующий индексу команды в списке) и т.п. Я бы выбрал первый способ, сделал бы его для скорости на TStringList. Т.е. в Strings писал бы имена команд, а в Objects -- экземпляры компонентов.

Тогда SetupComponent добавлял бы такую пару в StringList, и назначал бы компоненту обработчик, уже прописанный в TCommandDispatcher, в зависимости от типа. Т.е.

Код: Выделить всё

if (AComponent is TButton) then
  TButton(AComponent).OnClick := Self.ButtonClickHandler; // @ButtonClickHandler для {$mode objfpc}

А ButtonClickHandler для всех кнопок выглядел бы одинаково:

Код: Выделить всё

ExecCommandForComponent(Sender);

ExecCommandForComponent, в свою очередь, искала бы в списке команду для данного экземпляра компонента и передавала бы её на исполнение менеджеру команд.

Тогда в результате получим один класс-диспетчер, который содержит по одному обработчику на нескольких типов компонентов, и код инициализации формы в виде множества вызовов типа:

Код: Выделить всё

CommandDispatcher.SetupComponent(btnUpdateView, 'update_view_cmd');


zub писал(а):Еще меня мучает вопросик - где для формы производить инициализацию дочерних контролов? в конструкторе или в AfterConstruction?

Имхо лучше в AfterConstruction, в конструкторе Handle может быть ещё не выделен. Да вообщем то и за AfterConstruction не ручаюсь, лучше смотреть в исходниках.

Добавлено спустя 5 минут 28 секунд:
Re: Вопросы по LCL
Из плюсов дизайнера -- предварительный просмотр, и ещё там немного быстрее устанавливать привязки компонентов друг к другу, чем через код. Если я правильно понимаю, единственная причина по которой может понадобиться переписывать программу на Pascal с WinAPI на LCL -- это кроссплатформенность. А поскольку DPI, размеры шрифтов и элементов GUI на разных ОС разные, то без "резинового" GUI не обойтись. Для начальных сведений можно посмотреть http://freepascal.ru/article//lazarus/20090217210602/ , дальше -- http://wiki.lazarus.freepascal.org/Autosize_/_Layout
zub
долгожитель
Сообщения: 2889
Зарегистрирован: 14.11.2005 22:51:26
Контактная информация:

Re: Вопросы по LCL

Сообщение zub »

hinst, Odyssey
Большое спасибо за ответы.

Добавлено спустя 14 часов 20 минут 53 секунды:
еще подкопил вопросов)), на этот раз по TTreeViev
У меня в дереве отображаются разнотипные объекты (не обезательно классы), соответственно есть несколько релизаций myTreeNode, инкапсулирующих в себе все нужные свойства чтоб отличить что за объект символизирует данный узел.
1) LCLный TTreeViev как я понял позволяет создавать узлы только типа TTreeNode?
2) Как мне отличить на что в данном узле указывает Data?
3) как мне искать у определенных TreeNode нужный подузел?
Аватара пользователя
Light13
постоялец
Сообщения: 127
Зарегистрирован: 17.07.2009 07:50:10
Откуда: Челябинск

Re: Вопросы по LCL

Сообщение Light13 »

проверяйте оператором is что у вас там в вашем ноде лежит
Mr.Smart
долгожитель
Сообщения: 1796
Зарегистрирован: 29.03.2008 00:01:11
Откуда: из леса!

Re: Вопросы по LCL

Сообщение Mr.Smart »

2) if TObject(Node.Data) is TMyClass then
3) Node.FindNode('...')
Ответить