Публикации Разное

Что такое FpGUI и с чем его едят.

18.02.2013
Вадим Исаев

19.10.2013 Алексей В. Логинов (AlexL): Обновление текста статьи и скриншотов.

Введение
Особенности fpGUI
Где взять и как установить
Программирование
Как добавить новый компонент в Uidesigner
Документация и примеры
Заключение

Введение

FpGUI - это ещё один набор визуальных компонентов (сайт - fpgui.sourceforge.net) для Free Pascal, позволяющий создавать пользовательский интерфейс для ваших программ в графической оболочке. Расшифровывается как "Free Pascal Graphic User Interface". Начат в 2000 году Себастьяном Гюнтером (Sebastian Gunther) как высокоуровневый интерфейс для GTK, однако в 2002 году проект был заброшен. В 2003 году проектом заинтересовался Виктор Наги (Viktor Nagy), который решил сделать его самостоятельным, независящим от высокоуровневых библиотек графического интерфейса пользователя, под именем lptk, но в 2005 году забросил. В 2006 году проект продолжил Грэм Гэлденхайз (Graeme Geldenhuys).

Все элементы FpGUI отрисовывает самостоятельно с помощью низкоуровневой библиотеки рисования, однако компоненты выглядят здесь также, как если бы вы пользовались любой стандартной средой программирования (см. рисунок 1). Так что пользователю вашей программы не придётся в ужасе шарахаться от её вида.


Рисунок 1. Вид программы, написанной с помощью fpGUI

Поддерживаемые операционные системы:

  • Linux;
  • BSD;
  • Windows;
  • OpenSolaris;
  • MacOS;
  • ARM-Linux;
  • WinCE.

Компоненты без проблем компилируются как в 32-х, так и в 64-х разрядных ОС.

Кроссплатформенность обеспечивается отрисовкой компонентов с помощью низкоуровневых библиотек:

  • libX11, libXft и libfontconfig для *NIX-подобных ОС;
  • GDI для Windows.

Какие здесь есть компоненты:

  • Всё, что есть на вкладках Standard и Additional в Lazarus, есть и в fpGUI.
  • Основные окна диалогов (для открытия файлов, каталогов, выбор цвета, символы) и окна ввода/вывода сообщений (InputQuery, ShowMessage).
  • Компоненты для отображения данных. Однако не надейтесь получить здесь всё, что вам нужно. Пока что в наличие есть три компонента, один из которых (TfpgDBEdit) закомментирован, т.к. разработчик считает, что TfpgEdit, на котором строится TfpgDBEdit, нужно слегка подправить (наверное ему времени не хватает это сделать, т.к. буржуйское государство живёт по вполне социалистическому принципу: кто не работает - тот не ест :-) ).
    Итак, что есть рабочего из компонентов взаимодействия с БД:
    • TfpgFieldDataLink - компонент связи виджета с полем в каком-то определённом наборе данных, наследник от TDataLink. Обеспечивает передачу сообщений туда-сюда об изменении данных.
      Обычно этот элемент входит составной частью в тот виджет, который будет работать с данными из связанного набора данных. Таким образом, когда вы создаёте наследника от виджета (например, это будет наследник от TfpgEdit), то включаете в него компонент типа TfpgFieldDataLink. Далее необходимо в компоненте-наследнике прописать свойство OnDataChange, которое отвечает за изменение данных, и после создания компонента типа TfpgFieldDataLink присвоить его свойству OnDataChange это самое свойство наследника, после чего обмен данными пойдёт как по маслу.
    • TfpgDBLabel - этот компонент служит иллюстрацией вышесказанного. Т.е. в этом компоненте, наследнике от TfpgLabel, добавлены необходимые свойства и методы для работы с БД через TfpgFieldDataLink и сформировано событие OnDataChange, которое заведует получением текста из поля БД в свойство Text, отображающее нужное значение. По его образцу и подобию вы можете соорудить и остальные недостающие компоненты.

