6. СОЗДАНИЕ ДОПОЛНИТЕЛЬНОГО МОДУЛЯ ПРОЕКТА
6.1. Подключение дополнительного модуля Form4 к проекту
Откройте свой проект с созданными в нем модулями Form1, Form2 и Form3 и подключите дополнительный модуль с формой Form4 аналогично тому, как это было сделано в лабораторной работе №1.
6.2. Компоновка формы Form4
Порядок заполнения формы Form4 элементами управления определяется их расположением на рисунке 2 и аналогичен действиям, выполненными в лаб. раб. №2, за исключением небольших отличий в настройках:
1). Установите компоненты TrackBar1 и TrackBar2 с параметрами:
- Max = 20;
- Min = -20;
- Position = 0;
- TickStyle = tsManual;
2). Компоненты CSpinEdit1 и CSpinEdit2 находятся на вкладке Samples панели компонентов. Для них необходимо установить следующие настройки:
-.MaxValue = 10;
- MinValue = -10;
- Value = 0.
3). Компонент Edit1 находятся на вкладке Standard панели компонентов. Для него необходимо установить следующие настройки:
- Text = 90.
4). Установите кнопки Button1, Button2, Button3, Button4, Button5 и Button6 с соответствующими надписями;
5). Установите движок регулирования скорости вращения TrackBar3 с настройками:
- Max = 10;
- Min = 1;
- Position = 1;
7. РАЗРАБОТКА ФАЙЛА РЕАЛИЗАЦИИ Unit4.cpp
7.1. Предварительные пояснения
Разработку файла реализации будем вести в следующем порядке:
1) Объявим прототипы всех разрабатываемых функций и глобальные переменные, используемые в этих функциях или в обработчиках событий;
2) Выполним предварительную инициализацию переменных;
3) Разработаем функции, обеспечивающие исходную статическую прорисовку объектов, а именно:
- функцию FormPaint – являющуюся обработчиком события OnPaint для формы Form4;
- функцию графического конвейера GrafKonv(), входящую в состав FormPaint;
- функции, входящие в состав графического конвейера;
4) Разработаем функции, обеспечивающие динамические преобразования в режиме анимации:
- создадим обработчики событий для управляющих компонентов, обеспечивающих переносы фигуры и центра вращения;
- создадим обработчики событий для реализации вращения фигуры;
- создадим функцию Povorot();
5) разработаем вспомогательные функции.
7.2. Объявление переменных и функций
На рисунке 3, где изображена структурная схема программы, приведен весь перечень используемых функций. Часть этих функций стандартные, т.е. являются обработчиками инициализирующих или управляющих событий, а часть - функции собственноручной разработки, перечислим их:
- static void GrafKonv(void) - функция запуска графического конвейера;
- static void Preobr(void) - функция преобразования координат фигуры;
- static void Normir(void) - функция нормировки;
- static void ShowAll(void) - функция прорисовки всего изображения;
- static void ShowOsi(void) - функция прорисовки осей координат;
- static void ShowFig(TColorcol, floatmatrT[4][3]) - функция прорисовки фигуры;
- static void Oboznath(float matrTo[4][3]) - функция прорисовки обозначений вершин фигуры;
- static void ShowToht(void) - функция прорисовки точки Е;
- static void Povorot(void) - функция вычисления матрицы вращения;
- static void Zalivka(void) - функция заливки фигуры заданным цветом;
Каждый студент вправе выбирать свой набор функций, свои названия функций и свои списки формальных параметров функций, главное, чтобы была обеспечена корректная работа программы.
Перечислим также имена матриц координат фигуры и матриц преобразования, используемые в функциях:
- static float matrIsx[4][3] - матрица исходных координат фигуры;
- static float matrRez[4][3] - матрица результирующих координат фигуры;
- static float matrTek[4][3] - матрица текущих координат фигуры;
- static float matrTekOld[4][3] - матрица текущих координат фигуры предыдущего преобразования;
- static int matrEkr[4][2] - матрица экранных координат фигуры;
- static float Ted[3][3] - единичная матрица преобразования;
- static float Tpr[3][3] - матрица видового преобразования;
- static float Tvr[3][3] - матрица вращения;
Все эти функции и матрицы объявите глобально. Список переменных, которые необходимо также объявить глобально составьте самостоятельно, используя данные из лабораторной работы №2.
7.3. Разработка функции инициализации исходных данных FormCreate()
Порядок создания обработчика FormCreate полностью идентичен созданию аналогичной функции в лабораторной работе №2. В составе этой функции необходимо проинициализировать графический буфер formBitmap, четыре матрицы: matrIsx[4][3], matrTek[4][3], Ted[3][3], Tpr[3][3] и переменную nOs.
Первичную инициализацию матрицы текущих координат выполните в виде:
for(int i=0; i<4; i++)
for(int j=0; j<3; j++)
matrTek[i][j]=matrIsx[i][j];
Кроме этого, для обеспечения первичной прорисовки фигуры необходимо также заранее прочитать значения исходных параметров компонентов ввода и управления, установленных на форме Form4. К ним относятся следующие команды:
xE = StrToFloat(Form4->CSpinEdit1->Text); // координата x точки E
yE = StrToFloat(Form4->CSpinEdit2->Text); // координата y точки E
tetta= StrToFloat(Form4->Edit1->Text); // угол поворота фигуры
skor=Form4->TrackBar3->Position; // скорость поворота фигуры
Объявите глобально переменные xE, yE, tetta как float, а переменную skor как int.
7.4. Создание обработчика события FormPaint
Процесс создания этого обработчика полностью идентичен созданию аналогичной функции в лабораторной работе №2. Перепишите содержимое этой функции из предыдущей лабораторной работы, поменяв только номер формы.
Запустите проект на исполнение (предварительно закомментировав вызов функции GrafKonv()) и убедитесь, что в окне проекта формы Form4 в его левой части появился белый прямоугольник графического окна.
СТАТИЧЕСКИЙ РЕЖИМ
На этом этапе выполним разработку графического конвейера GrafKonv() и функций, входящих в его состав, что обеспечит исходную, статическую прорисовку всех объектов графического окна:
- осей координат;
- исходной фигуры ABCD;
- обозначений вершин фигуры;
- точки Е – произвольного центра вращения.
7.5. Разработка функции графического конвейера GrafKonv()
Содержание функции GrafKonv полностью совпадает с аналогичной функцией в лабораторной работе №2. Напомним её текст:
void GrafKonv(void)
{
Preobr(); // Вызываем функцию видовых преобразований фигуры
Normir(); // Вызываем функцию нормировки преобразованных координат
ShowAll(); // Рисуем на битмапе всё: оси, фигуру, обозначения, точку Е
}
Подготовьте функцию к отладке, т.е. заглушите вызовы всех, еще не разработанных функций, входящих в состав GrafKonv() и раскомментируйте вызов GrafKonv() в обработчике FormPaint. После этого можно запустить проект на исполнение для проверки.
7.6. Разработка функций Preobr() и Normir()
Содержание функций Preobr() и Normir() полностью совпадает с аналогичными функциями в лабораторной работе №2. Скопируйте эти функции из предыдущей лабораторной работы в состав данной программы. Подготовьте функции к отладке и запустите проект на исполнение для проверки.
7.7. Разработка функции прорисовки изображения ShowAll()
В задачу функции ShowAll() данной лабораторной работы входит последовательный запуск функций, ответственных за прорисовку таких графических объектов как:
- оси координат;
- две фигуры (предыдущая и текущая (преобразованная));
- заливка текущей фигуры;
- обозначения вершин для обеих фигур и точки Е;
- точка E.
Перед вызовами функций заливки и простановки обозначений необходимо проверить состояние флажков, ответственных за их работу. С учетом этого текст функции ShowAll() будет иметь вид:
void ShowAll(void)
{
ShowOsi(); // Прорисовка осей координат
ShowFig(clSilver, matrTekOld); // Прорисовка исходной фигуры серым цветом
ShowFig(clRed, matrTek); // Прорисовка преобразованной(текущей) фигуры
if(Form4->CheckBox2->Checked) // Если 2-ойфлажоквключен,
Zalivka(); // выполняемзаливкутекущейфигуры
if(Form4->CheckBox1->Checked) // Если 1-ыйфлажоквключен,
{Oboznath(matrTekOld); // рисуем обозначения вершин исходной фигуры,
Oboznath(matrTek); // рисуем обозначения вершин текущей фигуры.
}
ShowToht(); // Прорисовка точки E
}
Подготовьте функцию к отладке и запустите программу на исполнение для проверки.
7.8. Разработка функций ShowOsi() и ShowFig()
Тексты функций ShowOsi() и ShowFig() полностью совпадают с аналогичными функциями в лабораторной работе №2. Перепишите содержимое этих функций из предыдущей лабораторной работы.
Подготовьте эти функции к отладке и запустите программу на исполнение, чтобы убедиться в правильности прорисовки осей координат и исходной фигуры. Отладку выполняйте последовательно, сначала для одной функции, затем для второй.
7.9. Разработка функции заливки фигуры Zalivka()
Для заливки (закраски) фигуры заданным цветом применим стандартную функцию пакета C++Builder – FloodFill(). Принцип работы этой функции заключается в закраске всех пикселей, окружающих так называемый затравочный пиксель до тех пор, пока не встретится пиксель другого цвета, отличающийся от затравочного пикселя. Это, как правило, пиксели линий, ограничивающих заливаемую область.
В теле функции Zalivka() нам необходимо рассчитать координаты затравочного пикселя. Возьмем, например, для этого среднюю точку одной их диагоналей нашей фигуры и пересчитаем эти координаты в экранные. Затем, изменим цвет инструмента "Кисть" на заданный по варианту и запустим функцию закраски фигуры – FloodFill(). В заключение не забудем вернуть цвет кисти в исходное положение:
void Zalivka(void)
{
float xF=(matrTek[0][0] + matrTek[2][0])/2; // Вычисляем координаты
float yF=(matrTek[0][1] + matrTek[2][1])/2; // затравочного пикселя
int exF=W/2+int(h*xF); // Преобразуем координаты затравочного
int eyF=H/2-int(h*yF); // пикселя в экранные
FBC->Brush->Color=clRed; // Устанавливаем цвет кисти
FBC->FloodFill(exF, eyF, FBC->Pixels[exF][eyF], fsSurface); // Заливка
FBC->Brush->Color=clWhite; // Возвращаем цвет кисти в исходное
}
Как видно из текста программного кода функции ShowAll(), заливка фигуры осуществляется только в том случае, если включен флажок компонента CheckBox2 ("Заливка фигуры"). Поэтому, необходимо создать обработчик события CheckBox2Click, согласно пояснениям в подразделе 7.15.
Подготовьте функцию к отладке и запустите программу на исполнение. Убедитесь в том, что заливка фигуры выполняется при включении флажка компонента “Заливка”, и наоборот, исчезает при его выключении.
7.10. Разработка функции прорисовки обозначений Oboznath()
Текст функции Oboznath() полностью совпадает с аналогичной функцией в лабораторной работе №2. Перепишите содержимое этой функции из предыдущей лабораторной работы.
Создайте обработчик события CheckBox1Click, согласно пояснениям в подразделе 7.15.
Подготовьте функцию к отладке и запустите программу на исполнение. Проверьте работу флажка CheckBox1Click (“Обозначения”) и убедитесь в правильности прорисовки обозначений вершин фигуры, а также в соответствии между координатами, выведенными возле каждой вершины и реальным местоположением фигуры в декартовой системе координат графического окна.
7.11. Разработка функции прорисовки точки Е
В задачу функции прорисовки точки ShowToht() входит выполнение следующих операций:
- пересчет координат точки Е в экранные;
- рисование точки в виде маленькой окружности;
- заливка точки черным цветом, с использованием функции FloodFill();
- простановка обозначения точки Е с её координатами (если включен флажок CheckBox1).
Значения исходных координат точки E - xE и yE были проинициализированы в составе обработчика FormCreate(), а текущие координаты получаем при обработке событий CSpinEdit1 и CSpinEdit2 во время внесения изменений в эти окошки. Порядок создания обработчиков CSpinEdit1 и CSpinEdit2 будет рассмотрен ниже, в динамическом режиме. Текст программного кода функции ShowToht() имеет вид:
void ShowToht(void)
{
int exE=W/2+int(h*xE);
int eyE=H/2-int(h*yE);
FBC->Ellipse(exE-3, eyE-3, exE+3, eyE+3);
FBC->Brush->Color=clBlack;
FBC->FloodFill(exE, eyE, FPC->Pixels[exE][eyE], fsSurface);
FBC->Brush->Color=clWhite;
if(Form4->CheckBox1->Checked)
FBC->TextOut(exE, eyE-20, "E("+FloatToStr(xE)+","+FloatToStr(yE)+")");
}
Подготовьте функцию к отладке и запустите программу на исполнение. Точка Е будет прорисована в исходном месте - в центре системы координат. При включении флажка "Обозначения" возле точки Е должны появиться её наименование и координаты.
На этом этапе завершается программирование статического изображения исходной фигурыABCD, точки Е и осей координат.
Далее рассмотрим программирование активных обработчиков событий, действия которых должны вызывать преобразование координат фигуры ABCD и точки Е, а также перерисовку всего изображения.
ДИНАМИЧЕСКИЙ РЕЖИМ
7.12. Предварительные замечания
Под динамическим режимом понимается такая работа программы, при которой можно выполнять различные преобразования фигуры ABCD и точки Е. В нашей программе к ним относятся:
- перенос фигуры ABCD вдоль осей X и Y с помощью движков TrackBar1 и TrackBar2;
- перенос точки Е вдоль осей X и Y с использованием компонентов CSpinEdit1 и CSpinEdit2;
- вращение фигуры относительно начала координат с использованием кнопки Button1;
- вращение фигуры относительно произвольной точки E с использованием кнопки Button1 или трех кнопок Button3, Button4 и Button5.
Все перечисленные преобразования выполним в режиме анимации.
Если в предыдущей лабораторной работе мы, при переносе фигуры, сначала вводили параметры переноса в матрицу преобразования Tpr и запускали конвейер обработки изображения с использованием цикла For, то в этой работе для реализации переноса фигуры в режиме анимации будем использовать компонент TrackBar. При перемещении движка этого компонента происходит непрерывное считывание каждой новой позиции движка на его шкале с последующей автоматической перерисовкой формы. Поэтому, для этого случая нет надобности специально формировать цикл, программа сделает это сама.
Точно так же организуем перемещение точки Е, но уже с использованием компонентов CSpinEdit.
Что касается вращения фигуры, то здесь для запуска этого процесса у нас установлена кнопка Button4. Поэтому, для реализации вращения необходимо сформировать цикл, аналогично тому, как это было сделано в предыдущей лабораторной работе. Для пересчета элементов матрицы преобразования (в данном случае это будет матрица вращения Tvr[3][3]) создадим отдельную функцию Povorot(), которую и будем вызывать в цикле, перед каждым запуском конвейера.
Далее мы рассмотрим создание всех вышеперечисленных обработчиков и функций.
7.13. Создание обработчиков событий для движков TrackBar1 и TrackBar2
Создайте обработчики событий для движков TrackBar1 и TrackBar2, аналогично тому как это делалось в лаб. раб. №2, п. 7.11. Движки предназначены для перемещения (переноса) фигуры по осям координатной плоскости: вправо, влево, вверх, вниз. Рассмотрим пример программного кода для TrackBar1:
void __fastcall TForm4::TrackBar1Change(TObject *Sender)
{
for(int i=0; i<4; i++) // Запоминаем значения матрицы координат
for(int j=0; j<3; j++) // перед их преобразованием
matrTekOld[i][j]=matrTek[i][j];
for(int i=0; i<3; i++) // Очищаем матрицу видового преобразования
for(int j=0; j<3; j++) // от предыдущих изменений, т.е. приводим
Tpr[i][j]=Ted[i][j]; // её к единичной матрице
Tpr[2][0]=TrackBar1->Position-oldx; // Вводим параметр переноса по Х в матрицу
// видового преобразования
FormPaint(0); // Вызываем перерисовку изображения
}
Аналогичную функцию с необходимыми изменениями создайте для TrackBar2.
Переменные oldx (и oldy для обработчика TrackBar2) содержат предыдущие значения Position движков TrackBar1 и TrackBar2 . Необходимость учета этих значений связана с тем, что параметр Position движка TrackBar осуществляет полный перенос фигуры, т.е. от начала координат. Это нас не устраивает, так как нам надо переносить фигуру от её предыдущего положения на координатной плоскости на величину изменения положения движка. Поэтому параметры переноса фигуры по оси X или Y вычисляются как разница между текущим значением движков TrackBar1 или TrackBar2 и их предыдущим положением. Необходимые предыдущие значения переменных oldx и oldy можно получить, если например, в функции ShowFig, в самом её конце поместить команды:
oldx=Form4->TrackBar1->Position;
oldy=Form4->TrackBar2->Position;
Переменные oldx и oldy объявите глобально как static int.
Запустите программу на исполнение и проверьте работу движков по перемещению фигуры.
7.14. Создание обработчиков событий CSpinEdit1 и CSpinEdit2
Создайте обработчики событий для CSpinEdit1 и CSpinEdit2.
Компоненты CSpinEdit1 и CSpinEdit2 – представляют собой скроллинговые окошки ввода данных. В нашем конкретном случае через них мы вводим координаты точки Е – т.е. значения переменных xE для CspinEdit1 или yE для CSpinEdit2. Поэтому, содержимым обработчиков событий для этих функций будут команды чтения данных, введенных в эти окошки, и запуск команды перерисовки изображения, после которой точка Е будет прорисована в новом месте. Функция обработки события, например для CSpinEdit1, будет иметь вид:
void __fastcall TForm4::CSpinEdit1Change(TObject *Sender)
{
xE = StrToFloat(Form4->CSpinEdit1->Text);
FormPaint(0);
}
Функция обработки события для CSpinEdit2 создается аналогично.
Запустите программу на исполнение и проверьте работу компонентов CSpinEdit1 и CSpinEdit2 по перемещению точки Е в горизонтальном или вертикальном направлениях.
7.15. Создание обработчиков событий CheckBox1 и CheckBox2
Флажки CheckBox1 и CheckBox2 предназначены для перезапуска графического окна с целью перерисовки изображения с новыми установками: разрешения прорисовки обозначений вершин фигуры ABCD и точки Е и для закраски фигуры заданным цветом. Порядок программирования таких обработчиков был рассмотрен в предыдущих лабораторных работах, из которых известно, что в их содержимое входят только одна команда - FormPaint(0).
7.16. Создание обработчика события для кнопки "Поворот"
Кнопка "Поворот" (Button4) предназначена для запуска видового преобразования типа "вращение" на заданный угол θ для исходной фигуры ABCD.
При нажатии на кнопку "Поворот" должны выполняться следующие действия:
- запоминание текущих координат фигуры в матрице matrTekOld[4][3] – для того, чтобы можно было обозначить предыдущее положение фигуры, т.е. её положение до поворота;
- организация цикла перерисовки фигуры со значениями углов поворота от 0 до θ, с шагом изменения параметра цикла в один градус.
Текст программного кода для этого обработчика имеет вид:
void __fastcall TForm4::Button4Click(TObject *Sender)
{
for(int i=0;i<4;i++)
for(int j=0;j<3;j++)
matrTekOld[i][j]=matrTek[i][j];
for (float i=0; i<abs(tetta); i++)
{
Povorot(); // Пересчет матрицы вращения
FormPaint(0); // Перерисовка графического окна
Sleep(5*skor); // Задержка времени
}
}
Значения угла поворота θ (tetta) и скорости вращения skor были проинициализированы в составе обработчика FormCreate(), а текущие значения угла и скорости вращения получаем при обработке событий Edit1 и TrackBar3 во время внесения изменений в эти окошки. Порядок создания обработчиков Edit1 и TrackBar3 будет рассмотрен ниже.
Перед запуском программы для проверки, предварительно заглушите вызов функции Povorot(). Понятно, что при нажатии на кнопку "Поворот" никакого поворота фигуры мы пока не увидим.
7.17. Разработка функции вращения фигуры Povorot()
Функция Povorot входит в состав обработчика события Button4Click (кнопка "Поворот").
При нажатии на кнопку "Поворот" запускается цикл, в котором эта функция вызывается столько раз, сколько градусов введено в окошко Edit1, с перерисовкой фигуры в каждом новом положении. Благодаря этому создается анимационный эффект вращения фигуры. Функция Povorot используется для реализации вращения фигуры как вокруг начала координат, так и вокруг произвольной точки.
Основное назначение функции Povorot заключается в заполнении ячеек матрицы вращения Tvr[3][3] необходимыми параметрами, для обеспечения поворота фигуры на один градус. Затем эта матрица используется в функции Preobr() в составе конвейера, для преобразования текущих координат фигуры. Последовательность команд этой функции имеет вид:
void Povorot(void)
{
float te;
if (tetta>=0) te= 3.14159/180; // Переводим один градус поворота в радианы
else te=-3.14159/180;
float ll=xE*(1-cos(te))+yE*sin(te); // Вычисляем заранее некоторые параметры
float mm=yE*(1-cos(te))-xE*sin(te); // матрицы вращения
// Формируем матрицу вращения для поворота на один градус
Tvr[0][0]= cos(te); Tvr[0][1]=sin(te); Tvr[0][2]=0;
Tvr[1][0]=-sin(te); Tvr[1][1]=cos(te); Tvr[1][2]=0;
Tvr[2][0]= ll; Tvr[2][1]=mm; Tvr[2][2]=1;
for(int i=0; i<3; i++) // Вносим изменения в текущую матрицу
for(int j=0; j<3; j++) // преобразования
Tpr[i][j]=Tvr[i][j];
}
Уберите заглушку, установленную в обработчике Button4Click перед вызовом функции Povorot(), и запустите программу на исполнение. При нажатии на кнопку "Поворот" исходная фигура начнет вращаться с заданной скоростью до заданного значения угла поворота.
7.18. Создание обработчика события Edit1 для ввода угла поворота
Создайте обработчик события для окошка ввода Edit1 и в состав данной функции введите команду чтения значения угла поворота:
tetta= StrToFloat(Form4->Edit1->Text);
7.19. Создание обработчика TrackBar3 для регулирования скорости вращения
Создайте обработчик события для компонента TrackBar3 и в состав данной функции введите команду:
skor=Form4->TrackBar3->Position;
7.20. Создание обработчика события для кнопки "Исходное"
Создайте обработчик события для кнопки "Исходное" (Button6) уже известным вам способом.
Эта кнопка предназначена для выведения всех переменных, ответственных за положение фигуры ABCD и точки Е в исходное состояние. В составе этого обработчика необходимо выполнить:
- установку в исходные положения движков TrackBar1 и TrackBar2;
- обнуление окошек CSpinEdit - координат точки Е;
- присвоение исходных значений матрицам координат matrTek[4][3] и matrTekOld[4][3].
С учетом этого команды обработчика Button6Click будут иметь вид:
Form4->TrackBar1->Position=0;
Form4->TrackBar2->Position=0;
Form4->CSpinEdit1->Text=0;
Form4->CSpinEdit2->Text=0;
for(int i=0; i<4; i++)
for(int j=0; j<3; j++)
{matrTek[i][j]=matrIsx[i][j];
matrTekOld[i][j]=matrIsx[i][j];
}
И в заключение здесь необходимо вызвать функцию перерисовки изображения - FormPaint(0).
Запустите программу на исполнение, выполните любые изменения положения фигуры и точки Е и затем, нажав на кнопку "Исходное" убедитесь, что фигура, точка и движки элементов управления возвращаются в исходное положение.
7.21. Создание обработчиков событий для кнопок "Шаг 1", "Шаг 2" и "Шаг 3"
Создайте обработчики событий для кнопок Button1, Button2 и Button3.
При последовательном нажатии на кнопки "Шаг 1", "Шаг 2" и "Шаг 3" должно происходить поэтапное преобразование фигуры согласно алгоритму вращения объекта вокруг произвольной точки (см. п. 3.2).
Все эти преобразования, а именно: перенос точки и фигуры таким образом, чтобы точка Е попала в центр координат (Шаг 1), вращение фигуры вокруг начала координат (Шаг 2) и обратный перенос точки и фигуры (Шаг 3) аналогичны раннее рассмотренным функциям, поэтому здесь предлагается создать эти обработчики самостоятельно.
На этом разработка файла реализации для данной лабораторной работы закончена.
Здесь не использована кнопка "Стоп". Надо сказать, что в рассмотренном варианте программы это сделать достаточно сложно, т. к. обычными методами прервать выполнение какой-либо функции невозможно. Но для студентов, знакомых с порядком использования системного таймера, это не составило бы особого труда.
Мы же будем использовать таймер в следующих лабораторных работах.
8. Контрольные вопросы
1. Как выводится матрица для вращения объектов на плоскости?
2. Вокруг какой точки на плоскости вращает объекты матрица вращения?
3. Каково условие «чистого» вращения с помощью матрицы (1)?
4. Какое направление вращения в компьютерной графике принято за «положительное»?
5. У каких элементов матрицы поворота (1) необходимо поменять знак для смены направления вращения? Почему?
6. Как осуществить вращение на плоскости вокруг произвольной точки?
7. Как построить результирующую матрицу для такого преобразования?
8. За сколько шагов можно решить задачу поворота объекта вокруг произвольной точки, лежащей в плоскости координат XOY?
9. Что произойдет, если при выводе результирующей матрицы поменять порядок следования исходных матриц? Почему?
10. Как поменять направление вращения объекта?