Читать книгу Программирование для Android и работа с датчиками в среде Delphi 11 - Виталий Иванович Донцов - Страница 26

11. КОМПОНЕНТЫ ДЛЯ 2D И 3D ГРАФИКИ
11.8. ВОЗМОЖНОСТЬ РИСОВАНИЯ НА ЭКРАНЕ

Оглавление

Для формы существует в Events событие OnTouch, позволяющее рисовать на экране в ответ на прикосновение и движение. Для этого:

Создаем глобальную переменную:

var

Form1: TForm1;

Path: TPathData;


При открытии на OnCreate в Form1 создаем траекторию:

Path:=TpathData.Create;


Подготавливаем сцену для визуализаци в OnPaint и Form1:

with Canvas do

if (Path.Count> 0) and (BeginScene) then

try

Stroke.Kind:=TBrushKind.Solid;

Stroke.Color:=TAlphaColors. Blue;

Stroke.Thickness:=2;

DrawPath (Path,1);

finally

endScene;

end;


Формируем событие OnTouch в Form1:

case Action of

TTouchAction.Down: begin

Path.MoveTo (Touches [0].Location);

end;


TTouchAction.Move: begin

Path.LineTo (Touches [High (Touches)].Location);

FormPaint(Sender,Form1.Canvas,Form1.ClientRect);

end;

В итоге движение пальца рисует синию линию (полилиния – Path).

Для изменения цвета и размера линии нужно ввести компоненты SpinBox и ColorListBox (обеспечивает выбор до 200 цветов), поместив их на Panel. Также нам понадобится Button для стирания рисунка:

Path.Clear; // Очистка компонента – полилиния (Path)

Path:=TpathData.Create; // Создание заново компонента Path

SpinBox1.Value:= 2; // Исходное значение величины кисти

ColorListBox1.Color:= TAlphaColors. Black; //Исходный цвет – черный


Важно: OnTouch реагирует на любое прикосновение к экрану, и чтобы рисунок не выводился на области Panel с компонентами настройки, ограничиваем выведение рисунка областью выше Panel:

if Touches [0].Location. Y <Panel1.Position. Y then

begin

case Action of

TTouchAction.Down: begin……………..


Для перехода в область настройки достаточно коснуться этой области внизу экрана (осторожно, чтобы не закрыть все приложение основными кнопками смартфона «>» и «O»), при этом исчезает рисунок и снова появляется при переходе в область рисивания. Однако, изменение цвета изменяет и цвет всех предыдущих линий, которые все перерисовываются заново с новыми установками цвета и размера линий.

Для того, чтобы рисовать другую линию, нужно ввести новый компонент Path1 (что вполне логично). Также нужно ввести понятие «сессии» и внести на Форму компонент Button для перехода к новой сессии и NumberBox для счета и отображения номера очередной сессии. Теперь на новую сессию рисуется новая линия с новыми настройками:

TTouchAction.Move: begin

if NumberBox1.Value = 1 then Path.LineTo (Touches [High (Touches)]. Location);

if NumberBox1.Value=2 then Path1.LineTo (Touches [High (Touches)]. Location);

Но теперь исчезли все предыдущие линии, что также понятно, так как каждый раз рисунок создается заново, и для того, чтобы были видны предудущие линии нужно, чтобы выводились на рисование ОБЕ линии:

with Canvas do

if (Path.Count> 0) and (BeginScene) then

try

Stroke.Kind:=TBrushKind.Solid;

if NumberBox1.Value = 1 then

begin

Stroke.Color:= TAlphaColors. Blue;

Stroke.Thickness:= 1;

DrawPath (Path,1);

end;

if NumberBox1.Value = 2 then

begin

Stroke.Color:= TAlphaColors. Blue;

Stroke.Thickness:= 1;

DrawPath (Path,1);

Stroke.Thickness:= 5;

Stroke.Color:= TAlphaColors.Red;

DrawPath (Path1,1);

end;

finally

endScene;

end;

В случае сессии 1 рисуется одна линия, а при сессии 2 рисуются (отображаются на экране) обе линии.

Для свободного выбора цветов введем компонент ColorListBox, а для изменения размера линии введем SpinBox. При этом нужно, чтобы они запоминались и считывались по мере увеличения числа сессий; при этом каждая сессия – новый компонент Path и новые установки рисования, причем все возможно задействованные в рисовании компоненты Path должны быть заранее объявлены и созданы как первый.

Новые сессии даже с аналогичным предудыщим старым набором свойств будут задействовать новый Path. Это касается и элемента «Ластик» который по существу является кистью с цветом фона (и настраиваемым размером); причем повторные обращения к Ластику приведут к новому задейстованному компоненту Path и новой сессии.

Для запоминания предудущих сессий подойдет элемент StringGrid, с простым обращением к его ячейкам – StringGrid. Cells [col, row]:

NumberBox1.Value :=NumberBox1.Value +1;//Новая сессия

StringGrid1.Cells [0, Round(NumberBox1.Value)]:= FloatToStr (SpinBox1.Value); //Новая сессия записывается по № сессии

StringGrid1.Cells [1, Round(NumberBox1.Value)]:= FloatToToStr (ColorListBox1.Color);


Для SpinBox1.Value размерность Double, что требует преобразовать его значение в FloatToStr () для таблицы, воспринимающей строковые данные. Для ColorListBox.Color цвет TAlphaColors может выражаться несколькими способами, в том числе цифрами, поэтому казалось бы возможно преобазование IntToStr (), так как цвет в TAlphaColors – это целое число, но это 10-значное число, превосходящее Integer, поэтому используется Double: FloatToStr () для записи, а для чтения из таблицы: Round (StrToFloat ()), так как цвет – это целое число, а Float дробное.

Для строки Таблицы используется номер сессии: NumberBox1.Value, причем, так как NumberBox1.Value имеет размерность Double, а для таблицы нужно целое число, можно NumberBox1.Value округлить: Round ().

В конечном итоге для 3-х сессий получим следующий код:

procedure TForm1.PaintBox1Paint (Sender: TObject; Canvas: TCanvas);

var

i: Integer;

begin

Sender:=PaintBox1;

with Canvas do

if (Path.Count> 0) and (BeginScene) then

try

Stroke.Kind:=TBrushKind.Solid;

if NumberBox1.Value = 1 then //Если первая сессия

begin //Начальные установки – черный цвет на блом фоне

Stroke.Color:= TAlphaColors. Black;

Stroke.Thickness:= 2;

DrawPath (Path,1);

end;

if NumberBox1.Value = 2 then

begin

Stroke.Color:= TAlphaColors. Black;//Сессия 1

Stroke.Thickness:= 2;

DrawPath (Path,1);

Stroke.Thickness:= StrToInt (StringGrid1.Cells [0, 2]); //Сессия 1

Stroke.Color:= Round (StrToFloat (StringGrid1.Cells [1, 2]));

Программирование для Android и работа с датчиками в среде Delphi 11

Подняться наверх