Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > Программирование игр, графики и искусственного интеллекта > преобразование фигур


Автор: Reptor 13.11.2007, 19:00
Вопрос состоит в том что есть например набор точек и они соеденены прямыми (пусть это будет 4 точки ну соответственно фигура будет пусть прямоугольник). Эти точки задаються 2 координатами. С помощью каких инструментов можно преобразовать эти точки в 3 мерное представление или что б фигура которая получица была 3-ех мерная (или даже не 3 мерная а как будто лежала на плоскости ну если например смотреть на стол то его столешница как бы так лежит тоесть она не плоская как если на бумажке соденить 4 точки ) ну вот что то такого плана??

Автор: Reptor 14.11.2007, 12:58
Модераторы можно вас попросить что б вы переместили эту тему в раздел Программирование игр, графики и искусственного интеллекта. Мне кажеться этот вопрос туда больше подойдёт. Извеняюсь что сразу как то не сориентировался. 

Автор: Solomon 14.11.2007, 15:20
Ну с прямоугольником можно что то еще предумать, но вот с фигурой хоть немного посложное врятли что то выйдет... Т.е. я думаю можно какойто свой алгоритм сделать, но он будет работать только для конкретного случая, если я ошибась то пускай меня кто нибуть поправит. 

Reptor,  А можеш в общих чертах расказать для чего это требуется? 

Автор: Reptor 14.11.2007, 17:39
Solomon, ну надо сделать прожку в которой задаются точки (2 координаты) потом они соидиняются (ну просто линиями)  и получается обычный наобор точек который соединён линиями на плоскости. Вот а теперь зная точки просто надо что б то что получилось выглядело как 3Д. Вот такая задача

Автор: Solomon 15.11.2007, 15:24
Понял что ничего не понял ))

Цитата(Reptor @  14.11.2007,  16:39 Найти цитируемый пост)
потом они соидиняются (ну просто линиями) 
 т.е. линиями соединяются в той последовательности в который мы их и ввели?
Сомневаюсь что при каких либо расскладах все эт будет выглядеть как 3Д. Я, если чесно, немогу себе это представить.

Автор: Reptor 15.11.2007, 23:14
Solomon, можно сказать что задача стоит таким образом что просто надо сделать 3 мерную фигуру зная  2-ух мерные координаты точек. например как в 3Д studio Max есть вид  с боку и есть 3Д. Ну вот пример в прикрепленом файле. Мне надо получить то что в окне Prespective

Автор: Solomon 16.11.2007, 15:10
Reptor, Это все хорошо конечно... smile
Там нет ничего подобного c тем что пытаешся сделать ты... 
Если делать перевод 3D-2D это просто, а вот наоборот практически не осуществимо, если конечно это не 100% что будет простой прямоугольник.

Автор: Reptor 16.11.2007, 18:41
Solomon, хорошо а как просто нарисовать такую картинку как та что в окне Prespective ?? без преобразования уже 2Д->3Д.

Добавлено через 1 минуту и 28 секунд
Ребята може ещё кто то присоеденится к беседе? может у кого есть какие идеи?

Автор: Solomon 17.11.2007, 16:50
Reptor, Ну можно как это делается в 3Д Максе задаеш последовательно точки, которые имеют 3 координаты и соответственно последовательно соединяеш линиями... 

Хотя стой... что то придумать я думаю можно будет, хотя опять же только для плоских фигур, их можно будет покрутить в 3д простванстве, но это только с плоскими выдет.. тип прямоугольника или ромба, и при этом ему желательно сделать заливку и  если есть возможность то тень... тогда я думаю что то может выйти более мение нормальное.. smile


Автор: Reptor 17.11.2007, 17:53
Цитата

Хотя стой... что то придумать я думаю можно будет, хотя опять же только для плоских фигур, их можно будет покрутить в 3д простванстве, но это только с плоскими выдет.. тип прямоугольника или ромба, и при этом ему желательно сделать заливку и  если есть возможность то тень... 



