В основе любого Dеlрhi-приложения лежит проект. Основой проекта в свою очередь является форма, на которую помещаются необходимые для решения конкретной задачи компоненты. В такой последовательности - проект, формы, компоненты – мы рассмотрим структуру Dеlрhi-приложения. По ходу изложения материала мы будем часто обращаться к примеру с вычислением идеального веса, который был рассмотрен в первой главе. Если вы его забыли, перечитайте первую главу еще раз.
СТРУКТУРА ПРОЕКТА
ПОНЯТИЕ ПРОЕКТА
Вы быстро поймете суть и назначение проекта, если усвоите несколько очень простых и понятных истин. Вот они:
· решаемая на компьютере задача реализуется в виде приложения;
· приложение - это достаточно сложная вещь, которая создается из различных частей;
·
каждая часть размещена в отдельном файле и
выполняет строго определенные функции; набор файлов, необходимых для создания
приложения, называется проектом;
· компилятор последовательно обрабатывает файлы проекта и строит из них выполняемый файл.
С первого взгляда может показаться, что введение проектов добавляет работы пpoграммисту, однако это не так. Среда Delphi прекрасно управляет файлами проекта вообще без вмешательства человека. Вам остается только пользоваться результатами ее труда.
Поняв общую идею проекта, перейдем к конкретике. Проект Dеlрhi-приложения состоит из трех основных типов файлов:
· Файлы описания форм - двоичные файлы с расширением DFM, описывающие формы с компонентами. В этих файлах запоминаются начальные значения свойств, установленные вами в «Инспекторе Объектов».
· Файлы программных модулей - текстовые файлы с расширением РAS, содержащие исходные коды форм на языке Object Pascal. В этих файлах вы пишете методы обработки событий, генерируемых формами и компонентами.
·
Главный файл проекта - текстовый файл с
расширением DPR, содержащий главный программный блок. Файл проекта подключает
все используемые программные модули и содержит операторы для запуска приложения.
Этот файл среда Delphi создает и контролирует сама.
ФАЙЛЫ ОПИСАНИЯ ФОРМ
Помните, с чего вы начинали знакомство с визуальной средой? Конечно, с формы. Так вот, первая составная часть проекта - это двоичный файл с расширением DFM, описывающий форму. В DFМ-файле сохрaняютcя все установки свойств формы и ее компонентов, сделанные вами во время проектиpoвания приложения. Количество DFМ-файлов равно количеству используемых в приложении форм. Например, в нашем примере об идеальном весе используется только одна форма, поэтому и DFМ-файл только один - Unitl.DFM.
Иногда в литературе DFМ-файл называют графическим образом формы. Это всего лишь сравнение, профессиональный программист должен знать о форме чуточку больше. На самом деле образ формы в DFМ-файле не является графическим, он скорее описательный. В DFМ-файле попросту хранятся исходные значения для свойств формы и ее компонентов, заданные вами в «Инспекторе Объектов». Хотя сам DFМ-файл - двоичный, у него существует текстовое представление. Заниматься его изучением не имеет смысла (иначе зачем тогда визуальная среда?), но взглянуть краем глаза будет полезно. Вызовите у формы всплывающее меню щелчком правой кнопки мыши и выберите команду View as Text.
В ответ Delphi заменит графическое изображение формы на следующий текст в редакторе кода:
object Form1: TForm1
Left = 200
Тор = 108
Width = 435
Height =
300
Caption =
'Weight Calculator'
Font.Color
= clWindowText
Font.Height
= -11
Font.Name =
'MS Sans Serif'
Font.Style
= []
PixelsPerInch = 96
TextHeight
= 13
object Button1:
TButton
Left = 288
Тор = 72
Width = 75
Height = 25
Caption =
'Go'
TabOrder =
О
OnClick =
Button1Click
end
object Button2:
TButton
Left = 288
Тор = 176
Width = 75
Height = 25
Caption = 'Close'
TabOrder = 1
OnClick =
Button2Click
end
object Edit1:
TEdit
Left = 64
Тор = 72
Width = 121
Height = 21
TabOrder =
2
end
object Edit2:
TEdit
Left = 64
Тор = 176
Width = 121
Height = 21
TabOrder = 3
end
object Label1:
TLabel
Left = 64
Тор = 56
Width = 82
Height = 13
Caption = 'Inpиt yoиr height:'
end
object Labe12:
TLabel
Left = 64
Тор = 160
Width = 84
'Height = 13
Caption = 'Yoиr ideal
weight:'
end
end
Несмотря на столь длинный текст описания, разобраться в нем совсем несложно. Здесь на специальном языке задаются исходные значения для свойств формы Form1 и ее компонентов Button1, Button2, Edit1, Edit2, Label1, Label2. Большего знать не требуется, поскольку вы всегда будете использовать визуальные средства проектирования и работать с графическим представлением формы, а не с текстовым описанием. Раз так, давайте поспешим вернуться к графическому представлению, не внося в текст никаких изменений. Для этого вызовите всплывающее меню редактора кода и выберите команду View Аs Form.
На экране вновь появится графический образ формы. Если вы все-таки внесли в текст свои корректировки, то они отразятся на внешнем виде формы.
DFМ-файл нужен только на этапе проектирования. При сборке приложения данные DFМ-файла помещаются в область ресурсов выполняемого ЕХЕ-модуля. Во время paботы приложения они интерпретируются, в результате форма и ее компоненты полyчают нужные свойства и отображаются на экране так, как вы задали при проектировании.
ФАЙЛЫ ПРОГРАММНЫХ МОДУЛЕЙ
Каждой проектируемой в
визуальной среде форме соответствует свой программный модуль (unit),
содержащий все относящиеся к форме объявления и методы обработки событий,
написанные на языке Object Pascal. Программные модули размещаются в отдельных
файлах с расширением PAS. Их количество может превышать количество форм. Почему?
Потому, что в ряде случаев РАS-модули могут и не относиться к формам, а
содержать вспомогательные утилиты (процедуры, функции, объекты и т.д.). Наша
задача об идеальном весе очень простая, поэтому в ней имеется только один
программный модуль, связанный с формой. Не
поленитесь изучить его
внимательно:
unit Unitl;
interface
uses
Windows, Messages,
SysUtils, Classes, Graphics, Controls,Forms,
Dialogs, StdCtrls;
type
{ Описание класса, соответствующего форме}
TForml = class(TForm)
Buttonl: TButton;
Button2: TButton;
Edit 1: TEdit;
Edit2: TEdit;
Labell: TLabel;
Labe12: TLabel;
procedure
ButtonlClick(Sender: TObject);
procedure
Button2Click(Sender: TObject);
private
{ private declaratioпs }
public
{ Public declaratioпs }
end;
var
Form1: TForm1; {экземпляр
класса}
imlementation
{$R *. DFM}
{подключение
двоичного образа формы}
procedure
TForm1.Button1Click(Sender: TObject);
beqin
{Реализация алгоритма "вычисления идеального веса"
}
Edit2.Text
:= IntToStr (StrTolnt (Edit1.Text) - 100 - 10);
end;
procedure TForm1.Bиtton2Click(Sender: TObject);
Close;
end;
Дадим необходимые комментарии к тексту программного модуля. В самом начале после слова unit записывается имя модуля:
unit Unit1;
Ни в коем случае не изменяйте это имя вручную. Delphi требует, чтобы имя модуля совпадало с именем файла, поэтому если вы хотите переименовать модуль, сохраните его в файле с новым именем, воспользовавшись командой меню File\Save As. Delphi сама подставит после слова unit новое имя. После этого удалите старый модуль.
Содержание интерфейсной секции модуля (interface) начинается с подключения стандартных модулей библиотеки VCL, в которых определены часто вызываемые подпрограммы и классы помещенных на форму компонентов.
uses
Windows, Messages,
SysUtils, Classes, Graphics, Controls, Forms, Dialogs, StdCtrls;
Delphi формирует список модулей без вашего участия и автоматически пополняет его, когда вы добавляете на форму новые компоненты. В принципе список подключенных модулей можно изменять вручную.
Смотрим дальше. В разделе описания типов (type) объявлен класс формы. По умолчанию он называется TForm1 и порожден от стандартного класса TForm.
type
TForm1 = class (TForm)
Button1: ТВuttоп;
Button2: TBиtton;
Edit1:
TEdit;
Edit2:
TEdit;
Label1:
TLabel;
Labe12:
TLabel;
procedure
ButtonlClick(Sender: TObject);
procedure Bиtton2Click(Sender:
TObject);
private
{ Private declaratioпs }
public
{ Public declaratioпs }
end;
Помещенные на форму компоненты представлены полями формы. У нас на форме шесть компонентов, поэтому и полей в описании класса - тоже шесть. Имена полей совпадают с именами компонентов, заданными в окне «Инспектора Объектов».
После полей идут заголовки
методов обработки событий. Название каждого такого метода Delphi формирует
автоматически на основании имени компонента и имени генерируемого им события.
Например, для кнопки Button1 метод обработки событий OnClick
называется Button1Click.
Обратите внимание, что поля, представляющие компоненты формы, а также методы обработки событий получают атрибут видимости published (он принимается по умолчанию для всех наследников TForm). Благодаря этому вы можете работать с ними на визуальном уровне, например видеть их имена в окне «Инспектора Объектов». Поскольку Delphi умеет понимать содержимое секции published на этапе проектирования, никогда не модифицируйте эту секцию вручную, пользуйтесь визуальными инструментами: «Палитрой Компонентов» и «Инспектором Объектов». Запомните:
· когда вы помещаете на форму компоненты, Delphi сама добавляет в описание класса соответствующие поля, а когда вы удаляете компоненты с формы, Delphi удаляет их поля из описания класса;
· когда вы определяете в форме или компонентах обработчики событий, Delphi сама определяет в классе соответствующие методы, а когда вы удаляете весь код из методов обработки событий, Delphi удаляет и сами методы.
Для вашего удобства в классе формы заранее объявлены пустые секции private и pubIic, в которых вы можете размещать любые вспомогательные поля, методы и свойства. Визуальная среда Delphi их «в упор не видит», поэтому с ними можно работать только на уровне программного кода, т.е. в «Редакторе Кода».
После описания класса идет объявление собственно объекта формы:
var
Forml: TForml;
Form1 - это переменная, которая содержит ссылку на объект класса TForm1. Конструирование объекта Form1 выполняется в главном файле проекта - DРR-файле (см. далее).
На этом содержание интерфейсной секции модуля заканчивается и начинается ceкция реализации (lmplementation). Сначала в ней подключается файл описания формы:
{$R *.DFM}
Пожалуйста не подумайте, что эта директива подключает все файлы с расширением DFМ. Подключается лишь один DFМ-файл, в котором описана форма данного модуля. Имя DFМ-файла получается заменой звездочки на имя модуля, в котором записана директива.
Далее следует реализация
методов обработки событий. Пустые заготовки для них Delphi создает сама
одновременно с добавлением заголовков в класс формы. Вы же начиняете их
операторами.
procedure
TForm1.Button1Click(Sender: TObject);
begin
{Реализация
алгоритма
"вычисления оптимального веса"}
Edit2.Text
:= IntToStr(StrToInt(Edit1.Text) - 100 - 10);
end;
procedure
TForm1.Button2Click(Sender: TObject);
begin
Close;
end;
Внимание! Если вы хотите удалить метод обработки события и убрать ссылки на него, просто сделайте метод пустым, удалив весь написанный вами код, включая комментарии и объявления локальных переменных. При сохранении или компиляции проекта Delphi сама выбросит из текста пустые методы.
При внимательном изучении исходного текста модуля остается невыясненным один вопрос: как обеспечивается вызов методов Button1Click и Button2Click при нажатии на форме кнопок, ведь в тексте модуля отсутствует даже намек на это. Все очень просто. Загляните в DFМ-файл, точнее, в его текстовое представление, приведенное выше. Кроме установки значений свойств вы найдете также установку обработчиков событий.
object Button1:
TButton
…
OnClick = Button1Click
end
object Button2:
TButton
OnClick =
Button2Click
end
Благодаря этому обеспечивается привязка методов формы к соответствующим событиям. Кстати, смысл приведенного фрагмента описания становится более прозрачным, если вспомнить, что события в языке Object Pasca1 - это на самом деле свойства, но их значениями являются указатели на методы. Таким образом, установка событий мало чем отличается от установки свойств формы, ведь по природе это одно и то же.
Мы достаточно глубоко погрузились во внутреннее устройство файлов описания форм и файлов программных модулей и, признаемся, сделали это намеренно, чтобы дать вам полное понимание вопроса, не заставляя принимать на веру далеко не очевидные вещи. А сейчас пора всплыть на уровень проекта и посмотреть, что же объединяет все эти файлы.
ГЛАВНЫЙ
ФАЙЛ ПРОЕКТА
В самом деле, как компилятору узнать, какие конкретно файлы входят в проект? Должно же быть какое-то организующее начало? Да, и оно есть. Это так называемый файл проекта, имеющий расширение DPR (сокр. от Delphi PRoject). Он представляет собой главный программный файл на языке Object Pascal, который подключает с помощью оператора uses все файлы модулей, входящих в проект. Для каждого проекта существует только один DРR-файл.
Когда вы по команде File\New Application начинаете разработку нового приложения, среда Delphi автоматически создает файл проекта. По мере создания новых форм содержимое этого файла видоизменяется автоматически. Когда вы закончите работу и будете готовы компилировать проект, в DРR-файле будет находиться перечень программных модулей, которые будут поданы на вход компилятору. Чтобы увидеть содержимое DРR-файла нашего приложения, вычисляющего идеальный вес, выберите в меню Delphi команду View\Project Source. В «Редакторе Кода» появится новая страница со следующим текстом:
proqram projectl;
uses
Forms,
Unitl in
'Unitl.pas' {Forml};
{$R *.RES}
begin
Application.lnitialize;
Application.CreateForm(TForml, Form1);
Application.Run;
end.
Немного прокомментируем этот текст. Подключение модуля Fоrms обязательно для всех программ, так как в нем содержится определение объекта Application. Этот объект лежит в основе любого Dеlрhi-приложения и доступен на протяжении всей его работы.
Подключаемый следом модуль Unit1 содержит определение формы приложения. Нaзвание формы приводится в фигурных скобках. Директива in указывает на то, что модуль является необходимой частью проекта и существует в виде исходного текста на языке Object Pascal.
Директива {$R *.RES} подключает к результирующему ЕХЕ-файлу так называемые ресурсы в данном случае - значок приложения. Этот значок будет виден на «Панели задач Windows».
Дальше следует главный программный блок, содержащий вызовы трех методов объекта Application. Вызов метода Initialization подготавливает приложение к работе, метод CreateForm загружает и инициализирует форму Form1, а метод Run активизирует форму и начинает выполнение приложения. Фактически время работы метода Run – это время работы приложения. Выход из метода Run происходит тогда, когда пользователь закрывает главную форму приложения; в результате приложение завершается.
Внимание! Никогда не изменяйте DPR-файл вручную. Оставьте эту работу для Delphi. Добавление и удаление модулей, а также управление созданием форм осуществляется с помощью команд и диалоговых окон визуальной среды.
ДРУГИЕ ФАЙЛЫ ПРОЕКТА
Выше мы рассмотрели основные файлы проекта. Кроме них существует ряд дополнительных файлов:
· Файл ресурсов с расширением RES (сокр. от RESource). В нем, например, хранится пиктограмма приложения, которая будет видна на «Панели Задач Windows». О том, как задать пиктограмму приложения, мы расскажем при обсуждении вопросов управления проектом.
· Подключаемые в модулях объектные файлы с расширением ОBJ, написанные на других языках, например, на С++.
· Файл опций с расширением DOF (сокр. от Delphi Options File), где сохраняются заданные программистом параметры компиляции и компоновки проекта.
· Файл с расширением DSK (сокр. от DeSКtop), где размещены настройки визуальной среды, используемые с данным проектом. (Чтобы Delphi сохраняла настройки среды в DSК-файле, выберите в меню команду Tools\Options... и в диалоговом окне Enviгonment Options на странице Pгefeгences в группе Autosave options отметьте пункт Desktop.)
В проект могут входить также логически автономные элементы: точечные рисунки (BМР-файлы), значки (IСО-файлы), файлы справочников (НLР-файлы) и т.п., однако ими управляет сам программист.
Теперь можно уточнить схему, отражающую структуру проекта, как показано на рис.:
Итак, состав проекта понятен. Нужно теперь выяснить, как им управлять - создавать и сохранять проект, добавлять и удалять модули, устанавливать опции компилятора и компоновщика, компилировать и запускать приложение. Этим сейчас и займемся.