Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:

Ракитин Р.Ю. ООП в Turbo Delphi

.PDF
Скачиваний:
53
Добавлен:
18.03.2015
Размер:
3.59 Mб
Скачать

61

Рассмотрим приложение, в котором при нажатии

на переключатель RadioGroup в объекте Label отображается название этой кнопки. При этом в зависимости от нажатого переключателя, гарнитура шрифта в метке меняется. Обработаем событие

OnClick.

procedure TForm1.RadioGroup1Click(Sender: TObject); begin

Label1.Caption:='нажата "'+ RadioGroup1.Items.Strings[RadioGroup1.ItemIndex]+ '" кнопка';

case RadioGroup1.ItemIndex of

0:Label1.Font.Name:='Times New Roman';

1:Label1.Font.Name:='Arial';

2:Label1.Font.Name:='Courier New Cyr'; end;

end;

События формы

Рассмотрим описание большинства событий, которые может обрабатывать главная форма приложения. Общее число событий не ограничивается стандартными, они могут быть дополнены обработчиками созданными программистом. Ниже будут рассмотрены события, которые наиболее часто используются в Delphi. События, которые может обработать компонент можно увидеть на вкладке Events (события) инспектора объектов.

OnActivate генерируется когда приложение стало активным;

OnCanResize это событие генерируется перед тем, как изменить размер окна. Здесь можно запретить какие-либо изменения или производить какие-то подготовительные действия;

OnClick генерируется, когда пользователь щелкнул по форме (одинарное нажатие левой кнопкой мыши);

OnClose генерируется, когда окно закрывается;

OnCloseQuery генерируется до закрытия окна. В этом обработчике происходит запрос на закрытие, поэтому из этого обработчика можно вывести окно, которое будет запрашивать подтверждение на закрытие;

OnCreate генерируется, когда окно создается;

OnDblClick генерируется, когда пользователь дважды щелкнул по окну; OnDeactivate генерируется, когда окно деактивируется;

OnDestroy когда окно уничтожается;

ОnHide генерируется, когда окно исчезает из виду. Событие генерируется даже тогда, когда память, выделенная для окна, не уничтожается;

OnKeyDown генерируется, когда нажата клавиша на клавиатуре;

62

OnKeyPress генерируется, когда нажата и отпущена клавиша на клавиатуре; OnKeyUp генерируется, когда отпущена клавиша на клавиатуре; OnMouseDown генерируется, когда нажата кнопка мыши;

OnMouseMove генерируется, когда двигается мышка; OnMouseUp генерируется, когда отпускается кнопка мыши; OnMouseWheel генерируется колесиком мыши;

OnMouseWheelDown генерируется, когда колесико мыши прокручено вниз; OnMouseWheelUp генерируется, когда колесико мыши прокручено вверх; OnPaint генерируется, когда надо перерисовать окно;

OnResize генерируется, когда надо изменить размеры окна; OnShortCut когда нажата горячая клавиша;

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

Каждое из стандартных событий связано с методами, в которые могут передаваться различные параметры, например код нажатой клавиши, состояние служебных клавиш, координаты мыши т.д. Более подробно основные события и связанные с ними обработчики будут рассмотрены ниже.

Обработка щелчка мыши

Управление большинством программ Windows осуществляется с помощью мыши. Помимо стандартных действий с элементами управления мышь также используется для самых разных дополнительных операций (например, для вызова контекстного меню при щелчке правой кнопкой). В системе Delphi имеется возможность обработки фактического щелчка мышкой на объекте. Такая возможность используется, когда важно просто среагировать на щелчок, не анализируя координаты указателя. Для этого обрабатывают событие OnClick, пример использования данного события был подробно рассмотрен выше.

Такой подход далеко не всегда устраивает разработчика, поэтому в Delphi имеются события: OnMouseDown (при нажатии кнопки мыши) и OnMouseUp (при отпускании кнопки мыши). Они содержат подробную информацию о параметрах щелчка: координаты указателя в рамках клиентской области объекта, на котором был выполнен щелчок, тип щелчка (одинарный или двойной), какая кнопка мыши была нажата/отпущена и в каком состоянии системные клавиши SHIFT, ALT, CTRL.

Обработчики этих событий отличаются только названиями, списки их параметров полностью совпадают. Например, для события OnMouseDown обработчик имеет вид:

63

Procedure TMyForm.ButtonlMouseDown (Sender: TObject; Button: TMouseButton; Shift: TShiftState; X, Y: Integer);