Solomon, да как раз это и надо что б фигура была плоская и 3Д. Только желательно что б это был многогранник а не только прямоугольник. Вот а всё остальное:
Цитата

 опять же только для плоских фигур, их можно будет покрутить в 3д простванстве

Цитата

 сделать заливку и  если есть возможность то тень... 


это то что надо  smile 

Только вот это хорошо что теоретически это возможно  но я понятия не имею как это реализовать? с помощью каких инструментов??

Добавлено через 1 минуту и 37 секунд
да может есть что почитать на эту тему? и примеры ?

Автор: Solomon 19.11.2007, 16:03
ты это с помощу чего хочеш реализовать? Open, Директ,...?

Автор: Reptor 19.11.2007, 19:22
Solomon, Да вот я даже не знаю а что луче? Ну скорее всего это будет openGL так как я на Java пишу. Да OpenGL.

Автор: DragonFire 20.11.2007, 10:39
Берешь OpenGL иницитализируешь (примеров куча), задаешь режим воспроизведения - перспективный, рисуешь фигуру в трехмерном пространстве но чтобы все координаты z были равны 0. ПОворачиваешь фигуру по всем осям на 45 градусов и получаешь то что тебе нужно... Для наглядности можно будет прикрутить скажем плоскость xy (z=0) и тогда получится как будто твоя линия лежит на поверхности того же стола как ты и хотел. 
Доступно?) Сорь раньше не заглянул в тему...

Добавлено через 4 минуты и 46 секунд
Если надобно могу выделить 15 минут и написать исходники, но учти что я пишу на дельфях... 
Если интересно сразу скажи предпочитаешь ли ты разбираться в коде VCL или чистом API.. Если вообще не изучал OpenGL то сразу во все въехать будет проблематично) 

Автор: Reptor 20.11.2007, 18:58
DragonFire, да огромное спасибо. Выдели плиз 15 мин. Я думаю мне тут всёровно или это VCL или API меня больше Open интересует.  На чём тебе больше нравится давай VCL. Можеш ещё посоветовать литературку и примеры так как я опен совсем не знаю. Вот надо начинать и сразу с такой задачи.

Добавлено через 1 минуту и 21 секунду
DragonFire, оттолкнусь от твоего примера. Разберу что и как буду очень благодарен за помощь. 

Автор: DragonFire 20.11.2007, 22:06
Создай чистый проект переименуй форму в frmGL присвой ей обработчики событий Create, Destroy, Resize, Paint и запускай))) 
Надеюсь это то что тебе нужно... КОмменты почти к каждой строке расставил разберешься... 

Код

unit ULook;

interface

uses
  Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
  OpenGL;

type
  TfrmGL = class(TForm)
    procedure FormCreate(Sender: TObject);
    procedure FormPaint(Sender: TObject);
    procedure FormDestroy(Sender: TObject);
    procedure FormResize(Sender: TObject);

  private
    DC : HDC;
    hrc: HGLRC;
  end;

var
  frmGL: TfrmGL;

implementation

{$R *.DFM}

{=======================================================================
Перерисовка окна}
procedure TfrmGL.FormPaint(Sender: TObject);
begin
 glClear (GL_COLOR_BUFFER_BIT);      //Очистка буфера цвета
 glPushMatrix;                       //Запоминаем матрице
  //Двигаем матрицу
 glTranslatef(0,0,-5);               //Отодвигаем камеру подальше чтобы все было видно
 glROtatef(-45,1,1,1);               //Крутим все на 45 градусов чтобы было трехмерно

 glColor3f (0.55, 0.55, 0.55);       //Текущий цвет примитивов
 glBegin(GL_QUADS);                  //Рисуем плоскость
   glVertex3f(1.0, 1.0, 0);
   glVertex3f(-1.0, 1.0, 0);
   glVertex3f(-1.0, -1.0, 0);
   glVertex3f(1.0, -1.0, 0);
 glEnd;

 glColor3f (0.0, 0.0, 0.0);          //Текущий цвет примитивов
 glBegin (GL_LINE_STRIP);            //Рисуем линии
  glVertex3f(-0.5,-0.5,0);
  glVertex3f(0.5,0.5,0);
  glVertex3f(0.5,-0.6,0);
  glVertex3f(-0.1,-0.65,0);
 glEnd;

 glPopMatrix;                        //Матрице восстанавливаем
 SwapBuffers(DC);                    //Выводим на экран что нарисовали