Особенности fpGUI

  • Строки, как и в Lazarus, кодируются с помощью UTF-8, что позволяет без малейших проблем переносить исходники программ между Windows и Linux.
  • На основе fpGUI сделана среда визуального проектирования форм - Uidesigner, которая весьма похожа на Lazarus (см. рисунок 2).


    Рисунок 2. Вид дизайнера форм Uidesigner

  • Очень интересной особенностью является то, что практически любой компонент пользовательского интерфейса, лежащий на форме, можно создать программно с помощью специализированной функции:
    CreateXXXX()
    где XXXX - это название компонента, например, label, button, ComboBox и т.п. Это удобно если разработка ведётся не с помощью идущего в комплекте дизайнера форм Uidesigner, а в каком-нибудь другом редакторе. А вот для создания самой формы такой функции, увы, не предусмотрено, хотя и было бы неплохо.
  • Не все интересные компоненты лежат в подкаталоге src. Вот что я нашёл ещё:
    • docview/components/richtext - компонент для просмотра форматированного текста. Несмотря на название, форматирование текста там происходит с помощью html-тегов. Кому интересно - можете его использовать. Лично мне для вывода отчётов вполне хватает браузера по умолчанию в системе.
    • prototypes/mdi - позволяет создавать MDI-приложения. Это будет безусловно интересно для тех, кто раньше программировал в Lazarus и не имел возможности создавать такие приложения (включён в пакет fpgui для дистрибутива Mageia).
  • Есть возможность подключить компоненты fpGUI в Lazarus или MSEide. С моей точки зрения эта возможность не очень актуальна, т.к. пользователи этих систем вполне успешно используют родные компоненты. С другой стороны, uidesigner уже вполне неплох и его можно беспроблемно использовать для разработки форм, хотя отсутствие собственного редактора кода и визуального отображения событий на первых порах может вызывать неудобство.

Где взять и как установить

fpGUI распространяется в виде исходников. Порядок установки следующий:

  • Необходимо скачать архив fpgui_source-1.0.tar.gz (где 1.0 - это версия компонентов) с сайта http://sourceforge.net/projects/fpgui/files/fpGUI/ и распаковать его в отдельный каталог (пусть он у нас будет называться fpgui - в домашнем каталоге, если у вас Linux, или в каталоге установки Free Pascal, если у вас Windows).
  • Следующий шаг - компиляция компонентов. Для этого заходите в каталог с fpgui, подкаталог src и в нём увидите файл скрипта - build.sh для Linux и build.bat для Windows. Запускаете тот файл скрипта, который соответствует вашей операционной системе, и он вам скомпилирует все компоненты, а откомпилированные модули сложит в подкаталог lib.
  • Далее, путь к этому каталогу нужно занести в конфигурационный файл Free Pascal - /etc/fpc.cfg для Linux или, если у вас Windows, в каталоге, куда вы установили Free Pascal, в подкаталоге bin найдёте файл fpc.cfg. В Linux для его редактирования вам понадобятся права root. В этом файле находите строки, которые начинаются с символов -Fu (это указание, где лежат откомпилированные стандартные модули) и после их всех добавляете ещё одну строку:
    Для Linux:
    -Fu/home/имя_пользователя/fpgui/lib

    Для Windows:
    -FuДиск_и_каталог_где_установлен_Free_Pascal/fpgui/lib
    где имя_пользователя - это имя, под которым вы заходите в систему. Теперь компилятор будет знать где искать модули fpgui.
  • И последний шаг - компилируем Uidesigner. В каталоге, куда вы распаковали fpgui, заходим в подкаталог uidesigner и выполняем команду:
    fpc uidesigner.lpr
    Обычно компиляция проходит без малейших проблем.
  • В некоторых дистрибутивах linux достаточно установить только пакеты fpgui, uidesigner (например, в дистрибутивах Mageia, EduMagic).

