Untitled
unknown
plain_text
a year ago
8.3 kB
4
Indexable
---- basic.frag
#version 330 core
in vec3 chCol;
out vec4 outCol;
void main()
{
outCol = vec4(chCol, 1.0);
}
---- basic.vert
#version 330 core
layout(location = 0) in vec2 inPos;
layout(location = 1) in vec3 inCol;
out vec3 chCol;
void main()
{
chCol = inCol;
gl_Position = vec4(inPos.x, inPos.y, 0.0, 1.0);
}
---- main.cpp
// Autor: Nedeljko Tesanovic
// Opis: Zestoko iskomentarisan program koji crta sareni trougao u OpenGL-u
#define _CRT_SECURE_NO_WARNINGS
//Biblioteke za stvari iz C++-a (unos, ispis, fajlovi, itd - potrebne za kompajler sejdera)
#include <iostream>
#include <fstream>
#include <sstream>
//Biblioteke OpenGL-a
#include <GL/glew.h> //Omogucava laksu upotrebu OpenGL naredbi
#include <GLFW/glfw3.h>//Olaksava pravljenje i otvaranje prozora (konteksta) sa OpenGL sadrzajem
unsigned int compileShader(GLenum type, const char* source); //Uzima kod u fajlu na putanji "source", kompajlira ga i vraca sejder tipa "type"
unsigned int createShader(const char* vsSource, const char* fsSource); //Pravi objedinjeni sejder program koji se sastoji od Verteks sejdera ciji je kod na putanji vsSource i Fragment sejdera na putanji fsSource
int main(void)
{
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++ INICIJALIZACIJA ++++++++++++++++++++++++++++++++++++++++++++++++++++++
// Pokretanje GLFW biblioteke
// Nju koristimo za stvaranje okvira prozora
if (!glfwInit()) // !0 == 1; glfwInit inicijalizuje GLFW i vrati 1 ako je inicijalizovana uspjesno, a 0 ako nije
{
std::cout<<"GLFW Biblioteka se nije ucitala! :(\n";
return 1;
}
//Odredjivanje OpenGL verzije i profila (3.3, programabilni pajplajn)
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3);
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
//Stvaranje prozora
GLFWwindow* window; //Mjesto u memoriji za prozor
unsigned int wWidth = 500;
unsigned int wHeight = 500;
const char wTitle[] = "[Generic Title]";
window = glfwCreateWindow(wWidth, wHeight, wTitle, NULL, NULL); // Napravi novi prozor
// glfwCreateWindow( sirina, visina, naslov, monitor na koji ovaj prozor ide preko citavog ekrana (u tom slucaju umjesto NULL ide glfwGetPrimaryMonitor() ), i prozori sa kojima ce dijeliti resurse )
if (window == NULL) //Ako prozor nije napravljen
{
std::cout << "Prozor nije napravljen! :(\n";
glfwTerminate(); //Gasi GLFW
return 2; //Vrati kod za gresku
}
// Postavljanje novopecenog prozora kao aktivni (sa kojim cemo da radimo)
glfwMakeContextCurrent(window);
// Inicijalizacija GLEW biblioteke
if (glewInit() != GLEW_OK) //Slicno kao glfwInit. GLEW_OK je predefinisani izlazni kod za uspjesnu inicijalizaciju sadrzan unutar biblioteke
{
std::cout << "GLEW nije mogao da se ucita! :'(\n";
return 3;
}
float vertices[]{
// poz // boja
-0.25, 0.0, 1.0, 0.0, 0.0,
0.25, 0.0, 0.0, 1.0, 0.0,
0.0, 0.5, 0.0, 0.0, 1.0,
};
unsigned int VAO;
glGenVertexArrays(1, &VAO);
glBindVertexArray(VAO);
unsigned int VBO;
glGenBuffers(1, &VBO);
glBindBuffer(GL_ARRAY_BUFFER,VBO);
glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);
glVertexAttribPointer(0, 2, GL_FLOAT, GL_FALSE, (2 + 3) * sizeof(float), (void*)0);
glEnableVertexAttribArray(0);
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, (2 + 3) * sizeof(float), (void*)(2 * sizeof(float)));
glEnableVertexAttribArray(1);
glBindVertexArray(0);
unsigned int shaderProgram = createShader("basic.vert", "basic.frag");
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++ RENDER LOOP - PETLJA ZA CRTANJE +++++++++++++++++++++++++++++++++++++++++++++++++
glClearColor(0.5, 0.5, 0.5, 1.0); //Podesavanje boje pozadine: RGBA (R - Crvena, G - Zelena, B - Plava, A = neprovidno; Opseg od 0 do 1, gdje je 0 crno a 1 svijetlo)
while (!glfwWindowShouldClose(window)) //Beskonacna petlja iz koje izlazimo tek kada prozor treba da se zatvori
{
//Unos od korisnika bez callback funckcije. GLFW_PRESS = Dugme je trenutno pritisnuto. GLFW_RELEASE = Dugme trenutno nije pritisnuto
if (glfwGetKey(window, GLFW_KEY_ESCAPE) == GLFW_PRESS)
{
glfwSetWindowShouldClose(window, GL_TRUE);
}
//Brisanje ekrana
glClear(GL_COLOR_BUFFER_BIT);
glBindVertexArray(VAO);
glDrawArrays(GL_TRIANGLES, 0, 3);
glBindVertexArray(0);
glUseProgram(shaderProgram);
//Zamjena vidljivog bafera sa pozadinskim
glfwSwapBuffers(window);
//Hvatanje dogadjaja koji se ticu okvira prozora (promjena velicine, pomjeranje itd)
glfwPollEvents();
}
// ++++++++++++++++++++++++++++++++++++++++++++++++++++++ POSPREMANJE +++++++++++++++++++++++++++++++++++++++++++++++++
//Sve OK - batali program
glDeleteVertexArrays(1, &VAO);
glDeleteBuffers(GL_ARRAY_BUFFER, &VBO);
glfwTerminate();
return 0;
}
unsigned int compileShader(GLenum type, const char* source)
{
//Uzima kod u fajlu na putanji "source", kompajlira ga i vraca sejder tipa "type"
//Citanje izvornog koda iz fajla
std::string content = "";
std::ifstream file(source);
std::stringstream ss;
if (file.is_open())
{
ss << file.rdbuf();
file.close();
std::cout << "Uspjesno procitao fajl sa putanje \"" << source << "\"!" << std::endl;
}
else {
ss << "";
std::cout << "Greska pri citanju fajla sa putanje \"" << source << "\"!" << std::endl;
}
std::string temp = ss.str();
const char* sourceCode = temp.c_str(); //Izvorni kod sejdera koji citamo iz fajla na putanji "source"
int shader = glCreateShader(type); //Napravimo prazan sejder odredjenog tipa (vertex ili fragment)
int success; //Da li je kompajliranje bilo uspjesno (1 - da)
char infoLog[512]; //Poruka o gresci (Objasnjava sta je puklo unutar sejdera)
glShaderSource(shader, 1, &sourceCode, NULL); //Postavi izvorni kod sejdera
glCompileShader(shader); //Kompajliraj sejder
glGetShaderiv(shader, GL_COMPILE_STATUS, &success); //Provjeri da li je sejder uspjesno kompajliran
if (success == GL_FALSE)
{
glGetShaderInfoLog(shader, 512, NULL, infoLog); //Pribavi poruku o gresci
if (type == GL_VERTEX_SHADER)
printf("VERTEX");
else if (type == GL_FRAGMENT_SHADER)
printf("FRAGMENT");
printf(" sejder ima gresku! Greska: \n");
printf(infoLog);
}
return shader;
}
unsigned int createShader(const char* vsSource, const char* fsSource)
{
//Pravi objedinjeni sejder program koji se sastoji od Vertex sejdera ciji je kod na putanji vsSource
unsigned int program; //Objedinjeni sejder
unsigned int vertexShader; //Verteks sejder (za prostorne podatke)
unsigned int fragmentShader; //Fragment sejder (za boje, teksture itd)
program = glCreateProgram(); //Napravi prazan objedinjeni sejder program
vertexShader = compileShader(GL_VERTEX_SHADER, vsSource); //Napravi i kompajliraj vertex sejder
fragmentShader = compileShader(GL_FRAGMENT_SHADER, fsSource); //Napravi i kompajliraj fragment sejder
//Zakaci verteks i fragment sejdere za objedinjeni program
glAttachShader(program, vertexShader);
glAttachShader(program, fragmentShader);
glLinkProgram(program); //Povezi ih u jedan objedinjeni sejder program
glValidateProgram(program); //Izvrsi provjeru novopecenog programa
int success;
char infoLog[512];
glGetProgramiv(program, GL_VALIDATE_STATUS, &success); //Slicno kao za sejdere
if (success == GL_FALSE)
{
glGetShaderInfoLog(program, 512, NULL, infoLog);
std::cout << "Objedinjeni sejder ima gresku! Greska: \n";
std::cout << infoLog << std::endl;
}
//Posto su kodovi sejdera u objedinjenom sejderu, oni pojedinacni programi nam ne trebaju, pa ih brisemo zarad ustede na memoriji
glDetachShader(program, vertexShader);
glDeleteShader(vertexShader);
glDetachShader(program, fragmentShader);
glDeleteShader(fragmentShader);
return program;
}
Editor is loading...
Leave a Comment