Навигация
Главная
Поиск
Форум
FAQ's
Ссылки
Карта сайта
Чат программистов

Статьи
-Delphi
-C/C++
-Turbo Pascal
-Assembler
-Java/JS
-PHP
-Perl
-DHTML
-Prolog
-GPSS
-Сайтостроительство
-CMS: PHP Fusion
-Инвестирование

Файлы
-Для программистов
-Компонеты для Delphi
-Исходники на Delphi
-Исходники на C/C++
-Книги по Delphi
-Книги по С/С++
-Книги по JAVA/JS
-Книги по Basic/VB/.NET
-Книги по PHP/MySQL
-Книги по Assembler
-PHP Fusion MOD'ы
-by Kest
Professional Download System
Реклама
Услуги

Автоматическое добавление статей на сайты на Wordpress, Joomla, DLE
Заказать продвижение сайта
Программа для рисования блок-схем
Инженерный калькулятор онлайн
Таблица сложения онлайн
Популярные статьи
OpenGL и Delphi... 65535
Форум на вашем ... 65535
HACK F.A.Q 65535
Бип из системно... 65535
Гостевая книга ... 65535
Invision Power ... 65535
Содержание сайт... 65535
Организация зап... 65535
Вызов хранимых ... 65535
Программируемая... 65535
Эмулятор микроп... 65535
Подключение Mic... 65535
Создание потоко... 65535
Приложение «Про... 65535
Оператор выбора... 65535
Создание отчето... 63912
Модуль Forms 63636
ТЕХНОЛОГИИ ДОСТ... 60488
Пример работы с... 59881
Имитационное мо... 55959
Реклама
Сейчас на сайте
Гостей: 4
На сайте нет зарегистрированных пользователей

Пользователей: 13,079
новичок: Openair
Новости
Реклама
Выполняем курсовые и лабораторные по разным языкам программирования
Подробнее - курсовые и лабораторные на заказ
Delphi, Turbo Pascal, Assembler, C, C++, C#, Visual Basic, Java, GPSS, Prolog, 3D MAX, Компас 3D
Заказать программу для Windows Mobile, Symbian