end;

{=======================================================================
Формат пикселя}
procedure SetDCPixelFormat (hdc : HDC);
var
 pfd : TPixelFormatDescriptor;
 nPixelFormat : Integer;
begin
 FillChar (pfd, SizeOf (pfd), 0);
 pfd.dwFlags  := PFD_DRAW_TO_WINDOW or PFD_SUPPORT_OPENGL or PFD_DOUBLEBUFFER;
 nPixelFormat := ChoosePixelFormat (hdc, @pfd);
 SetPixelFormat (hdc, nPixelFormat, @pfd);
end;

{=======================================================================
Создание формы}
procedure TfrmGL.FormCreate(Sender: TObject);
begin
  //создаем ссылки разные
 DC := GetDC (Handle);
 SetDCPixelFormat (DC);
 hrc := wglCreateContext (DC);
 wglMakeCurrent (DC, hrc);
end;

{=======================================================================
Конец работы приложения}
procedure TfrmGL.FormDestroy(Sender: TObject);
begin
  //чистим ссылки
 wglMakeCurrent(0, 0);
 wglDeleteContext(hrc);
 ReleaseDC (Handle, DC);
 DeleteDC (DC);
end;

{=======================================================================
Изменение отображаемой области}
procedure TfrmGL.FormResize(Sender: TObject);
begin
 glLoadIdentity;                                              //Сбрасываем все настройки режима отображения (сдвиги матрицы вида)
 glViewPort(0,0,ClientWidth,ClientHeight);                    //Тут рисуем
 gluPerspective(50.0, ClientWidth / ClientHeight, 2.0, 10.0); //Включаем перспективу
 InvalidateRect(Handle, nil, False); //Перерипсовка окна
 glClearColor (0.3, 0.3, 0.55, 1.0); //Цвет фона
 glLineWidth(2.5);                   //Ширина линий
 glEnable(GL_LINE_SMOOTH);           //Сгладим линии чтобы было красиво
end;

end.



Добавлено через 2 минуты и 50 секунд
А ну и юнит переименуй с юнита ULook в Unit1

Автор: Reptor 21.11.2007, 11:22
DragonFire,  запустил всё работает. Огромное спасибо да это то что надо  smile . Теперь старт есть буду разбираться как теперь это всё наполнять свойствами ну вроде что б можно было вращать по всем осям ну маштабировать ну что то в таком роде. Что б можно было под 2-им углом смотреть. 

Посоветуй пожалуста ещё литературку хорошую.

Автор: DragonFire 21.11.2007, 14:46
ну по OpenGL много хорошей литературы.. на форуме много вопросов разобрано. Поворот масштабирование - это все достаточно быстро освоишь... 
Я читал вначале Краснова "OpenGL. Графика в проектах Delphi". Вот лови: 
http://pv.bstu.ru/graphics/books/opengl_1.djvu

Автор: Reptor 21.11.2007, 14:58
DragonFire, хорошо спасибо. Буду потихоньку начинать читать и разбираться что и как. 

Автор: Reptor 21.11.2007, 15:37
а можно мне как то поменять систему координат?? что б не было 
 glVertex3f(1.0, 1.0, 0);
 glVertex3f(-1.0, 1.0, 0);

а было как стандартно  
glVertex3f(60, 30, 0);
glVertex3f(80, 90, 0); 

Автор: DragonFire 21.11.2007, 22:06
а что тебе мешает написать 
glVertex3f(1/60, 1/30, 0);
glVertex3f(1/80, 1/90, 0);

Добавлено через 1 минуту и 29 секунд
тогда все будет в пределах от -1 до 1)) 
А если не хочешь так то делай перед риссование уменьшение масштаба
glScalef(0.1,0.1,0.1); (уменьшить в 10 раз нарисованное ниже)

Автор: Reptor 22.11.2007, 18:46
что то я не понимаю почему линия (картинка в атаче) идёт под углом  smile  smile 
Код


 glTranslatef(0,0,-5);               
 glROtatef(0,0,0,0); //-70, 90 , 0, 0             
 glColor3f (0.55, 0.55, 0.55);       
 glScalef(0.1,0.1,0.1);
 glBegin(GL_POLYGON);         

    glVertex3f(10, 10, 0);     // verh pravo

    glVertex3f(-10, 10, 0);   //verh levo
    glVertex3f(-10, 5, 0);
    glVertex3f(-30, 5, 0);
    glVertex3f(-30, -5, 0);
    glVertex3f(-10, -5, 0);
    glVertex3f(-10, -10, 0);       //niz levo

    glVertex3f(10, -10, 0);                    // niz pravo



Автор: DragonFire 23.11.2007, 10:51
Код

 glBegin(GL_QUADS);                
    glVertex3f(10, 10, 0);   
    glVertex3f(-10, 10, 0);  
    glVertex3f(-10, -10, 0);      
    glVertex3f(10, -10, 0);
 glEnd;
 glBegin(GL_QUADS);
    glVertex3f(-30, -5, 0);
    glVertex3f(-10, -5, 0);
     glVertex3f(-10, 5, 0);
    glVertex3f(-30, 5, 0);
 glEnd;

Делай так.. QUADS рисует тока четырехугольники... 

Автор: Reptor 23.11.2007, 16:26
Цитата

QUADS рисует тока четырехугольники... 

DragonFire, да я понял но я ведь пользуюсь (в том коде что привёл выше)  GL_POLYGON вот в чём не ясность почему он рисует линию под углом? 


Автор: DragonFire 23.11.2007, 20:19
разбиратся ща некогда, а GL_POLYGON я вообще не использую... 
Это несколько нестандартный подход, замедляющий работу, лучше все выводи треугольниками... 
Если всеже нужно именно GL_POLYGON, то ночью послезавтра могу покопать и сказать что не так... 

Автор: Reptor 23.11.2007, 20:22
DragonFire, да было б очень здорово. Я что то совсем не могу понять что не так  smile  smile  smile  Вроде обычные точки соединяю по координатам и чё оно его кривит совсем не ясно. И как это треугольниками не совсем понял?

Автор: DragonFire 23.11.2007, 23:24
Ну просто у меня через GL_POLYGON вообще криво отображает все опенжл... Бъет на квадраты по 4 точки... Так что хз...
А стандартный и самый быстрый метод вывода плоскости на экран - это разбить ее на треугольники и выводить по треугольникам.. Но это я так.. прирост скорости заметен тока при большом количестве примитивов... 

Автор: Reptor 24.11.2007, 00:06
DragonFire, ну а всё таки как это треугольниками?

Автор: DragonFire 25.11.2007, 13:45
ну хочешь ты вывести плоскость скажем квадратную - берешь и рисуешь 2 треугольника прямоугольных - вместо одного квадрата... И т.д.

Автор: mes 2.12.2007, 12:49
Цитата(Reptor @  22.11.2007,  18:46 Найти цитируемый пост)
что то я не понимаю почему линия (картинка в атаче) идёт под углом     



Рисунок отображенный в к аттаче ( qqq.rar 5,84 Kb ) не может соответвовать  коду приведенному в посте. smile 


Автор: DragonFire 2.12.2007, 13:53
У мну тож не то совсем отображается, но возможно OpenGL багнутый на компе стоит.... 

Автор: Reptor 9.12.2007, 14:23
mes, да вот в том то и дело что не может. Мне совсем не понятно почему так.  smile   Но что есть то есть просто выполнил код и зделал скриншот резкльтата. 

Автор: Gongex 2.1.2008, 21:20
делал на днях трехмерный куб,вращающийся...Сначала сделал 4 точки,потом соединил линиями,и начал двигать их.Получилась плоскость,а сделать из 4-х точек куб,это так:

если у тебя есть x(1,2,3,4)   и    y(1,2,3,4) и плоскость которая "лежит на столе":

 ddx = qx(2) - qx(3) + qx(3) - qx(1)
 ddy = qy(2) - qy(3) + qy(3) - qy(1)

ddx это ровная "высота"от х1 и х2

линии вниз
Line (x(3) - ddx, y(3) + ddy)-(x(3) , y(3) )
Line (x(1)  - ddx, y(1) + ddy)-(x(1) , y(1) )
Line (x(2) - ddx, y(2)  + ddy)-(x(2) , y(2) )
Line (x(4) - ddx, y(4)  + ddy)-(x(4) , y(4) )

вторая спроецированная плоскость
Line (x(3) - ddx, y(3)  + ddy)-(x(1)  - ddx, y(1) + ddy)
Line (x(1)  - ddx, y(1)  + ddy)-(x(2)  - ddx, y(2)  + ddy)
Line (x(2) - ddx, y(2)  + ddy)-(x(4)  - ddx, y(4) + ddy)
Line (x(4)  - ddx, y(4)  + ddy)-(x(3)  - ddx, y(3) + ddy)

извини это при условии что известны 4 точки,

4 точки расположены так:вверху слева х1 справа х2,внизу слева х3,справа х4

если у тебя прога на vb давай код я спроецирую

Автор: Gongex 2.1.2008, 23:37
вот вычисления чтобы из двух точек получить квадрат:

Код

Private Sub Form_Load()
x(1) = 4000
x(2) = 6000
y(1) = 5000
y(2) = 5000

b(1) = 2
b(5) = 2
b(2) = 1 ' это направление смещения точек
b(6) = 1


от таймера:

Cls

это эффект жвижения квадрата

Код

If b(1) = 1 Then x(1) = x(1) - 65
If b(1) = 2 Then x(1) = x(1) + 65
If x(1) < 4000 Then b(1) = 2
If x(1) > 6000 Then b(1) = 1

If b(2) = 1 Then x(2) = x(2) - 65
If b(2) = 2 Then x(2) = x(2) + 65
If x(2) < 4000 Then b(2) = 2
If x(2) > 6000 Then b(2) = 1

If b(5) = 1 Then y(1) = y(1) - 65
If b(5) = 2 Then y(1) = y(1) + 65
If y(1) < 4000 Then b(5) = 2
If y(1) > 6000 Then b(5) = 1

If b(6) = 1 Then y(2) = y(2) - 65
If b(6) = 2 Then y(2) = y(2) + 65
If y(2) < 4000 Then b(6) = 2
If y(2) > 6000 Then b(6) = 1

получаем остальные две точки:

Line (x(1), y(1))-(x(2), y(2)) это известно

x(3) = x(1) + y(1) - y(2)    игреки к иксу
y(3) = y(1) + x(2) - x(1)  а иксы к игреку

Line (x(1), y(1))-(x(3), y(3))

x(4) = x(2) + y(1) - y(2)
y(4) = y(2) + x(2) - x(1)

Line (x(2), y(2))-(x(4), y(4))


потом эти х1 и х2 крути как хочешь,куб должен быть ровным

Добавлено @ 23:45
Цитата(DragonFire @ 20.11.2007,  22:06)
(1.0, 1.0, 0);
   glVertex3f(-1.0, 1.0, 0);
   glVertex3f(-1.0, -1.0, 0);
   glVertex3f(1.0, -1.0, 0);
 glEnd;

 glColor3f (0.0, 0.0, 0.0);          //Текущий цвет примитивов
 glBegin (GL_LINE_STRIP);            //Рисуем линии
  glVertex3f(-0.5,-0.5,0);
 

у DragonFire такой код длиннющий,уверен все можно сделать 10-ю строками

Gongex, 
M
arilou
используйте тэги форматирования кода

Автор: DragonFire 10.1.2008, 17:37
Gongex, 
Процедуру рисования возможно и можно упросить, только вот код не для оптимизированного движка выкладывался а как наглядный пример, насколько я помню) 

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)