从这里就接触到了可编程图形渲染管线. 下面介绍使用Vertex Shader (顶点着色器)和 Fragment Shader(像素着色器)的方法. 我们的目标是使用这两个着色器给三角形填充绿色. 添加了一个cpp文件存放Shader文件,MyShaderCode.cpp: 1 const char* vertexShaderCode = 2 " #version 430 \r\n" 3 " \r\n" 4 " in layout(location=0)…
大部分OpenGL教程都会在一开始就讲解VAO,但是该教程的作者认为这是很不合理的,因为要理解它的作用需要建立在我们此前学过的知识基础上.因此直到教程已经进行了一大半,作者才引入VAO这个概念.在我看来这也是非常合理和自然的. 先预览一下最终的代码逻辑: 准备工作 为了讲解后面的内容,我们对代码进行了更改(算是回退吧,改回到以前不使用Instancing的版本): 去掉了sendDataToOpenGL()函数中关于实例化的部分代码 把VertexShader中的MVP矩阵改回Uniform 在…
上节的最后我们实现了两个绿色的三角形,而绿色是直接在Fragment Shader中指定的. 这节我们将为这两个三角形进行更加自由的着色——五个顶点各自使用不同的颜色. 要实现这个目的,我们分两步进行,首先 在顶点数组里增加数据用来表示颜色 修改sendDataToOpenGL()函数中的verts数组: GLfloat verts[] = { +0.0f, +0.0f, //Vertex 0 +1.0, +0.0, +0.0f, //Color 0 +1.0f, +1.0f, //Vertex…
启用Depth Test OpenGL是个3D绘图API,也就是说不只有xy坐标轴,还有第三个坐标轴z,z轴的方向是垂直于屏幕,指向屏幕内. 靠近人眼的方向是负方向,标准化设备坐标的最小值是-1, 最大正值是1. 在未启用深度测试的情况下,同一个像素如果被绘制两次,后绘制的像素会覆盖先绘制的像素. 如果启用了深度测试,情况则完全不同了.后绘制的像素会对深度做一次比较,如果后绘制的像素深度(z)小于之前的像素深度,则会覆盖,如果大于或者等于之前的像素深度,则不会覆盖. Depth需要在绘制之前启用…
我们使用15节学到的知识来绘制14节的立方体. 在第14节我们使用了两次glDrawElements实现了OpenGL实例化,发现这样仍然不太方便,如果需要绘制成千上万的立方体,就需要手写成千上万次的glDrawElements(). 而15节我们知道了glDrawElementsInstanced函数可以支持批量绘制. 我们需要绘制的多个立方体唯一不同的只是转换矩阵,为了达到这个目的,我们只需要定义一组不同的变换矩阵,采用glDrawElementsInstanced即可达到目的. 构建矩阵的…
本节我们将绘制一个3维物体,立方体. 如果要渲染3D物体,我们需要了解MVP(Model View Projection),它表示三个转换矩阵.实际上这个名字不够明确,更加确切的释义如下: Model - Model to World  模型空间到世界空间 View - World to View      世界空间到视图空间 Projection - View to Projection   视图空间到投影空间 要实现这三个转换矩阵,我们需要借助glm数学库提供的一些方便的结构体和函数. 重构…
本节我们将尝试利用三角形制作一个“走马灯”效果. 一个三角形如图示方式,从左向右依次移动. 先看一下代码: MyGlWindow.cpp #include <gl\glew.h> #include "MyGlWindow.h" #include <iostream> #include <fstream> float triangleWidth = 0.1f; ; ; ; void MyGlWindow::sendDataToOpenGL() { //…
在上一节的案例中,我们使用了四个Buffer Object,立方体的VertexBuffer,立方体的索引Buffer,四面体的VertexBuffer,四面体的索引Buffer. 我们这节尝试把两个图形的Vertex Buffer结合,两个图形的索引Buffer结合,形成两个Buffer,让程序更加简化. 先看最终代码: MyGlWindow.cpp: #include <gl\glew.h> #include "MyGlWindow.h" #include <io…
友情提示:继续本节之前,需要保存此前的代码,本节为了试验,会对代码做一些修改,但后续的修改需要我们把代码返回之前的进度. OpenGL内置支持Instancing,有专门的函数来处理这件事情. 为了方便,我们先使用最简单的三角形来学习 先修改sendDataToOpenGL()函数: void MyGlWindow::sendDataToOpenGL() { GLfloat tri[] = { -1.0f,+0.0f, -1.0f,+1.0f, -0.9f,+0.0f }; GLuint ver…
如果我们需要绘制两个(或者多个)一样的立方体(或者物体),只是位置.缩放.旋转不一样,那么我们可以不需要多次将这个物体的顶点信息.颜色信息等发送到显卡,而是发送一次,绘制多次,仅仅是每次绘制之前应用不同的转换矩阵.这种方法叫做OpenGL Instancing.它的效率比每次都重新发送一次数据到显卡要高很多. 看具体代码: void MyGlWindow::paintGL() { glClear(GL_DEPTH_BUFFER_BIT | GL_COLOR_BUFFER_BIT); glView…
本节将采用两种方法绘制两个三角形. 先看第一种方法的代码 MyGlWindow.cpp #include <gl\glew.h> #include "MyGlWindow.h" void MyGlWindow::initializeGL() { glewInit(); GLfloat verts[] = { +0.0f, +0.0f, +1.0f, +1.0f, -1.0f, +1.0f, +0.0f, +0.0f, -1.0f, -1.0f, +1.0f, -1.0f,…
本节将绘制一个三角形 先看最终代码: MyGlWindow.cpp: #include <gl\glew.h> #include "MyGlWindow.h" void MyGlWindow::initializeGL() { glewInit(); GLfloat verts[]= { +0.0f, +1.0f, -1.0f, -1.0f, +1.0f, -1.0f, }; GLuint myBufferID; glGenBuffers(, &myBufferID…
本节绘制一个三角形,并讲解Buffer Object-缓冲对象 OpenGL的窗口坐标 屏幕中心为坐标原点,横向朝右为x正方向,纵向朝上为y正方向,最大值最小值分别为1,-1. Buffer Object 缓冲对象为内存中的一块空间,用来和OpenGL交互数据. 使用BufferObject的步骤: 创建Buffer的“名称”(或者理解为ID,地址), GLuint类型; 生成Buffer; 绑定Buffer到OpenGL的绑定点(Binding Point); 设置Buffer数据; 具体代码…
用红色来填充GLWidget窗口 修改MyGlWindow.h,添加两个函数,一个用来初始化OpengGL,一个用来绘制OpenGL #pragma once #include <QtOpenGL\qgl.h> class MyGlWindow:public QGLWidget { protected: void initializeGL(); void paintGL(); }; MyGlWindow.cpp #include <gl\glew.h> #include "…
这系列文章是我学习Youtube上一套OpenGL教程的笔记,自己对教程的案例重新制作并且做了一定程度的修改(更有条理,且修正了一些问题).后续将持续更新. Visual Studio 2017工程 教程使用的是visual studio 2012,我电脑上装的是visual studio 2017. 先创建一个Visual C++ Win32 Console Application,命名为GraphicsPad,放在C:\Grphics目录下,不要勾选Create directory for…
移动相机需要用到键盘按键,按键事件的引入需要包含头文件 #include <Qt3DInput\qkeyevent.h> 并实现QWidget中定义的虚函数keyPressEvent 我们首先在MyGlWindow中重写这个虚函数. 在MyGlWindow.h加入 void keyPressEvent(QKeyEvent*); 在MyGlWindow.cpp中定义: void MyGlWindow::keyPressEvent(QKeyEvent * e) { switch (e->ke…
在11节我们说过,MVP矩阵中目前只应用了两个矩阵,World to View 矩阵被省略了,这就导致我们的画面没有办法转换视角. 本节我们将添加这一环节,让相机可以旋转. 为了实现这一目的,我们添加一个相机类, Camera类. Camera.h: #pragma once #include <glm\glm.hpp> class Camera { private: glm::vec3 position; glm::vec3 viewDirection; const glm::vec3 UP…
上节说过矩阵是可以结合的,而且相乘是按照和应用顺序相反的顺序进行的.我们之前初始化translationMatrix和rotationMatrix的时候,第一个参数都是使用的一个初始矩阵 glm::matrix4(),实际上我们可以对代码稍作优化,让初始化过程精简一些. 对比一下优化之前和优化之后的代码: 之前: glm::mat4 projectionMatrix = glm::perspective(30.0f, ((float)width()) / height(), 0.1f, 10.0…
为了证明我们上节渲染出来的是一个立方体而不是一个平面,我们决定将它旋转一定角度,这样我们就需要一个旋转矩阵(也属于ModelTransformMatrix的一部分) 上一节我们的ModelTransformMatrix中做了一个移动(translation)的操作,所以我们将它重命名为translationMatrix. 先看修改后的paintGL()函数: void MyGlWindow::paintGL() { glClear(GL_DEPTH_BUFFER_BIT | GL_COLOR_B…
使用之前的方法写Shader是一件很痛苦的事情,把Shader代码直接卸载C++文件中,需要使用很多引号来包裹,既不美观也不方便. 我们这节的目的是使用纯文本文件保存Shader. 首先在工程中创建两个文件,分别命名为VertexShaderCode.glsl 和 FragmentShaderCode.glsl,后缀名可以自己随意指定,不一定非要是glsl. 然后把上节的Shader代码拷贝到两个文件中去. VertexShaderCode.glsl #version ) vec2 positi…
着色器的一般结构: Shader "MyShader/MyShaderName" { Properties { // ... properties here ... } SubShader { // ... subshader for graphics hardware A ... Pass { // ... pass commands ... } // ... more passes if needed ... } SubShader { // ... subshader for g…
cg片段 Cg程序片段写CGPROGRAM和ENDCG之间 开始时的片段可以作为#pragma语句编译指令 Pass { // ... the usual pass state setup ... CGPROGRAM // compilation directives for this snippet, e.g.: #pragma vertex vert #pragma fragment frag // the Cg/HLSL code itself ENDCG // ... the rest…
An Oblivious Watermarking for 3-D Polygonal Meshes Using Distribution of Vertex Norms 转眼就11月底了,突然开始有点惶恐...感觉这个月身体一直在不舒服,每年总有一段时间觉得心口压抑,虽然也寻医问药,但似乎并没有什么效果.等到我不想去理它的时候,它自己又莫名地好了,真是让人神伤.这个月回了一次家,看到家人似乎又来了几分,心里的焦虑越发浓郁了,也许,这才是我那么惧怕时光匆匆的缘由吧.扯远了... 下周要汇报论文,…
[Vertex and fragment programs] When you use vertex and fragment programs (the so called "programmable pipeline"), most of the hardcoded functionality ("fixed function pipeline") in the graphics hardware is switched off. For example, us…
顶点片段着色器 V&F Shader:英文全称Vertex and Fragment Shader,最强大的Shader类型,也是我们在使用ShaderLab中的重点部分,属于可编程管线,使用的是CG/HLSL语法.分为vertex顶点部分和Fragment像素部分. 本篇的末尾讲述顶点函数传入的结构体类型的参数appdata_base. Shader "Custom/Exam1" { Properties { _MainTex ("Texture", 2D…
Vertex And Fragment Shader(顶点和片段着色器) Shader "Unlit/ Vertex­_And_Fragment_Shader " { Properties { _MainColor("主颜色", color) = (1, 1, 1, 1) } SubShader { Tags { "RenderType"="Opaque" } LOD 100 Pass { //固定的一些格式 Tags{&qu…
现代3D图形编程学习系列翻译地址 http://www.cnblogs.com/grass-and-moon/category/920962.html opengl使用不同的缓存对象 在设置颜色一章中,我们使用了一个缓存对象来存储点和颜色的信息.那么我们有没有可能,将点和颜色的信息分开存储呢?这在实际应用中也许可以使得各个属性之间保持相互的独立.本章补充内容需要做的事情就是这个. 相对于上一章需要改变的内容有 顶点属性和颜色分别独立存储: const float vertex[] = { 0.0…
https://chortle.ccsu.edu/VectorLessons/index.html Chapter0 Points and Lines (已看) Chapter1 Vectors, Points, and Column Matrices (已看) Chapter2 Matrix Addition (已看) Chapter3 Vector Addition (已看) Chapter4 Vector Length (已看) Chapter5 Vector Direction (已看)…
原文如下:obj2opengl: convert obj 3D models to arrays compatible with iPhone OpenGL ES obj2opengl在GitHub中的主页:https://github.com/HBehrens/obj2opengl 终于找到一个iPhone OpenGL ES转换和加载OBJ 3D模型的好工具了,感谢作者 Heiko Behrens 原文翻译如下: 任何时候你想在iPhone应用程序或其他任何OpenGL工程中使用如Blend…
2.1 几何数据类型 向量表示两个点之间的移动,点表示位置. 2.2 向量,坐标向量和基 向量$\overrightarrow{v}$ ,坐标向量c,基向量$\overrightarrow{b^{t}}$ 2.5 Rotation xyz-Euler角度…