Программирование

Главным объектом любой вашей программы является объект fpgApplication типа TfpgApplication. Как и Application в Lazarus/MSEide+MSEgui он заведует отловом сообщений в программе и перераспределением их куда следует.

Хотя на самом деле fpgApplication - это функция, а не переменная, но при первом вызове она создаёт внутри себя скрытую переменную этого типа и при всех последующих вызовах обращение уже идёт к этой скрытой переменной на протяжении жизни программы. Поэтому, будем считать, что fpgApplication - это уже готовая переменная.

Отличие fpgApplication в fpGUI от Application в Lazarus/MSEide+MSEgui состоит в том, что созданием главной формы приложения она не заведует, поэтому основная программа немножко удлиняется, т.к. необходимо дописать код создания и показа формы:

{$mode objfpc}{$H+}
Program prog_kotomatrica;

uses
  {$IFDEF UNIX}{$IFDEF UseCThreads}
  cthreads,
  {$ENDIF}{$ENDIF}
  Classes, fpg_main, 
  kotomatrica;  //В этом модуле находится описание формы TForm1 

var
  MainForm: TForm1;
begin
  fpgApplication.Initialize;
  MainForm:=TForm1.Create(nil);
  MainForm.Show;
  fpgApplication.Run;
  MainForm.Free;
  fpgApplication.Terminate;
end.

Как видите, ничего необычного. Основная программа выполняет следующие функции:

  • Создаёт и инициализирует скрытый объект Application;
  • Создаёт главную форму программы;
  • Показывает главную форму программы;
  • Переводит Application в режим отлова сообщений в программе;
  • После закрытия формы уничтожает её;
  • Уничтожает объект Application.

Этот код вы можете использовать как шаблон главной программы при написании своих приложений.

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

Uidesigner, в отличие от своих собратьев Lazarus/MSEide, при разработке форм не использует файл ресурсов, а генерирует код создания объектов формы в процедуре события формы AfterCreate() (см. рисунок 3). Практически так же ведёт себя Visual C#.


Рисунок 3. Код создания компонентов на форме

Надо сказать, что своего редактора кода в Uidesigner'е нет, поэтому не убивайте мышку бесконечным количеством двойных щелчков по кнопке или другому компоненту в бесплодных попытках вызвать код какого-нибудь события. Придётся параллельно пользоваться каким-нибудь сторонним редактором, например, для Linux есть очень хороший редактор для программистов - GEANY.

Как вы заметили, на рисунке 2 в колонке свойств объекта есть поля свойств, но совершенно отсутствуют поля событий. Ничего страшного, присваивать свойствам событий наименование процедур можно в поле Неизвестные строки(Unknown lines) (см. рисунок 2). Видимо разработчик до событий в дизайнере пока ещё не добрался. Вы можете ему помочь... Шаблоны и текст самих процедур придётся писать в редакторе ручками (см. рисунок 4). Как это делается и что в них писать, можно посмотреть в примерах к fpGUI.


Рисунок 4. Код процедуры события

Ещё один из недостатков Uidesigner - при добавлении компонентов на форму при генерации кода он забывает включить модуль добавляемого компонента в строку Uses (ошибка). Так что не забывайте их добавлять вручную. В пакете uidesigner для дистрибутива Mageia это исправлено.

Надо сказать, что если вы после работы с Uidesigner'ом потом добавили ещё кучу своего кода в сгенерированный им модуль и решили добавить ещё какие-нибудь визуальные компоненты на форму, то можете смело открывать модуль в Uidesignere'е, ваш код он не тронет.

Вот небольшой практический примерчик - краткая информация о системе. Алгоритм сбора информации строится на том, что в каталоге /proc содержатся файлы с описанием текущей системы. Информацию о процессоре мы возьмём из файла /proc/cpuinfo, информацию о памяти - из файла /proc/meminfo. Информация о ядре ОС берётся из файла /proc/version, информация о названии ОС - из файла /etc/issue. Последний файл есть не во всех дистрибутивах Linux, так что имейте это в виду. У меня получается вот такое окошко (см. рисунок 5):


Рисунок 5. Пример программы - информация о системе

Скачать пример

Как добавить новый компонент в Uidesigner

Новые компоненты в uidesigner добавляются в файл uidesigner/vfdwidgets.pas, в процедуру RegisterWidgets. Для каждого компонента создаётся объект типа TVFDWidgetClass (переменная в процедуре для него уже есть - wc), в конструкторе Create которого в качестве параметра указывается название класса компонента, например TfpgLabel. Далее устанавливается имя компонента (Label) и добавляются его свойства методом AddProperty('Название_свойства', Тип_свойства, 'Комментарий_к_свойству'). Здесь Тип_свойства - это один из предопределённых типов (TPropertyString, TPropertyInteger, TPropertyFloat, TPropertyEnum, TPropertyStringList, TPropertyBoolean, TPropertyFontDesc, TPropertyColor).

Иконка для компонента добавляется в процедуре LoadIcons того же файла с помощью процедуры fpgImages.AddMaskedBMP(). Первый параметр этой процедуры - текстовый идентификатор иконки, второй параметр - ссылка на байтовый массив иконки, третий параметр - размер массива, четвёртый и пятый - левый верхний угол кнопки элемента, которую вы будете кликать, чтобы установить элемент на форму. Как правило два последних параметра - 0, 0. Байтовые массивы иконок хранится в файле uidesigner/icons.inc.

Возникает резонный вопрос - что такое этот самый байтовый массив и как его получить, если под рукой есть только рисунок? После недолгих исследований выяснилось, что байтовый массив - это не что иное, как рисунок формата BMP, считанный побайтно. Для этого можно использовать класс TFileStream.

Когда все свойства добавлены, компонент регистрируется с помощью функции RegisterVFDWidget().

Вот и всё. В принципе, ничего сложного, и как именно это делается можно посмотреть в самом файле uidesigner/vfdwidgets.pas. После добавления необходимых компонентов uidesigner нужно заново перекомпилировать (см. Где взять и как установить).

Документация и примеры

В архиве с fpGUI идёт комплект документации по его компонентам, свойствам и методам. Только документация эта "сырая", в виде xml-файлов. В каталоге, куда вы разархивировали fpGUI, есть подкаталог docs, а в нём скрипт build_html.sh. Необходимо запустить этот скрипт, и тогда в подкаталоге docs/html будут созданы HTML-файлы. Начало просмотра - открыть файл index.html в любом браузере.

В подкаталоге examples можно найти огромное количество примеров. В принципе, по ним можно спокойно пройти начальный курс обучения по работе с fpGUI.

Заключение

fpGUI понравится тем людям, которые не любят визуальное программирование, но любят писать код руками. Для этого fpGUI весьма удобен из-за наличия в нём специальных функций создания компонентов, которые значительно сократят объём кода.

Кроссплатформенность (Windows/Unix/MacOS) позволяет даже при минимуме знаний особенностей той или иной ОС писать кроссплатформенные (переносимые) приложения.

Отсутствие привязки к определённой графической платформе (например, GNOME или KDE) делает программы более шустрыми, хотя с сегодняшним быстродействием процессоров это уже и не так актуально.

Uidesigner - программа для визуального проектирования форм, хотя ещё и далека от совершенства (не все наличествующие компоненты туда внесены и явно не хватает функции автоматического создания шаблона событий, как в Lazarus), тем не менее вполне работоспособна и позволяет сильно ускорить и упростить проектирование формы по сравнению с ручным написанием кода. Также хорошая поддержка русского языка.

Актуальные версии
FPC3.2.2release
Lazarus3.2release
MSE5.10.0release
fpGUI1.4.1release
links