OpenGL adalah alat pengaturcaraan 3D yang kuat yang digunakan untuk menarik pemandangan tiga dimensi yang kompleks dari primitif sederhana. Artikel ini akan mengajar anda cara melukis kubus ringkas yang boleh anda putar untuk dilihat dalam tiga dimensi!
Untuk projek ini, anda memerlukan editor kod dan beberapa pengetahuan mengenai pengaturcaraan C.
Langkah-langkah
Bahagian 1 dari 3: Persediaan Awal
Langkah 1. Pasang OpenGL Untuk mula ikuti langkah-langkah berikut untuk memasang OpenGL pada sistem anda
Sekiranya anda sudah memasang OpenGL, dan juga penyusun C yang serasi, anda boleh melangkau langkah ini dan pergi ke langkah seterusnya.
Langkah 2. Buat dokumen
Buat fail baru di editor kod kegemaran anda dan simpan sebagai mycube.c
Langkah 3. Tambah #sertakan
Ini adalah asas yang anda perlukan untuk program anda. Penting untuk menyedari bahawa sebenarnya terdapat keperluan yang berbeza untuk sistem operasi yang berbeza. Pastikan untuk memasukkan semua ini untuk memastikan program anda serba boleh dan dapat dijalankan untuk mana-mana pengguna.
// Termasuk #include #include #include #define GL_GLEXT_PROTOTYPES #ifdef _APPLE_ #include #else #include #endif
Langkah 4. Tambahkan prototaip fungsi dan pemboleh ubah global
Langkah anda seterusnya adalah menyatakan beberapa prototaip fungsi.
// Paparan kekosongan Prototaip Fungsi (); batal kekunci khas (); // Pemboleh ubah Global rotate_y = 0; double rotate_x = 0;
Langkah 5. Siapkan fungsi () utama
int main (int argc, char * argv ) {// Memulakan GLUT dan memproses parameter pengguna glutInit (& argc, argv); // Minta tetingkap warna sejati yang disangga dua kali dengan Z-buffer glutInitDisplayMode (GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH);
Langkah 6. Buat tetingkap
Langkah seterusnya adalah buat tetingkap di mana anda akan melukis kubus. Dalam tutorial ini, tetingkap disebut "Awesome Cube".
// Buat tetingkap glutCreateWindow ("Awesome Cube");
Langkah 7. Dayakan ujian kedalaman
OpenGL adalah bahasa yang ketat kerana tidak menganggap ciri khas diaktifkan. Agar program anda dipaparkan dengan betul dalam 3 dimensi menggunakan penyangga Z yang anda lihat sebelumnya, anda perlu membolehkan ujian mendalam. Semasa anda terus meneroka OpenGL, anda akan menemui banyak ciri yang perlu anda aktifkan termasuk pencahayaan, tekstur, menghadap cull dan banyak lagi.
// Dayakan ujian kedalaman Z-buffer glEnable (GL_DEPTH_TEST);
Langkah 8. Tambah fungsi panggilan balik
Berikut adalah fungsi panggilan balik yang anda tuliskan prototaip sebelumnya. Setiap kali melalui gelung utama, fungsi-fungsi ini akan dipanggil. Fungsi paparan melukis semula pemandangan berdasarkan perubahan pada pemboleh ubah yang dibuat sejak panggilan sebelumnya. Fungsi specialKeys membolehkan kita berinteraksi dengan program.
// Fungsi panggil balik glutDisplayFunc (paparan); glutSpecialFunc (specialKeys);
Langkah 9. Mulakan MainLoop
Ini akan mengingatkan fungsi utama sehingga anda menutup program untuk membolehkan animasi dan interaksi pengguna.
// Lulus kawalan ke GLUT untuk acara glutMainLoop (); // Kembali ke OS kembali 0; }
Bahagian 2 dari 3: Fungsi paparan ()
Langkah 1. Fahami tujuan fungsi ini
Semua kerja melukis kubus anda akan dilakukan dalam fungsi ini. Idea umum di belakang kubus anda adalah untuk menarik keenam-enam sisi secara berasingan dan meletakkannya pada kedudukan yang sesuai.
Secara konseptual, setiap sisi akan dilukis dengan menentukan empat sudut dan membiarkan OpenGL menyambungkan garis dan mengisinya dengan warna yang anda tentukan. Berikut adalah langkah-langkah untuk melakukan ini
Langkah 2. Tambah glClear ()
Langkah pertama yang perlu anda lakukan dalam fungsi ini adalah membersihkan warna dan penyangga Z. Tanpa langkah-langkah ini, gambar lama mungkin masih dapat dilihat di bawah gambar baru dan objek yang dilukis tidak akan berada di lokasi yang betul di layar.
paparan kosong () {// Kosongkan skrin dan Z-buffer glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
Langkah 3. Tambahkan glBegin () dan glEnd ()
OpenGL mentakrifkan objek sebagai gabungan pelbagai poligon. Menggunakan glBegin () perintah, anda meletakkan pensil dengan berkesan yang akan membentuk bentuknya. Untuk mengangkat pensil dan memulakan bentuk baru, anda mesti menggunakan glEnd () perintah. Dalam tutorial ini, anda akan menggunakan GL_POLYGON untuk melukis setiap sisi kubus tetapi mungkin menggunakan pilihan parameter lain seperti GL_LINE, GL_QUAD, atau GL_TRIANGLE untuk membuat bentuk lain.
- Di sini anda akan bermula dengan bahagian depan kubus anda. Nanti anda akan menambah warna ke semua 6 sisi.
// Bahagian pelbagai warna - FRONT glBegin (GL_POLYGON); // Vertices akan ditambah pada langkah seterusnya glEnd ();
Langkah 4. Tambah glVertex3f ()
Setelah anda menyatakan bahawa anda ingin memulakan poligon anda, anda perlu tentukan bucu objek. glVertex mempunyai pelbagai bentuk bergantung pada apa yang anda mahu lakukan dengan objek anda.
- Yang pertama ialah berapa banyak dimensi yang anda kerjakan. 3 di atas di glVertex3f mengatakan bahawa anda melukis dalam 3 dimensi. Anda juga boleh bekerja dalam 2 atau 4 dimensi. F di atas di glVertex3f mengatakan bahawa anda bekerja dengan nombor titik terapung. Anda juga boleh menggunakan seluar pendek, bilangan bulat atau ganda.
- Perhatikan bahawa titik-titik ini ditakrifkan dalam a lawan arah jam cara. Ini tidak begitu penting pada masa ini tetapi ketika anda mulai bekerja dengan pencahayaan, tekstur, dan menghadap ke arah celah, ini akan menjadi sangat penting sehingga terbiasa menentukan poin anda berlawanan arah jarum jam sekarang.
- Tambah tambah bucu antara garis glBegin () dan glEnd ().
// Bahagian pelbagai warna - FRONT glBegin (GL_POLYGON); glVertex3f (-0.5, -0.5, -0.5); // P1 glVertex3f (-0.5, 0.5, -0.5); // P2 glVertex3f (0.5, 0.5, -0.5); // P3 glVertex3f (0.5, -0.5, -0.5); // P4 glEnd ();
Langkah 5. Tambahkan glColor3f ()
glColor berfungsi dengan cara yang serupa dengan glVertex. Anda boleh menentukan titik sebagai seluar pendek, bilangan bulat, ganda, atau terapung. Setiap warna mempunyai nilai dari 0 hingga 1. Semua 0 menjadikan titik menjadi hitam dan semua 1 akan menjadikan titik menjadi putih. 3 in glColor3f () merujuk kepada sistem warna RGB tanpa saluran alpha. Alfa warna menentukan ketelusannya. Untuk menukar tahap alpha, gunakan glColor4f () dengan parameter terakhir menjadi nilai 0 hingga 1 untuk legap hingga lutsinar.
- Apabila anda memanggil glColor3f () setiap bucu yang diambil dari titik itu akan berwarna. Oleh itu, jika anda mahu keempat-empat bucu berwarna merah, tetapkan warnanya sekali bila-bila masa sebelum perintah glVertex3f () dan semua bucu akan berwarna merah.
- Bahagian depan yang ditentukan di bawah menunjukkan cara menentukan warna baru untuk setiap bucu. Apabila anda melakukan ini, anda dapat melihat sifat menarik warna OpenGL. Oleh kerana setiap titik poligon mempunyai warnanya sendiri, OpenGL akan menggabungkan warna secara automatik! Langkah seterusnya akan menunjukkan cara menetapkan empat bucu dengan warna yang sama.
// Bahagian pelbagai warna - FRONT glBegin (GL_POLYGON); glColor3f (1.0, 0.0, 0.0); glVertex3f (0.5, -0.5, -0.5); // P1 berwarna merah glukol3f (0.0, 1.0, 0.0); glVertex3f (0.5, 0.5, -0.5); // P2 berwarna hijau gl3 (0,0, 0,0, 1,0); glVertex3f (-0.5, 0.5, -0.5); // P3 berwarna biru glColor3f (1.0, 0.0, 1.0); glVertex3f (-0.5, -0.5, -0.5); // P4 berwarna ungu glEnd ();
Langkah 6. Kendalikan sisi lain
Tentukan lokasi setiap bucu bagi lima sisi kubus yang lain tetapi untuk kesederhanaan, ini telah dikira untuk anda dan termasuk dalam fungsi paparan akhir () di bawah.
// Bahagian putih - KEMBALI glBegin (GL_POLYGON); glColor3f (1.0, 1.0, 1.0); glVertex3f (0.5, -0.5, 0.5); glVertex3f (0.5, 0.5, 0.5); glVertex3f (-0.5, 0.5, 0.5); glVertex3f (-0.5, -0.5, 0.5); glEnd (); // Bahagian ungu - KANAN glBegin (GL_POLYGON); glColor3f (1.0, 0.0, 1.0); glVertex3f (0.5, -0.5, -0.5); glVertex3f (0.5, 0.5, -0.5); glVertex3f (0.5, 0.5, 0.5); glVertex3f (0.5, -0.5, 0.5); glEnd (); // Bahagian hijau - KIRI glBegin (GL_POLYGON); glColor3f (0.0, 1.0, 0.0); glVertex3f (-0.5, -0.5, 0.5); glVertex3f (-0.5, 0.5, 0.5); glVertex3f (-0.5, 0.5, -0.5); glVertex3f (-0.5, -0.5, -0.5); glEnd (); // Bahagian biru - TOP glBegin (GL_POLYGON); glColor3f (0.0, 0.0, 1.0); glVertex3f (0.5, 0.5, 0.5); glVertex3f (0.5, 0.5, -0.5); glVertex3f (-0.5, 0.5, -0.5); glVertex3f (-0.5, 0.5, 0.5); glEnd (); // Bahagian merah - BOTTOM glBegin (GL_POLYGON); glColor3f (1.0, 0.0, 0.0); glVertex3f (0.5, -0.5, -0.5); glVertex3f (0.5, -0.5, 0.5); glVertex3f (-0.5, -0.5, 0.5); glVertex3f (-0.5, -0.5, -0.5); glEnd (); glFlush (); glutSwapBuffers (); }
Kami juga ingin menambah dua baris terakhir kod untuk fungsi ini. Ini adalah glFlush ();
dan glutSwapBuffers ();
yang memberi kita kesan penyangga berganda yang anda pelajari sebelumnya.
Bahagian 3 dari 3: Interaktiviti Pengguna
Langkah 1. Tambah kunci khas ()
Anda hampir selesai tetapi pada masa ini, anda boleh melukis kubus tetapi tidak boleh memutarnya. Untuk melakukan ini, anda akan melakukannya buat kunci khas () berfungsi untuk membolehkan kita menekan kekunci anak panah dan memutar kubus!
- Fungsi ini adalah mengapa anda menyatakan pemboleh ubah global rotate_x dan rotate_y. Apabila anda menekan kekunci anak panah kanan dan kiri, rotate_y akan meningkat atau dikurangkan sebanyak 5 darjah. Begitu juga, apabila anda menekan kekunci anak panah atas dan bawah, rotate_x akan berubah dengan sewajarnya.
batal kekunci khas (kunci int, int x, int y) {// Anak panah kanan - tingkatkan putaran sebanyak 5 darjah jika (kunci == GLUT_KEY_RIGHT) putar_y + = 5; // Anak panah kiri - kurangkan putaran sebanyak 5 darjah yang lain jika (kunci == GLUT_KEY_LEFT) putar_y - = 5; lain jika (kunci == GLUT_KEY_UP) rotate_x + = 5; lain jika (kunci == GLUT_KEY_DOWN) putar_x - = 5; // Minta kemas kini paparan glutPostRedisplay (); }
Langkah 2. Tambah glRotate ()
Pernyataan terakhir anda adalah menambahkan pernyataan yang akan memutarkan objek anda. Kembali ke fungsi display () dan sebelum bahagian FRONT, tambahkan baris berikut:
// Tetapkan semula transformasi glLoadIdentity (); // Putar apabila pengguna menukar rotate_x dan rotate_y glRotatef (rotate_x, 1.0, 0.0, 0.0); glRotatef (rotate_y, 0.0, 1.0, 0.0); // Bahagian pelbagai warna - DEPAN….
Langkah 3. Tambahkan perintah berikut untuk skala kubus sebanyak 2 di sepanjang paksi-x, 2 di sepanjang paksi-y, putar kubus sebanyak 180 darjah mengenai paksi-y, dan terjemahkan kiub sebanyak 0.1 di sepanjang paksi-x
Pastikan untuk mengatur ini dan juga perintah glRotate () sebelumnya dalam urutan yang betul seperti yang dijelaskan di atas. (Sekiranya anda tidak pasti, ini dilakukan dalam kod akhir pada akhir tutorial.)
// Transformasi lain glTranslatef (0.1, 0.0, 0.0); glRotatef (180, 0.0, 1.0, 0.0); glScalef (2.0, 2.0, 0.0);
Langkah 4. Susun dan jalankan kod anda
Dengan andaian anda menggunakan gcc sebagai penyusun anda, jalankan perintah ini dari terminal anda untuk menyusun dan menguji program anda.
Di Linux: gcc cube.c -o cube -lglut -lGL./ mycube On Mac: gcc -o foo foo.c -framework GLUT -framework OpenGL./ mycube Pada Windows: gcc -Wall -ofoo foo.c -lglut32cu - lglu32 -lopengl32./ mycube
Langkah 5. Periksa kod lengkap anda
Sepatutnya seperti ini:
// // Fail: mycube.c // Pengarang: Matt Daisley // Dicipta: 4/25/2012 // Projek: Kod sumber untuk Membuat Cube dalam OpenGL // Penerangan: Membuat tetingkap OpenGL dan melukis kubus 3D / / Bahawa pengguna dapat memutar menggunakan kekunci anak panah // // Kawalan: Panah Kiri - Putar Kiri // Panah Kanan - Putar Kanan // Panah Atas - Putar Atas // Anak Panah Bawah - Putar ke Bawah // ------ -------------------------------------------------- - // Termasuk // ------------------------------------------- --------------- #include #include #include #define GL_GLEXT_PROTOTYPES #ifdef _APPLE_ #include #else #include #endif // ------------- --------------------------------------------- // Prototaip Fungsi / / ------------------------------------------------- --------- paparan kosong (); batal kekunci khas (); // ------------------------------------------------ ---------- // Pemboleh ubah Global // ---------------------------------- ------------------------ double rotate_y = 0; double rotate_x = 0; // ------------------------------------------------ ---------- // paparan () Fungsi panggil balik // ------------------------------- --------------------------- paparan kosong () {// Kosongkan skrin dan Z-buffer glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); // Tetapkan semula transformasi glLoadIdentity (); // Transformasi Lain // glTranslatef (0.1, 0.0, 0.0); // Tidak termasuk // glRotatef (180, 0.0, 1.0, 0.0); // Tidak termasuk // Putar apabila pengguna menukar rotate_x dan rotate_y glRotatef (rotate_x, 1.0, 0.0, 0.0); glRotatef (rotate_y, 0.0, 1.0, 0.0); // Transformasi Lain // glScalef (2.0, 2.0, 0.0); // Tidak termasuk // Bahagian pelbagai warna - FRONT glBegin (GL_POLYGON); glColor3f (1.0, 0.0, 0.0); glVertex3f (0.5, -0.5, -0.5); // P1 berwarna merah glukol3f (0.0, 1.0, 0.0); glVertex3f (0.5, 0.5, -0.5); // P2 berwarna hijau gl3 (0,0, 0,0, 1,0); glVertex3f (-0.5, 0.5, -0.5); // P3 berwarna biru glColor3f (1.0, 0.0, 1.0); glVertex3f (-0.5, -0.5, -0.5); // P4 berwarna ungu glEnd (); // Bahagian putih - KEMBALI glBegin (GL_POLYGON); glColor3f (1.0, 1.0, 1.0); glVertex3f (0.5, -0.5, 0.5); glVertex3f (0.5, 0.5, 0.5); glVertex3f (-0.5, 0.5, 0.5); glVertex3f (-0.5, -0.5, 0.5); glEnd (); // Bahagian ungu - KANAN glBegin (GL_POLYGON); glColor3f (1.0, 0.0, 1.0); glVertex3f (0.5, -0.5, -0.5); glVertex3f (0.5, 0.5, -0.5); glVertex3f (0.5, 0.5, 0.5); glVertex3f (0.5, -0.5, 0.5); glEnd (); // Bahagian hijau - KIRI glBegin (GL_POLYGON); glColor3f (0.0, 1.0, 0.0); glVertex3f (-0.5, -0.5, 0.5); glVertex3f (-0.5, 0.5, 0.5); glVertex3f (-0.5, 0.5, -0.5); glVertex3f (-0.5, -0.5, -0.5); glEnd (); // Bahagian biru - TOP glBegin (GL_POLYGON); glColor3f (0.0, 0.0, 1.0); glVertex3f (0.5, 0.5, 0.5); glVertex3f (0.5, 0.5, -0.5); glVertex3f (-0.5, 0.5, -0.5); glVertex3f (-0.5, 0.5, 0.5); glEnd (); // Bahagian merah - BOTTOM glBegin (GL_POLYGON); glColor3f (1.0, 0.0, 0.0); glVertex3f (0.5, -0.5, -0.5); glVertex3f (0.5, -0.5, 0.5); glVertex3f (-0.5, -0.5, 0.5); glVertex3f (-0.5, -0.5, -0.5); glEnd (); glFlush (); glutSwapBuffers (); } // ----------------------------------------------- ----------- // specialKeys () Fungsi Panggilan Balik // ------------------------------ ---------------------------- batal kekunci khas (kunci int, int x, int y) {// Anak panah kanan - tingkatkan putaran sebanyak 5 darjah jika (kunci == GLUT_KEY_RIGHT) putar_y + = 5; // Anak panah kiri - kurangkan putaran sebanyak 5 darjah yang lain jika (kunci == GLUT_KEY_LEFT) putar_y - = 5; lain jika (kunci == GLUT_KEY_UP) rotate_x + = 5; lain jika (kunci == GLUT_KEY_DOWN) putar_x - = 5; // Minta kemas kini paparan glutPostRedisplay (); } // ----------------------------------------------- ----------- // fungsi utama // ------------------------------- --------------------------- int main (int argc, char * argv ) {// Memulakan GLUT dan memproses parameter pengguna glutInit (& argc, argv); // Minta tetingkap warna sejati yang disangga dua kali dengan Z-buffer glutInitDisplayMode (GLUT_DOUBLE | GLUT_RGB | GLUT_DEPTH); // Buat tetingkap glutCreateWindow ("Awesome Cube"); // Dayakan ujian kedalaman Z-buffer glEnable (GL_DEPTH_TEST); // Fungsi panggil balik glutDisplayFunc (paparan); glutSpecialFunc (specialKeys); // Lulus kawalan ke GLUT untuk acara glutMainLoop (); // Kembali ke OS kembali 0; }