Двунаправленный динамический список на Delphi + Блок схемы
Программа тестирования (тест) - вступительные экзамены (математика, физи...
Поиск пути в графе заданном списками инцедентности на Turbo Pascal

Реклама



Подписывайся на YouTube канал о программировании, что бы не пропустить новые видео!

ПОДПИСЫВАЙСЯ на канал о программировании
Мы ознакомимся с основными принципами организации трехмерных построений в библиотеке OpenGL. Вы научитесь рисовать графические примитивы (сфера, параллелепипед, цилиндр и т.д.), СПЛАЙНЫ
В выполнялось построение точек, линии и многоуголь-
ников при помощи команд: gIBegin, glEnd. Причем координаты вершин задавались
при помощи процедуры glVertex2f. Аналогично строятся точки, линии и отрезки в
трехмерном пространстве при помощи процедуры
glVertex3f(x: Single, y: Single, z: Single)


только координаты точек задаются тремя значениями.
Теперь можно строить многогранники в трехмерном пространстве, собирая
их из многоугольников-граней. Однако, такой способ построения таких трехмерных
объектов как сфера, цилиндр, конус, диск и т.д. очень неудобен. Поэтому была
разработана специальная надстройка над OpenGL – библиотека glu. Для ОС се-
мейства Windows она реализована в виде динамической библиотеки glu32.dll. С
помощью библиотеки glu вы сможете легко строить трехмерные примитивы (Quadric-
объекты), невыпуклые многоугольники (Tess-объекты), NURBS-поверхности и
Для работы с Quadric-объектами в библиотеке glu вводится специальный тип
GLUquadricObj. Для работы с Quadric-объектами, сначала надо объявить пере-
менную типа GLUquadricObj. Переменная инициализируется при помощи процеду-
ры gluNewQuadric. При окончании работы с Quadric-объктами, переменную необ-
ходимо удалить при помощи процедуры gluDeleteQuadric. Например:
var
QuadObj: GLUquadricObj;
. . .
begin
. . .
QuadObj:=gluNewQuadric;
. . .
{графические построения}
. . .
gluDeleteQuadric(QuadObj); // Удаление объекта
. . .
end;


Режим воспроизведения объекта задается процедурой:
gluQuadricDrawStyle(QuadObj:GLUquadricObj, mode:cardinal)


Первый аргумент – это имя переменной Quadric-объекта, а параметр mode
может быть GLU_LINE (тогда будет строиться каркасная модель объекта),
GLU_POINT (строятся только точки вершин объекта) или GLU_FILL (тогда грани
объекта будут закрашиваться).
Сфера строится при помощи процедуры:
gluSphere(QuadObj:GLUquadricObj, radius:double, slices:integer,
stacks:integer)


Второй параметр – это радиус сферы, а третий и четвертый параметры – количе-
ство «меридианов» и «параллелей» из которых состоит каркас сферы. Разумеется, чем
больше второй и третий параметры, тем точнее передается сферическая форма объекта.
Цилиндр и конус можно нарисовать процедурой:
GluCylinder(QuadObj:GLUquadricObj, baseRadius:double, topRadius:
double, height:double, slices:integer, stacks:integer)


Аргументы: имя Quadric-объекта, радиусы одного и второго основания ци-
линдра и два числа, задающие частоту каркасной сетки.
И, наконец, - диск:
GluDisk(QuadObj:GLUquadricObj, innerRadius:double, outerRadius:
double, slices:integer, loops:integer)


Аргументы: имя Quadric-объекта, внутренний и внешний радиусы, число сек-
торов и концентрических окружностей из которых состоит каркас диска.
Библиотека glu позволяет выводить объекты не целыми, а частями. Для это-
го существует процедура, задающая плоскость отсечения объекта:
glClipPlane(plane:cardinal,equation:PGLdouble)


Параметр plane – это символическая константа, задающая имя плоскости от-
сечения: GL_CLIP_PLANE0, GL_CLIP_PLANE1 и т.д. Указатель equation адресует
массив, состоящих из четырех элементов – коэффициентов уравнения нормали к
плоскости отсечения. Та часть сцены, куда направлен вектор нормали к плоскости
отсечения, и будет отображаться.
После того как плоскость отсечения задана, само отсечение можно включить
при помощи процедуры glEnable, в качестве параметра следует задать имя плос-
кости отсечения (GL_CLIP_PLANE0, GL_CLIP_PLANE1 и т.д.). Отключение отсече-
ния выполняется процедурой glDisable.
Еще один класс объектов, поддерживаемый библиотекой glu – это NURBS-
поверхности (Non-Uniform Rational B-Spline). NURBS-объекты задаются специаль-
ным типом gluNurbsObj. Как и при работе с Quadric-объектами, NURBS-объект на-
до создавать и удалять:
var
Nurb: gluNurbsObj;
. . .
begin
. . .
Nurb:=gluNewNurbsRenderer;
. . .
{графические построения}
. . .
gluDeleteNurbsRenderer(Nurb); // Удаление объекта
. . .
end;



Существует два режима отображения NURBS-поверхности: закрашенная и
каркасная. Режимы задаются следующим образом:
gluNurbsProperty(Nurb, GLU_DISPLAY_MODE, GLU_FILL)


или
gluNurbsProperty(Nurb, GLU_DISPLAY_MODE, GLU_OUTLINE_POLYGON)


Команды построения заключаются в командные скобки:
gluBeginSurface(Nurb: gluNurbsObj)
gluEndSurface(Nurb: gluNurbsObj)


NURBS-поверхность строится при помощи процедуры
gluNurbsSurface(Nurb: gluNurbsObj,uknot_count:integer,
uknot:PGLFloat,vknot_count:integer,vknot:PGLFloat,
u_stride:integer,v_stride:integer,ctlarray:PGLFloat,
uorder:integer,vorder:integer,type:cardinal)


где Nurb – имя переменной NURBS-объекта, uknot_count, vknot_count – размер-
ность сетки узловых точек поверхности. Поверхность строится на сетке узловых
точек размерностью uknot_count x vknot_count узлов. Указатели *uknot и
*vknot адресуют одномерные массивы нелинейности (линейности) сетки узловых
точек в системе координат u;v. Массивы должны содержать соответственно по
uknot_count и vknot_count элементов, причем значения элементов массива должны
возрастать с ростом индекса массива. Параметры u_stride и v_stride указывают
сколько вещественных чисел содержится в строке структуры данных и сколько
вещественных чисел задают одну опорную точку. Параметр *ctlarray – это указа-
тель на массив опорных точек вида: ctlarray[0..u, 0..v, 0..2], где 0..u и 0..v это коли-
чество узловых точек в столбце и в строке матрицы поверхности соответственно,
а 0..2 место для хранения (x,y,z) координат опорной точки. Параметры uorder и
vorder – это степень сплайновой кривой плюс единица. Для кубических сплайнов
uorder и vorder равны 4. Последний параметр type задает тип возвращаемых зна-
чений. Если type равен GL_MAP2_VERTEX_3, то процедура возвращает координа-
ты точек в трехмерном пространстве. Количество опорных точек в массиве
*ctlarray должно равняться (uknot_count – uorder) x (vknot_count – vorder).
Например, для массивов нелинейности сетки опорных точек вида:
uknot: Array[0..7] of GLFloat = (0.0, 0.0, 0.0, 0.0,
1.0, 1.0, 1.0, 1.0);
vknot: Array[0..7] of GLFloat = (0.0, 0.0, 0.0, 0.0,
1.0, 1.0, 1.0, 1.0);



и массива координат сетки опорных точек вида:
ctlarray: Array [0..3,0..3,0..2] of GLFloat=
(
(//U[1]
(-0.8, 0.8, 0.5), //V[1]
(-0.5, 1, 0.2), //V[2]
(0.5, 1, 0.2), //V[3]
(0.8, 0.8, 0.5)), //V[4]
(//U[2]
(-1, 0.5, 0.5), //V[1]
(-0.5,0.5, -0.2), //V[2]
(0.5, 0.5, -0.2), //V[3]
(1, 0.5, 0.5)), //V[4]
(//U[3]
(-1, -0.5, 0.4), //V[1]
(-0.5,-0.5, -0.2), //V[2]
(0.5, -0.5, -0.2), //V[3]
(1, -0.5, 0.4)), //V[4]
(//U[4]
(-0.8, -0.8, 0.5), //V[1]
(-0.5, -1, 0.2), //V[2]
(0.5, -1, 0.2), //V[3]
(0.8, -0.8, 0.5)) //V[4]
);




Рис. 2. Пример NURBS-поверхности

следующий участок кода процедуры отрисовки строит каркасную модель простей-
шей NURBS-поверхности (рис.2):
. . .
gluNurbsProperty(N,GLU_DISPLAY_MODE,GLU_OUTLINE_POLYGON);
gluBeginSurface(N);
gluNurbsSurface(N, 4*2, @uknot, 4*2, @vknot,
4*3, 3, @ctlarray, 4, 4, GL_MAP2_VERTEX_3);
gluEndSurface(N);
. . .


Библиотека glu позволяет еще и вырезать куски из NURBS-поверхностей.
Внутри операторных скобок:
gluBeginTrim(Nurb:gluNurbsObj)
gluEndTrim(Nurb:gluNurbsObj)


После построения поверхности командой gluNurbsObj, задаем область вырезки:
gluPwlCurve(Nurb:gluNurbsObj, count:integer,
points:PGLFloat, stride:integer, type:cardinal)


Здесь: Nurb – имя поверхности, count – количество точек, которыми задается
замкнутая кусочно-линейная кривая. Та часть NURBS-поверхности, которая попа-
дет внутрь этой кривой, и будет отображаться. Points – указатель на массив точек,
задающих область вырезки. Причем точки следует задавать в координатах
NURBS-поверхности, то есть u, v и w. Параметр stride задает количество действи-
тельных чисел, которое отводится для задания одной точки в массиве, задающем
ограничивающую кривую. И наконец type – это тип возвращаемых значений, он
может принимать значения GLU_MAP1_TRIM_2, когда точки ограничивающей кри-
вой задаются двумя координатами (u и v), или GLU_MAP1_TRIM_3, если точки за-
даются тремя координатами.
Область вырезки можно задать не только в виде кусочно-гладкой кривой, но
и в виде гладкой сплайновой кривой. Так же, внутри операторных скобок вырезки,
используйте команду.
gluNurbsCurve(Nurb:gluNurbsObj, nknots:integer, knot:PGLFloat,
stride:integer, ctlpts:PGLFloat, order:integer, type:cardinal)


Здесь с аргументами попробуйте разобраться сами используя справочную
систему Delphi.
После того как объект сцены создан, его следует разместить на сцене в нуж-
ном месте. Для этого можно использовать процедуры перемещения, вращения и
масштабирования.
glTranslatef(x:single, y:single, z:single)



где x,y,z – смещения по координатным осям.
glRotatef(angle:single, x:single, y:single, z:single)


Для процедуры вращения следует указать угол и координаты вектора нор-
мали к плоскости вращения.
glScalef(x:single, y:single, z:single)


Для масштабирования надо задать масштабы сжатия/растяжения по коор-
динатным осям.
Для того, чтобы преобразования трансформации коснулись только заданно-
го объекта сцены и не повлияли на остальные, требуется заключить участок кода
формирования этого объекта и процедуры его трансформации в стек матриц пре-
образования вида, между командами glPushMatrix() и glPopMatrix().
Например, следующий участок программы рисует цилиндр, повёрнутый на
90 градусов вокруг оси X:
. . .
glPushMatrix();
glRotatef(90, 1, 0, 0);
gluCylinder(QuadObj, 1, 1, 2, 36, 12);
glPopMatrix();
. . .


Чтобы объекты на сцене выглядели более выразительно, включите источник
света с помощью команд:
glEnable(GL_LIGHTING)
glEnable(GL_LIGHT0)




Пример:

procedure TForm1.FormMouseDown(Sender: TObject; Button: TMouseButton;
Shift: TShiftState; X, Y: Integer);
begin
wX:=X;
wY:=Y;
rotate:=true;
end;
procedure TForm1.FormMouseUp(Sender: TObject; Button: TMouseButton;
Shift: TShiftState; X, Y: Integer);
begin
rotate:=false;
end;

procedure TForm1.FormMouseMove(Sender: TObject; Shift: TShiftState;
X,Y: Integer);
begin
if rotate then
begin
rX:=rX+(X-wX)/2;
rY:=rY+(Y-wY)/2;
wX:=X;
wY:=Y;
InvalidateRect(Handle,nil,false);
end;
end;




Кроме того, в обработчик события onPaint (процедуру отрисовки) необходи-
мо добавить команды вращения:
. . .
glRotatef(rX,0,1,0);
glRotatef(rY,1,0,0);
. . .


Переменные wX, wY, rX, rY, rotate – глобальные и имеют тип соответственно
single,single,single,single и boolean.



Исходники:

1.


2.

Опубликовал Kest January 24 2009 23:50:35 · 0 Комментариев · 19293 Прочтений · Для печати

• Не нашли ответ на свой вопрос? Тогда задайте вопрос в комментариях или на форуме! •


Комментарии
Нет комментариев.
Добавить комментарий
Имя:



smiley smiley smiley smiley smiley smiley smiley smiley smiley
Запретить смайлики в комментариях

Введите проверочный код:* =
Рейтинги
Рейтинг доступен только для пользователей.

Пожалуйста, залогиньтесь или зарегистрируйтесь для голосования.

Нет данных для оценки.
Гость
Имя

Пароль



Вы не зарегистрированны?
Нажмите здесь для регистрации.

Забыли пароль?
Запросите новый здесь.
Поделиться ссылкой
Фолловь меня в Твиттере! • Смотрите канал о путешествияхКак приготовить мидии в тайланде?
Загрузки
Новые загрузки
iChat v.7.0 Final...
iComm v.6.1 - выв...
Visual Studio 200...
CodeGear RAD Stud...
Шаблон для новост...

Случайные загрузки
Domen Name IP
PDJ Scrollers
Geo-Whois
RbControls
Векторный редакто...
Алгоритм DES шифр...
ATComponents
Tenis [Исходник н...
Binary2XMLDemo (Р...
Игра змейка
Клавиатурный трен...
Трассировка прово...
BSButton
Программирование ...
Создание отчетов ...
База каталогов ( ...
PDF
Программирование ...
Приемы программир...
GPSS World Studen...

Топ загрузок
Приложение Клие... 100449
Delphi 7 Enterp... 85822
Converter AMR<-... 20067
GPSS World Stud... 12518
Borland C++Buil... 11576
Borland Delphi ... 8504
Turbo Pascal fo... 7023
Visual Studio 2... 4989
Калькулятор [Ис... 4739
FreeSMS v1.3.1 3536
Случайные статьи
Изменение тайтла и...
Видео формат
Structured variabl...
Studio, то объект ...
Алгоритм нахождени...
Протокол РоЕ
Работа в среде Тур...
Процедуры и функции
26 шагов к 15 тыс....
Свойства ARM
Испытание имитацио...
Деструкторы в язы...
Выражение, указыва...
Суммирование маршр...
Расширение сети
Принудительное тун...
Подсчет атомов и ч...
SPLIT (РАСЩЕПИТЬ)
tell(X)
Какие маршруты соз...
Сортировка методом...
Motorola Moto X XT...
Объект Shape, свой...
Специализированные...
Политика безопасно...
Статистика



Друзья сайта
Программы, игры


Полезно
В какую объединенную сеть входит классовая сеть? Суммирование маршрутов Занимают ли таблицы память маршрутизатора?