Форум программистов, компьютерный форум, киберфорум
Наши страницы
Delphi для начинающих
Войти
Регистрация
Восстановить пароль
Показать сообщение отдельно
Ztrel
446 / 220 / 42
Регистрация: 14.11.2009
Сообщений: 371
0

Построение графиков функций на канве (Canvas)

27.04.2010, 21:29. Просмотров 63475. Ответов 0
Метки (Все метки)

Эх, ребята, ребята... (в последнее время что-то часто стал это говорить )
Неужели вам лень залезть в поисковик хоть раз? ))

Цитирую с сайта, извините меня модераторы, если что не так Стараюсь сделать как лучше

Начало

Наверное, все видели программы, которых довольно много, для построения всяческих графиков. Если Вы хотите написать что-то подобное на Delphi, то эта статья для Вас. В самых-самых программах Вам предлагается ввести формулу строкой, а не выбирать функции из списка. Самым сложным элементом таких программ является текстовый анализатор. В данной статье я не собираюсь рассказывать, как пишутся текстовые анализаторы. Я собираюсь рассказать о некоторых основных принципах построения графиков, и работы с графикой в среде Delphi без использования специальных графических платформ, таких как DirectX или OpenGL.


Введение

В Delphi для прорисовки различных элементов управления используется специальный класс TCanvas. Можно выделить 4 основных направления, в которых используется этот класс:

1. Загрузка и хранение графических изображений.

2. Создание новых и изменение хранимых изображений с помощью пера, кисти, шрифта.

3. Рисование и/или закраска фигур, линий, текстов.

4. Комбинирование изображений.

Как Вы уже поняли, мы пойдем по третьему направлению.

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


TCanvas


Свойства:


1. property Brush: TBrush;

Данное свойство позволяет определить цвет (Brush.Color) и стиль (Brush.Style) заполнения замкнутых фигур и фона.


2. property ClipRect: TRect; - read-only

Данное свойство позволяет получить доступную область рисования. Вне этой области рисовать невозможно.

Тип TRect, описанный в модуле Windows, имеет следующий синтаксис:

Delphi
1
2
3
4
5
6
7
8
9
10
11
Type 
 
  TRect = record
 
   Case integer of
 
     0: (Left, Top, Right, Bottom: Integer);
 
    1: (TopLeft, BottomRight: TPoint);
 
 end;

3. property Pen: TPen;

Данное свойство позволяет задать цвет пера, рисующего фигуры или линии.


Методы:


1. procedure FillRect (const Rect: TRect);

Метод позволяет заполнить цветом прямоугольную область холста Rect, используя текущее значение кисти Brush.


2. procedure MoveTo (x, y: integer);

Метод позволяет переместить перо в точку (X, Y).

3. procedure LineTo (x, y: integer);

Метод позволяет нарисовать прямую линию, которая начинается с текущей позиции пера и заканчивается точкой (x, y). При рисовании используются текущие установки пера Pen.

Ну вот, пожалуй, и все, что нам будет нужно, для успешного построения графика.


Построение графика. Теория.



Для начала предлагаю немного теории. Мы собираемся писать процедуру построения графика функции на определенной поверхности, заданной свойством Canvas. Я предлагаю поставить оси координат в середине этой области, а график растянуть так, чтобы он растянулся на всю область. Строить мы будем методом lineto. Поэтому нам нужно определиться с шагом изменения величины аргумента. Я предлагаю взять его обратным к масштабу по оси ординат. Так наш график будет выглядеть плавно при любой функции и любом начальном и конечном значении абсциссы. Масштаб по оси абсцисс считается, отношение ширины поверхности к разнице максимального и минимального значения абсциссы. Масштаб по оси ординат считается аналогично: отношение высоты поверхности к разнице между максимальным и минимальным значениями данной функции на данном интервале.


Процедура DrawGraph


Ну вот и все с теорией и я приведу полный код функции, а потом разберем его.


Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
Type TFunc = function (x: real): real;
 
procedure DrawGraph (f: TFunc; a: real; b: real; C: TCanvas);
 
var x, y, h: real;
 
    max, min: real;
 
    sx, sy: real;
 
    xmid, ymid: integer;
 
begin
 
sx := (c.ClipRect.Right)/(b-a);
 
 h := 1/sx;
 
 xmid := c.ClipRect.Right div 2;
 
 ymid := c.ClipRect.Bottom div 2;
 
 x := a;
 
 max := f( x);
 
 min := max;
 
 while x<=b do
 
  begin
 
   y := f( x);
 
   if y<min then min := y;
 
   if y>max then max := y;
 
   x := x + h;
 
  end;
 
 sy := c.ClipRect.Bottom/ (max-min);
 
 c.Brush.Color := clBlack;
 
 c.FillRect(Rect(0, 0, c.ClipRect.Right, c.ClipRect.Bottom));
 
 c.Pen.Color := clYellow;
 
 c.MoveTo(0, ymid);
 
 c.LineTo(c.ClipRect.Right, ymid);
 
 c.MoveTo(xmid, 0);
 
 c.LineTo(xmid, c.ClipRect.Bottom);
 
 x := a;
 
 y := f(x);
 
 c.Pen.Color := clWhite;
 
 c.MoveTo(xmid+round(sx*x), ymid-round(sy*y));
 
 while x<=b do
 
  begin
 
   y := f(x);
 
   c.LineTo(xmid+round(sx*x), ymid-round(sy*y));
 
   x := x + h;
 
  end;
 
