opengl 学习 之 02 lesson

简介

绘制三角形,然后加载shader,改变三角形的颜色

link

http://www.opengl-tutorial.org/uncategorized/2017/06/07/website-update/

GLSL

渲染语言:Shaders are programmed in a language called GLSL

GLSL需要被编译在运行时,意味着每时每刻你加载你的程序,你的shaders会被重新编译。

种类

一种 Vertex Shader,顶点着色器

另一种 Fragment Shader,碎片着色器

code

// Include standard headers
#include <stdio.h>
#include <stdlib.h> // Include GLEW
#include <GL/glew.h> // Include GLFW
#include <GLFW/glfw3.h>
GLFWwindow* window; // Include GLM
#include <glm/glm.hpp>
using namespace glm; #include <common/shader.hpp> int main( void )
{
// Initialise GLFW
if( !glfwInit() )
{
fprintf( stderr, "Failed to initialize GLFW\n" );
getchar();
return -1;
} glfwWindowHint(GLFW_SAMPLES, 4);
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3);
glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE); // To make MacOS happy; should not be needed
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); // Open a window and create its OpenGL context
window = glfwCreateWindow( 1024, 768, "Tutorial 02 - Red triangle", NULL, NULL);
if( window == NULL ){
fprintf( stderr, "Failed to open GLFW window. If you have an Intel GPU, they are not 3.3 compatible. Try the 2.1 version of the tutorials.\n" );
getchar();
glfwTerminate();
return -1;
}
glfwMakeContextCurrent(window); // Initialize GLEW
glewExperimental = true; // Needed for core profile
if (glewInit() != GLEW_OK) {
fprintf(stderr, "Failed to initialize GLEW\n");
getchar();
glfwTerminate();
return -1;
} // Ensure we can capture the escape key being pressed below
glfwSetInputMode(window, GLFW_STICKY_KEYS, GL_TRUE); // Dark blue background
glClearColor(0.0f, 0.0f, 0.4f, 0.0f); GLuint VertexArrayID;
glGenVertexArrays(1, &VertexArrayID);
glBindVertexArray(VertexArrayID); // Create and compile our GLSL program from the shaders
GLuint programID = LoadShaders( "SimpleVertexShader.vertexshader", "SimpleFragmentShader.fragmentshader" ); static const GLfloat g_vertex_buffer_data[] = {
-1.0f, -1.0f, 0.0f,
1.0f, -1.0f, 0.0f,
0.0f, 1.0f, 0.0f,
}; GLuint vertexbuffer;
glGenBuffers(1, &vertexbuffer);
glBindBuffer(GL_ARRAY_BUFFER, vertexbuffer);
glBufferData(GL_ARRAY_BUFFER, sizeof(g_vertex_buffer_data), g_vertex_buffer_data, GL_STATIC_DRAW); do{ // Clear the screen
glClear( GL_COLOR_BUFFER_BIT ); // Use our shader
glUseProgram(programID); // 1rst attribute buffer : vertices
glEnableVertexAttribArray(0);
glBindBuffer(GL_ARRAY_BUFFER, vertexbuffer);
glVertexAttribPointer(
0, // attribute 0. No particular reason for 0, but must match the layout in the shader.
3, // size
GL_FLOAT, // type
GL_FALSE, // normalized?
0, // stride
(void*)0 // array buffer offset
); // Draw the triangle !
glDrawArrays(GL_TRIANGLES, 0, 3); // 3 indices starting at 0 -> 1 triangle glDisableVertexAttribArray(0); // Swap buffers
glfwSwapBuffers(window);
glfwPollEvents(); } // Check if the ESC key was pressed or the window was closed
while( glfwGetKey(window, GLFW_KEY_ESCAPE ) != GLFW_PRESS &&
glfwWindowShouldClose(window) == 0 ); // Cleanup VBO
glDeleteBuffers(1, &vertexbuffer);
glDeleteVertexArrays(1, &VertexArrayID);
glDeleteProgram(programID); // Close OpenGL window and terminate GLFW
glfwTerminate(); return 0;
}
#include <stdio.h>
#include <string>
#include <vector>
#include <iostream>
#include <fstream>
#include <algorithm>
#include <sstream>
using namespace std; #include <stdlib.h>
#include <string.h> #include <GL/glew.h> #include "shader.hpp" GLuint LoadShaders(const char * vertex_file_path,const char * fragment_file_path){ // Create the shaders
GLuint VertexShaderID = glCreateShader(GL_VERTEX_SHADER);
GLuint FragmentShaderID = glCreateShader(GL_FRAGMENT_SHADER); // Read the Vertex Shader code from the file
std::string VertexShaderCode;
std::ifstream VertexShaderStream(vertex_file_path, std::ios::in);
if(VertexShaderStream.is_open()){
std::stringstream sstr;
sstr << VertexShaderStream.rdbuf();
VertexShaderCode = sstr.str();
VertexShaderStream.close();
}else{
printf("Impossible to open %s. Are you in the right directory ? Don't forget to read the FAQ !\n", vertex_file_path);
getchar();
return 0;
} // Read the Fragment Shader code from the file
std::string FragmentShaderCode;
std::ifstream FragmentShaderStream(fragment_file_path, std::ios::in);
if(FragmentShaderStream.is_open()){
std::stringstream sstr;
sstr << FragmentShaderStream.rdbuf();
FragmentShaderCode = sstr.str();
FragmentShaderStream.close();
} GLint Result = GL_FALSE;
int InfoLogLength; // Compile Vertex Shader
printf("Compiling shader : %s\n", vertex_file_path);
char const * VertexSourcePointer = VertexShaderCode.c_str();
glShaderSource(VertexShaderID, 1, &VertexSourcePointer , NULL);
glCompileShader(VertexShaderID); // Check Vertex Shader
glGetShaderiv(VertexShaderID, GL_COMPILE_STATUS, &Result);
glGetShaderiv(VertexShaderID, GL_INFO_LOG_LENGTH, &InfoLogLength);
if ( InfoLogLength > 0 ){
std::vector<char> VertexShaderErrorMessage(InfoLogLength+1);
glGetShaderInfoLog(VertexShaderID, InfoLogLength, NULL, &VertexShaderErrorMessage[0]);
printf("%s\n", &VertexShaderErrorMessage[0]);
} // Compile Fragment Shader
printf("Compiling shader : %s\n", fragment_file_path);
char const * FragmentSourcePointer = FragmentShaderCode.c_str();
glShaderSource(FragmentShaderID, 1, &FragmentSourcePointer , NULL);
glCompileShader(FragmentShaderID); // Check Fragment Shader
glGetShaderiv(FragmentShaderID, GL_COMPILE_STATUS, &Result);
glGetShaderiv(FragmentShaderID, GL_INFO_LOG_LENGTH, &InfoLogLength);
if ( InfoLogLength > 0 ){
std::vector<char> FragmentShaderErrorMessage(InfoLogLength+1);
glGetShaderInfoLog(FragmentShaderID, InfoLogLength, NULL, &FragmentShaderErrorMessage[0]);
printf("%s\n", &FragmentShaderErrorMessage[0]);
} // Link the program
printf("Linking program\n");
GLuint ProgramID = glCreateProgram();
glAttachShader(ProgramID, VertexShaderID);
glAttachShader(ProgramID, FragmentShaderID);
glLinkProgram(ProgramID); // Check the program
glGetProgramiv(ProgramID, GL_LINK_STATUS, &Result);
glGetProgramiv(ProgramID, GL_INFO_LOG_LENGTH, &InfoLogLength);
if ( InfoLogLength > 0 ){
std::vector<char> ProgramErrorMessage(InfoLogLength+1);
glGetProgramInfoLog(ProgramID, InfoLogLength, NULL, &ProgramErrorMessage[0]);
printf("%s\n", &ProgramErrorMessage[0]);
} glDetachShader(ProgramID, VertexShaderID);
glDetachShader(ProgramID, FragmentShaderID); glDeleteShader(VertexShaderID);
glDeleteShader(FragmentShaderID); return ProgramID;
}
#version 330 core

// Input vertex data, different for all executions of this shader.
layout(location = 0) in vec3 vertexPosition_modelspace; void main(){ gl_Position.xyz = vertexPosition_modelspace;
gl_Position.w = 1.0; }
#version 330 core

// Ouput data
out vec3 color; void main()
{ // Output color = red
color = vec3(1,0,0); }

程序说明

程序包含一个 核心程序和解析shader的程序和shader

opengl 学习 02的更多相关文章

  1. OpenGL学习之windows下安装opengl的glut库

    OpenGL学习之windows下安装opengl的glut库 GLUT不是OpenGL所必须的,但它会给我们的学习带来一定的方便,推荐安装.  Windows环境下的GLUT下载地址:(大小约为15 ...

  2. OpenGL学习进程(8)第六课:点、边和图形(三)绘制图形

    本节是OpenGL学习的第六个课时,下面介绍OpenGL图形的相关知识:     (1)多边形的概念: 多边形是由多条线段首尾相连而形成的闭合区域.OpenGL规定,一个多边形必须是一个“凸多边形”. ...

  3. [OpenGL ES 02]OpenGL ES渲染管线与着色器

    [OpenGL ES 02]OpenGL ES渲染管线与着色器 罗朝辉 (http://www.cnblogs.com/kesalin/) 本文遵循"署名-非商业用途-保持一致"创 ...

  4. OpenGL学习笔记3——缓冲区对象

    在GL中特别提出了缓冲区对象这一概念,是针对提高绘图效率的一个手段.由于GL的架构是基于客户——服务器模型建立的,因此默认所有的绘图数据均是存储在本地客户端,通过GL内核渲染处理以后再将数据发往GPU ...

  5. JavaScript学习02 基础语法

    JavaScript学习02 基础语法 JavaScript中很多基础内容和Java中大体上基本一样,所以不需要再单独重复讲了,包括: 各种算术运算符.比较运算符.逻辑运算符: if else语句.s ...

  6. Java虚拟机JVM学习02 类的加载概述

    Java虚拟机JVM学习02 类的加载概述 类的加载 类的加载指的是将类的.class文件中的二进制数据读入到内存中,将其放在运行时数据区的方法区内,然后在堆区创建一个java.lang.Class对 ...

  7. Python学习02 列表 List

    Python学习02 列表 List Python列表 List Python中的列表(List)用逗号分隔,方括号包围(comma-separated values (items) between ...

  8. Android Testing学习02 HelloTesting 项目建立与执行

    Android Testing学习02 HelloTesting 项目建立与执行 Android测试,分为待测试的项目和测试项目,这两个项目会生成两个独立的apk,但是内部,它们会共享同一个进程. 下 ...

  9. OpenGL学习进程(12)第九课:矩阵乘法实现3D变换

    本节是OpenGL学习的第九个课时,下面将详细介绍OpenGL的多种3D变换和如何操作矩阵堆栈.     (1)3D变换: OpenGL中绘制3D世界的空间变换包括:模型变换.视图变换.投影变换和视口 ...

  10. OpenGL学习进程(11)第八课:颜色绘制的详解

        本节是OpenGL学习的第八个课时,下面将详细介绍OpenGL的颜色模式,颜色混合以及抗锯齿.     (1)颜色模式: OpenGL支持两种颜色模式:一种是RGBA,一种是颜色索引模式. R ...

随机推荐

  1. Cursor+playwright+mcp,好玩

    Cursor+playwright+mcp能干嘛,我就不多说,本文只讲怎么用上 第一步,安装下载Cursor.node.js,至于什么python环境,playwright网上一堆教程,自己查 第二步 ...

  2. python,指定目录下创建自定义名称文件夹的方法

    比如,我们需要在D盘TU目录下创建名称为"test"的文件夹 脚本如下: import os path = r'D://tu' a = "test" os.mk ...

  3. 一个基于 C# Unity 开发的金庸群侠传 3D 版,直呼牛逼!

    前言 大家应该都知道 Unity 游戏引擎是基于 C# 编程语言开发的,今天大姚给大家分享一个基于 C# Unity 开发的金庸群侠传 3D 版,该游戏真的是勾起了一代人的慢慢回忆. 项目介绍 JYX ...

  4. 开源的java内网穿透 - 维基代理(wiki-proxy)

    1.简介 维基代理(wiki-proxy).开源的java内网穿透项目. 技术栈:cdkjFramework(维基框架).JPA.Netty 遵循MIT许可,因此您可以对它进行复制.修改.传播并用于任 ...

  5. Web前端入门第 46 问:CSS 中的数学函数不要只会 calc

    数学函数可以用来做什么? 最基础的当然是用来进行四则运算了,再进一步可以用来平方,对数,幂,绝对值,取余等,当然还可以用来计算三角函数. CSS 中的数学函数 灵活运用 CSS 中的数学函数,可以抛弃 ...

  6. 工具使用之“contains包含的使用总结”

    一.集合之间的包含 1.判断listOne是否全部包含listTow中的值 格式:CollectionUtils.containsAll(listOne, listTow) 或 listTow.con ...

  7. 设计模式之“模板方法模式(TemplateMethod)”

    一.使用场景 场景1 当我们要完成在某一细节层次一致的一个过程或一系列步骤,但其个别步骤在更详细的层次上的实现可能不同时,我们通常考虑用模板方法模式来处理 例如:将子类重复声明的方法提到父类去声明,利 ...

  8. .net core workflow流程定义

    .net core workflow流程定义 WikeFlow官网:http://www.wikesoft.com WikeFlow学习版演示地址:http://workflow.wikesoft.c ...

  9. SQL 条件求和

    SUMIF 就是 Excel 中的 sumif () 函数的功能. 工作中用的频率极其高, 像我就几乎天天在用的呢. 也是做个简单的笔记而已. 为啥我总是喜欢对比 Excel 呢, 因为我也渐渐发现, ...

  10. C语言一点五编程实战:纯 C 的模块化×继承×多态框架

    本文将大量涉及C语言高级操作,如函数指针.结构体指针.二级指针.指针频繁引用解引用.typedef.static.inline和C语言项目结构等知识,请确保自己不会被上述知识冲击,如果没有这顾虑,请尽 ...