Параметр Sender определяет, какой объект программы вызывает данную подпрограмму. Тип TMouseButton является перечислимым типом и содержит три значения: mbLeft, mbRight, mbMiddle (признаки использования, соответственно, левой, правой и средней кнопок мыши). Тип TShiftState представляет собой множество системных клавиш и клавиш мыши:

type

TShiftState = set of (ssShift, ssAlt, ssCtrl, ssLeft, ssRight, ssMiddle, ssDouble);

то есть допускается одновременная обработка нескольких клавиш.

Для демонстрации возможностей события создадим следующее приложение. На форме разместим компоненты: Button, BitBtn, CheckBox и RadioButton, а также Label для вывода результата работы. Выделим объект Button и перейдем в окно

Object Inspector (Инспектор объектов) на вкладке Events

создадим обработчик для события OnMouseDown для

этого перейдем на нужную строку и в правой части два раза щелкнем мышкой. Автоматически создастся заготовка для обработчика события. В обработчике запишем:

procedure TForm1.Button1MouseDown(Sender: TObject; Button: TMouseButton;

Shift: TShiftState; X, Y: Integer); begin

//приводим тип и выводим его имя

Label1.Caption := 'щелчок на ' + (Sender as TComponent).Name;

{проверяем какая кнопка мыши была нажата и добавляем соответствующую надпись} case Button of

mbMiddle: Label1.Caption:= Label1.Caption+ ' средней кнопкой';

mbLeft: Label1.Caption:= Label1.Caption+

'левой кнопкой'; mbRight:Label1.Caption:= Label1.Caption+

'правой кнопкой';

end;

{проверяем какая служебная кнопка была нажата и добавляем соответствующую надпись}

if ssShift in Shift then

Label1.Caption:= Label1.Caption+' с Shift';

64

if ssAlt in Shift then

Label1.Caption:= Label1.Caption+' с Alt'; end;

Теперь остальным объектам присвоим этот обработчик, для этого выделяем нужный объект

(BitBtn, CheckBox или RadioButton) и, перейдя на вкладку Events, возле события OnMouseDown, выбираем ранее созданный обработчик для Button1. Таким образом, в полученном приложении будет выводиться строка с именем объекта, на который нажали, название клавиши мыши и имя той системной клавиши, которая при этом удерживается.

Обработка нажатия клавиатуры

Помимо событий мыши, необходимо обрабатывать события, возникающие при нажатии различных клавиш на клавиатуре. В оконных компонентах Delphi определены три события, связанные с клавиатурой:

OnKeyDown событие наступает при нажатии пользователем любой клавиши. Можно распознать нажатые клавиши, включая функциональные клавиши,

икнопки мыши, но нельзя распознать символ нажатой клавиши; OnKeyPress событие наступает при нажатии пользователем клавиши

символа. Можно распознать только нажатую клавишу символа, различить символ в верхнем и нижнем регистре, различить символы кириллические и латинские, но нельзя распознать функциональные клавиши и кнопки;

OnKeyUp событие наступает при отпускании пользователем любой клавиши. Можно распознать нажатые клавиши, включая функциональные клавиши

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

Создадим приложение, в котором разместим три объекта Метка LbDown, LbUp, LbPress, в них будем выводить случайные числа при наступлении соответствующих событий OnKeyDown, OnKeyUp, OnKeyPress. Примерный вид приложения показан на рисунке.

Каждый из обработчиков имеет параметр Key, возвращающий код клавиши, которая была нажата на активном объекте. Подробнее о значениях кодов клавиш клавиатуры смотрите в приложении. Так же для обработчиков OnKeyDown, OnKeyUp существует дополнительный параметр Shift, характеризующий состояние служебных клавиш. Данный параметр был рассмотрен ранее.

+ Тип параметра Key зависит от обрабатываемого события. Для

событий OnKeyDown и OnKeyUp он целый, для OnKeyPress

символьный, поэтому записывается со знаком # или в кавычках.

Создадим обработчики данных событий для формы.

65

procedure TForm1.FormKeyDown(Sender: TObject; var Key: Word; Shift: TShiftState);

begin

//срабатывает если нажат Enter и удерживается Shift if (Key=13)and (Shift=[ssShift]) then

LbDown.Caption:=FormatFloat('0.00',random) end;

procedure TForm1.FormKeyUp(Sender: TObject; var Key: Word; Shift: TShiftState);

begin

//срабатывает если отпущен Enter if Key=13 then