end;
А теперь, если Вы чего-либо не поняли, давайте разберем этот код.



Delphi
1
Type TFunc = function (x: real): real;
Здесь я создал тип-функцию, для того, чтобы передавать в функцию построения графика можно было передавать имя функции в эту процедуру.


Delphi
1
procedure DrawGraph (f: TFunc; a: real; b: real; C: TCanvas);
Заголовок функции. Параметры: f – функция, график, которой будем строить. a – начальное значение переменной “x”. b – конечное значение переменной “x”. C – канва, на которой будем рисовать.


Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
sx := (c.ClipRect.Right)/(b-a);
 
 h := 1/sx;
 
 xmid := c.ClipRect.Right div 2;
 
 ymid := c.ClipRect.Bottom div 2;
 
 x := a;
 
 max := f( x);
 
 min := max;
 
 while x<=b do
 
  begin
 
   y := f( x);
 
   if y<min then min := y;
 
   if y>max then max := y;
 
   x := x + h;
 
  end;
 
 sy := c.ClipRect.Bottom/ (max-min);

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


Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
c.Brush.Color := clBlack;
 
 c.FillRect(Rect(0, 0, c.ClipRect.Right, c.ClipRect.Bottom));
 
 c.Pen.Color := clYellow;
 
 c.MoveTo(0, ymid);
 
 c.LineTo(c.ClipRect.Right, ymid);
 
 c.MoveTo(xmid, 0);
 
 c.LineTo(xmid, c.ClipRect.Bottom);

Здесь мы заливаем всю канву черным цветом и рисуем желтым цветом оси координат.


Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
 x := a;
 
 y := f(x);
 
 c.Pen.Color := clWhite;
 
 c.MoveTo(xmid+round(sx*x), ymid-round(sy*y));
 
 while x<=b do
 
  begin
 
   y := f(x);
 
   c.LineTo(xmid+round(sx*x), ymid-round(sy*y));
 
   x := x + h;
 
  end;

Ну и, наконец, нарисовали график нужной нам функции.


Небольшой пример:


Положим на форму одну кнопку и один компонент TImage. Создадим обработчик функции OnClick для кнопки примерно следующего характера, и следующую функцию для расчета функции


Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
Function f(x: real): real;
 
Begin
 
 Result := sin(x)*cos(x);
 
End;
 
 
procedure TForm1.Button1Click(Sender: TObject);
 
begin
 
 DrawGraph (f, -10, 10, Image1.Canvas);
 
end;

Вот и все.

Конец цитаты...

Вернуться к обсуждению:
Построение графиков функций на канве (Canvas)
75
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
27.04.2010, 21:29
Готовые ответы и решения:

Построение графиков функций
Здравствуйте. Подскажите, пожалуйста, какими компонентами мне лучше...

Построение графиков элементарных функций
Добрый вечер, нужно написать программку на delphi небольшую, простенькую...

Delphi. Построение графиков функций
Дана функция y=1/a+b*e^t. Нужно построить график ф-ции, ее первой и второй...

Chart: построение графиков нескольких функций
С использованием компонента Chart построить графики трех прямых каждого типа в...

Построение графиков двух функций на одной форме
Задать два графика на одной форме , на которых будет выдаваться по нажатию...

0
Другие темы раздела
Delphi Вопрос с сортировкой массива http://www.cyberforum.ru/delphi-beginners/thread122852.html
Помогите понять мою ошибку. Я начинающий, весь день пробую написать и что-то никак Задана матрица размером NxM. Получить массив B, присвоив его k-му элементу значение 0, если все элементы k-го...
Delphi Работа с двумя и более формами... Как-то внезапно пришлось научиться писать на делфи, но после паскаля никак не могу освоиться. Буду весьма признателен за помощь) В терминах скорее всего путаюсь, так что строго не судите) ... http://www.cyberforum.ru/delphi-beginners/thread122836.html
Delphi запрос к mysql
помогите. делаю запрос- INSERT INTO `test`.`data` (`12345`)VALUES ('+ '123456789' +') запись добавляется а вот так INSERT INTO `test`.`data` (`12345`)VALUES ('+ 'sdhstjertjwstrjaqjhuqa' +')...
Delphi вещественные типы данных
Раньше не обращал внимания, а щас стало интересно: тип Real, диапозон значений 5e-324..1.7e+308,память для него 6 байт,2 в (6*8) степени=281474976710656 значений. Как он хранит такие большие числа...
Delphi If MediaPlayer.stop ? http://www.cyberforum.ru/delphi-beginners/thread122712.html
Подскажите как сделать : на timer поставить if MediaPlayer1.stop остановлен then lst1.itemsindex:= +1; // listbox И тут вопрос почему не выделение не упускается (вниз или вверх)?...
Delphi В строке символов найти наиболее часто повторяющуюся цифру В строке символов, введенных в StringGrid(1строка), найти наиболее часто повторяющуюся цифру я неочень понимаю, в стринггриде может быть 5 ячеек, а символов внутри нее 15...как нам выделять... подробнее
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2018, vBulletin Solutions, Inc.
Рейтинг@Mail.ru