Реализация перемещения формы без заголовка

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

Создадим описание этой процедуры в объявлении класса формы TfmFigura (добавленная строка выделена жирно в листинге):

type

TfmFigura = class(TForm)

Image1: TImage;

procedure FormCreate(Sender: TObject);

procedure DragDrop(var dr: TWMNCHitTest); message wm_NCHitTest;

Тип TWMNCHitTest — это структура, содержащая информацию о положении указателя мыши. Не вдаваясь более в технические детали, создадим тело процедуры в разделе implementation:

procedure TfmFigura.DragDrop(var dr:TWMNCHitTest);

Begin

inherited; //наследует реализацию стандартной

//процедуры DragDrop

//Проверим, был ли щелчок мыши над областью формы

if dr.Result=htClient

then dr.Result:=HTCAPTION;//перенаправляем щелчок

//на заголовок

end;

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

Обработка щелчков мышью

Теперь осталось только каким-то образом обработать щелчки мышью на изображении сундука. Предположим, мы хотим, чтобы щелчок на изображении замка использовался для закрытия окна. Для того чтобы обработать щелчок мышью, разместим на форме компонент Shape категории Additional и установим значения его свойствам согласно табл. 1.3.

Таблица 1.3. Свойства компонента Shape

Свойство Установленное значение Назначение изменения
Name shpExit Новое имя компонента
Shape stEllipse Вид геометрической фигуры
Height 54 Высота фигуры
Width 54 Ширина фигуры
Left 153 Отступ от левого края формы
Top 184 Отступ сверху
Hint Закрыть Текст всплывающей подсказки
ShowHint true Отображать всплывающую подсказку
Cursor crHandPoint Вид курсора при прохождении компонента
Brush.Style bsClear Заливка фигуры прозрачная
Pen.Style psClear У фигуры нет контура

Теперь создадим обработчик события shpExit.OnMouseDown, которое возникает при щелчке на компоненте какой-либо кнопкой мыши:

procedure TfmFigura.shpExitMouseDown(Sender: TObject; Button: TMouseButton; Shift: TShiftState; X, Y: Integer);

Begin

if Button=mbLeft then Close;

end;

Откомпилируем и запустим приложение на выполнение. Пробуем нажать кнопку выключения (т.е. щелкнуть левой кнопкой мыши на изображении замка), но ничего не произойдет. Дело в том, что мы изменили стандартную процедуру DragDrop, и теперь указатель мыши всегда перенаправляется на заголовок формы. Необходимо сделать так, чтобы при размещении указателя над "кнопкой выключения" это перенаправление не происходило. Для этого закроем запущенное приложение и внесем следующие дополнения в процедуру (добавленный фрагмент выделен жирнож):

procedure TfmFigura.DragDrop(var dr:TWMNCHitTest);

begin

inherited;

if dr.Result=htClient

then if not(((dr.XPos-Left)>=shpExit.Left) and ((dr.XPos-Left)<=shpExit.Left+shpExit.Width) and ((dr.YPos-Top)>=shpExit.Left) and ((dr.YPos-Top)<=shpExit.Left+shpExit.Height))

then dr.Result:=HTCAPTION;

end;

Координаты, передаваемые в параметре dr, откладываются относительно верхнего левого угла экрана, поэтому для получения координат относительно левого верхнего угла формы необходимо вычесть из dr.XPos значение свойства fmFigura.Left, а из значения dr.YPos значение свойства fmFigura.Top. Полученные координаты указателя сопоставляются с координатами размещения компонента shpExit, и перенаправление происходит только в том случае, если указатель находится над "кнопкой выключения".

После повторного запуска приложения, "кнопка выключения" уже распознается, а щелчок на ней приводит к завершению работы приложения.

Перетаскивание компонентов в окне приложения

Часто возникает задача перемещения некоторого объекта (одного или нескольких) по форме. Технология перетаскивания (drag and drop – перетащи и оставь) позволяет зацепить мышью визуальный объект на экране и перетащить его в другое место. Решить задачу перемещения можно несколькими способами.

Способ первый. Его суть заключается в том, что свойства Left и Top объекта изменяются на разницу между начальными и конечными координатами (нажатия и отпускания мыши соответственно, рис. 1.3). Этот способ самый простой и надежный, но у него есть один недостаток: Left и Top изменяются по очереди, что приводит к заметному мерцанию.

Рис. 1.3. Положение курсора мыши в координатной системе объекта

Начнем создавать приложение, в котором будем перемещать два объекта Image по форме.

Разместим на форме два компонента Image и вставим в них разные картинки (рис. 1.4). Для адекватного отображения картинок свойство Proportional компонентов Image установим в значение true.

Рис. 1.4. Два компонента Image размещены на форме

Для начала необходимо объявить глобальные переменные (они объявляются в разделе Implementation) x0, y0: integer - они будут запоминать координаты начального положения перемещаемой картинки. И еще нам понадобится переменная drag типа boolean, чтобы нам отличать перемещение мыши над картинкой, от попытки ее сдвинуть:


Понравилась статья? Добавь ее в закладку (CTRL+D) и не забудь поделиться с друзьями:  



double arrow
Сейчас читают про: