• Najnowsze pytania
  • Bez odpowiedzi
  • Zadaj pytanie
  • Kategorie
  • Tagi
  • Zdobyte punkty
  • Ekipa ninja
  • IRC
  • FAQ
  • Regulamin
  • Książki warte uwagi

Opengl wirtualny aparat

Object Storage Arubacloud
+1 głos
212 wizyt
pytanie zadane 15 listopada 2021 w C i C++ przez afra Nowicjusz (130 p.)
Cześć!

Mam do napisania program realizujący 'wirtualny aparat'. Wybrałam język c++ i bibliotekę opengl. Projekt powinien realizować rysowanie sceny a następnie dokonywanie przekształceń takich jak obrót, skalowanie, zoom na jej obrazie 2D, tzn jej "zdjęcia". Funkcje przekształceń mają być własne. Mam już właściwie cały kod, ale funkcje przekształceń obracają całą scenę 3D, nie potrafię rozgryźć jak mogę 'zrobić jej zdjęcie' a potem manipulować samym obrazem 2D. Czy jest to możliwe do implementacji? A może powinnam od razu rysować w 2D? Jeśli tak to w jaki sposób mogę podejść do rysowania rzutu sceny 3D?

Z góry dziękuję za odpowiedź

1 odpowiedź

+1 głos
odpowiedź 15 listopada 2021 przez Patrycjerz Mędrzec (192,320 p.)

Cześć,

jeśli dobrze zrozumiałem, chodzi Ci o manipulację gotowym renderem sceny. Przychodzi mi do głowy zmianę celu renderowania (render target) na teksturę i nałożenie jej na model 3D (dwa trójkąty tworzące prostokąt). Później możesz takim prostokątem manipulować tak jak każdym innym modelem, za pomocą transformacji.

Trudno mi pokazać szczegóły implementacyjne, gdyż dawno nie programowałem w OpenGL, ale znalazłem taki kurs: Tutorial 14 : Render To Texture (opengl-tutorial.org).

komentarz 16 grudnia 2021 przez afra Nowicjusz (130 p.)
Hej,

Dziękuję za odpowiedź, długo nie odniosłam się do niej ponieważ musiałam to przetrawić i zająć się innymi przedmiotami na uczelni. Nie wydaje mi się, żeby rendering to było coś co powinnam zastosować, żeby go u siebie wdrożyć musiałabym porządnie przysiąść nad tym zagadnieniem, a celem projektu który robię jest nie nauka języka czy biblioteki tylko wdrożenie matematycznych przekształceń potrzebnych do obrotów, skalowania, rzutowania itd. Tak więc wydaje mi się, że mogłabvm to zrobić łatwiej (pymitywniej (; ) . Oczywiście mogę się mylić bo jestem zielona w temacie. Poniżej wkleję kod jaki udało mi się stworzyć (wszystkie funkcje obrotu, skalowania, translacji i rzutowania miałam napisać samodzielnie). Brakuje mi tylko sposobu jak moją scenę (układ sześcianów) zrzutować na powierznię 2D i potem tą powierzchnią manipulować jak zdjęciem. Nie wiem też co robię nie tak, że początkowo moja scena znajduje się tak daleko od obserwatora. Będę wdzięczna za wgląd w kod i wskazówki co robię źle i w jaki sposób ( o ile w ogóle) mogłabym zaimplementować ten brakujący rzut

 

 

#include <GL\glew.h>
#include <GL\freeglut.h>
#include<math.h>
#include <stdlib.h>

//współrządne bryły obcinania
const GLdouble cutleft = -10.0;
const GLdouble cutright = 10.0;
const GLdouble cuttop = 10.0;
const GLdouble cutbottom = -10.0;
const GLdouble cutnear = 25.0;
const GLdouble cutfar = 5.0;

const GLdouble TR[16] = {
    2 * cutnear / (cutright - cutleft),        0,                                        (cutright + cutleft) / (cutright - cutleft),    0,
    0,                                        2 * cutnear / (cuttop - cutbottom),        (cuttop + cutbottom) / (cuttop - cutbottom),    0,
    0,                                        0,                                        (cutfar+cutnear) / (cutfar-cutnear),            2*cutfar*cutnear/(cutfar-cutnear),
    0,                                        0,                                        -1,                                                0
};

//kąt obrotu sceny wokół osi
GLfloat rotatex = 0.0;
GLfloat rotatey = 0.0;
GLfloat rotatez = 0.0;
//współrzędna przesunięcia sceny wzdłóż osi ox
GLdouble move = 0.0;
//skala prezentacji sceny
GLdouble scale = 1.0;

//funkcja rysująca pojedynczy sześcian
void klocek( int k)
{    

    int i = 0;
    glColor3f(0.0, 1.0, 0.0);

        glBegin(GL_LINES);
        glVertex3i(i, i, i);
        glVertex3i(i, i + k, i);
        glEnd();

        glBegin(GL_LINES);
        glVertex3i(i, i + k, i);
        glVertex3i(i + k, i + k, i);
        glEnd();

        glBegin(GL_LINES);
        glVertex3i(i, i + k, i);
        glVertex3i(i, i + k, i + k);
        glEnd();

        glBegin(GL_LINES);
        glVertex3i(i, i, i);
        glVertex3i(i + k, i, i);
        glEnd();

        glBegin(GL_LINES);
        glVertex3i(i + k, i, i);
        glVertex3i(i + k, i + k, i);
        glEnd();

        glBegin(GL_LINES);
        glVertex3i(i + k, i, i);
        glVertex3i(i + k, i, i + k);
        glEnd();

        glBegin(GL_LINES);
        glVertex3i(i, i, i);
        glVertex3i(i, i, i + k);
        glEnd();

        glBegin(GL_LINES);
        glVertex3i(i, i, i + k);
        glVertex3i(i, i + k, i + k);
        glEnd();

        glBegin(GL_LINES);
        glVertex3i(i, i, i + k);
        glVertex3i(i + k, i, i + k);
        glEnd();

        glBegin(GL_LINES);
        glVertex3i(i + k, i + k, i + k);
        glVertex3i(i + k, i + k, i);
        glEnd();
    
        glBegin(GL_LINES);
        glVertex3i(i + k, i + k, i + k);
        glVertex3i(i, i + k, i + k);
        glEnd();

        glBegin(GL_LINES);
        glVertex3i(i + k, i + k, i + k);
        glVertex3i(i + k, i, i + k);
        glEnd();

}
//rysowanie zespołu brył
void ulica_prymitywow()
{

    glTranslatef(-5, 0, 0);
    klocek(3);
    
    glTranslatef(-1, 0, -4);
    klocek(4);

    glTranslatef(1, 0, -3);
    klocek(3);

    glTranslatef(10, 0, 7.5);
    klocek(2);

    glTranslatef(0, 0, -3);
    klocek(3);

    glTranslatef(0, 0, -4);
    klocek(4);

    
    

}

void move_scene()
{

    //macierz translacji
    GLdouble T[16] = { 1, 0, 0, move,
                       0, 1, 0, 0,
                       0, 0, 1, 0,
                       0, 0, 0, 1 };
    //mnożenie macierzy widoku
    glMultMatrixd(T);
};

void scale_scene()
{
    //macierz skalowania
    GLdouble T[16] = { scale, 0, 0, 0,
                       0, scale, 0, 0,
                       0, 0, scale, 0,
                       0, 0, 0, 1 };
    //mnożenie macierzy widoku
    glMultMatrixd(T);
}
//obrót sceny wokół osi
void rotate_scene()
{
    //obrót sceny wokół osi ox
        double cosinusx = cos(rotatex);
        double sinusx = sin(rotatex);
        GLdouble Tx[16] = { 1,    0,            0,                0,
                           0,    cosinusx,    -sinusx,        0,
                           0,    sinusx,        cosinusx,        0,
                           0,    0,            0,                1 };
        glMultMatrixd(Tx);
    //obrót sceny wokół osi oy
        double cosinusy = cos(rotatey);
        double sinusy = sin(rotatey);
        GLdouble Ty[16] = { cosinusy,        0,        sinusy,            0,
                            0,                1,        0,                0,
                            -sinusy,        0,        cosinusy,        0,
                            0,                0,        0,                1 };
        glMultMatrixd(Ty);
    //obrót sceny wokół osi oz
        double cosinusz = cos(rotatez);
        double sinusz = sin(rotatez);
        GLdouble Tz[16] = { cosinusz,        -sinusz,        0,        0,
                           sinusz,            cosinusz,        0,        0,
                           0,                0,                1,        0,
                           0,                0,                0,        1 };
        glMultMatrixd(Tz);

}

void Display()
{
    glClearColor(0.0, 0.0, 0.0, 1.0);

    glClear(GL_COLOR_BUFFER_BIT);

    glMatrixMode(GL_MODELVIEW);

    glLoadIdentity();

    //pzesunięcie poczatku układu do środka bryły odcinania
    glTranslatef(0, 0, -(cutnear + cutfar) / 2);

    rotate_scene();

    move_scene();
    
    scale_scene();

    ulica_prymitywow();

    
    glFlush();

    glutSwapBuffers();

}

void Reshape(int width, int height)
{
    glViewport(0, 0, width, height);

    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();
    glMultMatrixd(TR);
    Display();
}

void Keyboard(unsigned char key, int x, int y)
{

    if (key == 'n')
        move += 0.01;
    
    else if (key == 'm')
        move -= 0.01;
    
    else if (key == '+')
        scale += 0.01;
    
    else if (key == '-')
        scale -= 0.01;

    // odrysowanie okna
    Reshape(glutGet(GLUT_WINDOW_WIDTH), glutGet(GLUT_WINDOW_HEIGHT));
}

void SpecialKeys(int key, int x, int y)
{
    switch (key)
    {
        
    case GLUT_KEY_LEFT:
        rotatey -= 0.1;
        break;

    case GLUT_KEY_UP:
        rotatex -= 0.1;
        break;

    case GLUT_KEY_RIGHT:
        rotatey += 0.1;
        break;

    case GLUT_KEY_DOWN:
        rotatex += 0.1;
        break;

    case GLUT_KEY_PAGE_UP:
        rotatez += 0.1;
        break;

    case GLUT_KEY_PAGE_DOWN:
        rotatez -= 0.1;
        break;
    }

    // odrysowanie okna
    Reshape(glutGet(GLUT_WINDOW_WIDTH), glutGet(GLUT_WINDOW_HEIGHT));
}

enum
{
    EXIT
};

void Menu(int wartosc)
{
    switch (wartosc)
    {
    case EXIT:
            exit(0);
    }
}

int main(int argc, char * argv[])
{

    glutInit(&argc, argv);
    glutInitDisplayMode(GLUT_DOUBLE | GLUT_RGB);

    glutInitWindowSize(400, 400);

    glutCreateWindow("Ulica prymitywów");

    glutDisplayFunc(Display);

    glutReshapeFunc(Reshape);

    glutSpecialFunc(SpecialKeys);

    glutKeyboardFunc(Keyboard);

    glutCreateMenu(Menu);

    glutAddMenuEntry("Wyjscie", EXIT);

    glutAttachMenu(GLUT_RIGHT_BUTTON);

    glutMainLoop();

    return 0;
};

Podobne pytania

0 głosów
0 odpowiedzi 180 wizyt
pytanie zadane 8 maja 2023 w OpenGL, Unity przez RufinB Obywatel (1,830 p.)
0 głosów
0 odpowiedzi 148 wizyt
pytanie zadane 25 kwietnia 2023 w OpenGL, Unity przez RufinB Obywatel (1,830 p.)
+1 głos
0 odpowiedzi 232 wizyt
pytanie zadane 21 lutego 2023 w OpenGL, Unity przez RufinB Obywatel (1,830 p.)

92,576 zapytań

141,426 odpowiedzi

319,652 komentarzy

61,961 pasjonatów

Motyw:

Akcja Pajacyk

Pajacyk od wielu lat dożywia dzieci. Pomóż klikając w zielony brzuszek na stronie. Dziękujemy! ♡

Oto polecana książka warta uwagi.
Pełną listę książek znajdziesz tutaj.

Akademia Sekuraka

Kolejna edycja największej imprezy hakerskiej w Polsce, czyli Mega Sekurak Hacking Party odbędzie się już 20 maja 2024r. Z tej okazji mamy dla Was kod: pasjamshp - jeżeli wpiszecie go w koszyku, to wówczas otrzymacie 40% zniżki na bilet w wersji standard!

Więcej informacji na temat imprezy znajdziecie tutaj. Dziękujemy ekipie Sekuraka za taką fajną zniżkę dla wszystkich Pasjonatów!

Akademia Sekuraka

Niedawno wystartował dodruk tej świetnej, rozchwytywanej książki (około 940 stron). Mamy dla Was kod: pasja (wpiszcie go w koszyku), dzięki któremu otrzymujemy 10% zniżki - dziękujemy zaprzyjaźnionej ekipie Sekuraka za taki bonus dla Pasjonatów! Książka to pierwszy tom z serii o ITsec, który łagodnie wprowadzi w świat bezpieczeństwa IT każdą osobę - warto, polecamy!

...