LbUp.Caption:=FormatFloat('0.00',random)

end;

procedure TForm1.FormKeyPress(Sender: TObject; var Key: Char);

begin

//срабатывает если нажат Space if Key=#32 then

LbPress.Caption:=FormatFloat('0.00',random)

end;

Как видно из приведенного примера, необходимые действия связываются с нажатием определенной клавиши. Такой подход позволяет в одном обработчике описывать действия, происходящие при нажатии нескольких клавиш на клавиатуре.

Часто возникает необходимость запретить пользователю вводить определенные символы в объектах ввода текстовой информации. Рассмотрим приложение, в

котором при вводе символов с клавиатуры в объекте Edit разрешается ввод только чисел и запятой. Примерный вид

окна показан на рисунке. После нажатия Ввода введенное значение передается в объект Label. Для доступа к текстовому полю объект Edit имеет свойство Text. Остальные свойства данного компонента будут рассмотрены позднее.

Обработчик события OnKeyPress компонента TEdit запишем следующим образом.

procedure TForm1.Edit1KeyPress(Sender: TObject; var Key: Char);

const

{задаем допустимые символы из цифр,

запятой, клавиш Backspace и Enter} MyChar = ['0'..'9',',', #8, #13];

begin

//допустимый разделитель «запятая» if Key = '.' then Key:=',';

66

{если введенный символ не в допустимом наборе, то он стирается}

if not (Key in MyChar) then Key:=#0;

//если нажат Ввод, то проводим необходимые действия if Key = #13 then begin

...

Label1.Caption:=Edit1.Text;

...

end; end;

В приложении дополнительно предусмотрена замена разделителя «точка» на разделитель «запятая». Для возможности стирания введенных символов в качестве допустимого символа также добавим код клавиши Backspace (#8). К допустимым относится код клавиши Enter (#13), что позволяет обработать ее нажатие и выполнить перенос введенных текстовых данных из Edit в Label.

Процедуры и функции вызова диалоговых окон

В Windows работа приложений носит диалоговый характер. В Delphi имеются специальные компоненты вызова стандартных диалоговых окон (см. Главу 11). Часто пользователю необходимо уведомить пользователя о работе программы, запросить выбор некоторого варианта дальнейшего действия, запросить ввод некоторых параметров. Для всех этих целей используются диалоговые окна. Вызов таких окон осуществляется с помощью специальных методов, описанных в модуле Dialogs, рассмотрим их подробнее:

Показывает простое диалоговое окно с кнопкой ОК, содержащее заданную

строку

procedure ShowMessage (const Text: string);

Данная процедура используется, чтобы

сообщить

пользователю

какую-либо

информацию

без

необходимости

принимать

решение.

Для

вывода

многострочного сообщения, необходимо в

переменную Text вставить символы возврата каретки и переноса строки (#13#10).

Показывает строку в простом диалоговом окне, размещенном в заданном

месте

procedure ShowMessagePos (const Text: string; const XPos, YPos: Integer);

Левый верхний угол диалога располагается в заданных (в пикселях) экранных координатах (XPos, YPos). В остальном он аналогичен диалогу

ShowMessage.

67

Отображает сообщение, значок и выбираемые кнопки

function MessageDlg (const Message: string; DialogType: TMsgDlgType; Buttons: TMsgDlgButtons; HelpContext : longint): integer;

Функция используется для отображения сообщений пользователю. Эти сообщения могут быть информационными, предупреждающими или другого типа. Можно определить перечень отображаемых на диалоге кнопок.

Вид отображения окна задается параметром DialogType.

Значение

Описание

mtWarning

Окно замечаний

mtError

Окно ошибок

mtInformation

Информационное окно

mtConfirmation

Окно подтверждения

mtCustom

Заказное окно без рисунка

Параметр Buttons определяет, какие кнопки будут присутствовать в окне.

Значение

Надпись на кнопке

mbYes

Yes

mbNo

No

mbOk

Ok

mbCancel

Cancel

mbHelp

Help

mbAbort

Abort

mbRetry

Retry

mbIgnore

Ignore

mbAll

All

mbNoToAll

NoToAll

mbYesToAll

YesToAll

Также определены константы, соответствующие часто используемым

сочетанием кнопок

Значение

Надпись на кнопках

mbYesNoCancel

Входят кнопки Yes, No, Cancel

mbOkCancel

Входят кнопки Ok, Cancel

mbAbortRetryIgnore

Входят кнопки Abort, Retry, Ignore

mbYesAllNoAllCancel

Входят кнопки Yes, YesToAll, No, NoToAll, Cancel

68

Функция возвращает значение, соответствующее нажатой кнопке диалога:

Значение

Нажатая кнопка

mrYes = 6

Yes

mrNo = 7

No

mrOk = 1

Ok

mrCancel = 2

Cancel

mrAbort = 3

Abort

mrRetry = 4

Retry

mrIgnore = 5

Ignore

mrAll = 8

All

mrNoToAll = 9

NoToAll

mrYesToAll = 10

YesToAll

Например, процедура

MessageDlg('Диалоговое окно MessageDlg', MtWarning, [MbYes, MbNo, MbCancel, MbAll, MbHelp],0) создаст окно вида:

Предоставляет форматирование множества простых типов данных,

которые показываются один за другим в строку

procedure ShowMessageFmt (const Formatting: string; const Data: array of const);

Процедура показывает пользователю диалоговое окно, содержащее кнопку ОК. Строка Formatting может состоять из набора обычных символов и из символов форматирования данных.

Каждая подстрока форматирования данных начинается со знака «процент» (%) и заканчивается указателем на тип данных: d десятичный (целый); e научный; f фиксированный; g общий; m денежный; n число (с плавающей запятой); p указатель; s строка; u без знаковое целое; x шестнадцатеричное. Более подробно данное форматирование будет рассмотрено в Главе 6.

Например, следующий код

a:='Hello'; b:=256; c:=455.6565665; ShowMessageFmt('В строку можно добавить'+ #13#10 +

'строку: %s'+ #13#10+'число: %d'+ #13#10+ 'или еще число: %e', [a,b,c]);

69

покажет диалоговое окно вида

Отображает диалог, который просит пользователя о вводе текста

function InputQuery (const Caption, Prompt: string; var UserValue: string): boolean;

Функция отображает простое диалоговое окно с данным заголовком (Caption), подсказкой (Prompt) и полем ввода. В нём необходимо ввести данные. Если пользователь нажал OK, то введенные данные сохраняются в переменной UserValue, и возвращаемое значение будет True. В противном случае возвращаемое значение будет False.

Например, в следующем примере будет выведено окно с запросом имени, значение которого сохранится в случае нажатия Ok в переменной value.

InputQuery('Test program', 'Пожалуйста, укажите своё имя', value)

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

function InputBox (const Caption, Prompt, Default: string): string;

Функция отображает простое диалоговое окно с заданным заголовком (Caption) и подсказкой (Prompt). Оно просит, чтобы пользователь ввел данные в текстовое поле на диалоговом окне и возвращает его. Значение по умолчании (Default) отображено в текстовом поле.

Подтверждение закрытия программы

После завершения работы любого приложения возникает необходимость в выполнении определенных действий, предшествующих закрытию основной формы. К таким действиям, например, можно отнести сохранение данных открытого приложения. Рассмотрим способы корректного завершения работы приложения.

70

Закрытие приложения можно организовать, используя один из следующих способов:

нажатие крестика на главном окне;

вызов метода приложения Application.Terminate;

вызов метода Close для главной формы.

При закрытии приложения генерируются события OnClose и OnCloseQuery. Используя соответствующие методы данных событий, можно вывести диалоговые окна, сигнализирующие пользователю о необходимости проведения некоторых действий. Например, организуем запрос подтверждения выхода из приложения.

Создадим обработчик события OnClose для главной формы. procedure TForm1.FormClose(Sender: TObject;

var Action: TCloseAction); begin

if MessageDlg('Вы уверены что приложение нужно закрыть?', mtWarning,[mbYes, mbNo],0)=mrNo

then Action:=caNone; end;

В данном случае при нажатии «No» (Нет) на диалоговом окне в свойство Action основной формы запишем значение caNone (нет действия для объекта), вместо текущего caClose (то есть действие закрытия формы). В случае если нажата кнопка «Yes» (Да), процесс закрытия продолжится. Аналогичного результата можно добиться, обработав событие формы OnCloseQuery:

procedure TForm1.FormCloseQuery(Sender: TObject; var CanClose: Boolean);

begin

if MessageDlg('Вы уверены что приложение

нужно закрыть?', mtWarning,[mbYes, mbNo],0)=mrNo then CanClose:=false;

end;

Переменная CanClose при закрытии приложения принимает значение True, для того, чтобы отменить закрытие, изменим значение на False.