點擊上方藍字可直接關注!方便下次閱讀。如果對你有幫助,可以點個在看,讓它可以幫助到更多老鐵~

原教程地址:

https://learnopengl-cn.github.io/01%20Getting%20started/05%20Shaders/

一、  着色器概述

從基本意義上來講,着色器只是一種把輸入轉化爲輸出的程序。它們之間唯一的“通訊”方式只有通過輸入和輸出來實現。

着色器是使用一種叫GLSL的類 C 語言寫成的, GLSL 是爲圖形計算量身定製的,它包含一些針對向量和矩陣操作的有用特性。

1.  輸入與輸出

頂點着色器中定義一個輸出,在片段着色器中定義輸入來接收這個輸出。

頂點着色器:

out vec4 vertexColor;   // 爲片段着色器指定一個顏色輸出

片段着色器:

in vec4 vertexColor;      // 從頂點着色器傳來的輸入變量 (名稱相同、類型相同)

就是紅色三角形的例子!

2. Uniform 數據發送方式

Uniform 是一種從 CPU 中的應用向 GPU 中的着色器發送數據的方式,但 uniform 和頂點屬性有些不同。

首先, uniform 是全局的 (Global) 第二,無論你把 uniform 值設置成什麼, uniform 會一直保存它們的數據,直到它們被重置或更新。

爲了實現例程中的效果,我使用了QObject自帶的定時器事件,並使用 Qt update() 函數來更新繪圖。

程序例子:

//使用uniform的片段着色器

static const char *fragmentShaderSourceUniform =

"#version 330 core\n"

"out vec4 FragColor;\n"

"uniform vec4 ourColor;\n" // 在OpenGL程序代碼中設定這個變量

"void main(){\n"

" FragColor = ourColor;\n"

"}\n\0";

paintGL中更新 Uniform :

#ifdef COLORCHANGE

// 更新uniform顏色

float greenValue = sin(m_timeout) / 2.0f + 0.5f;

int vertexColorLocation = m_core->glGetUniformLocation(m_shaderProgram, "ourColor");

m_core->glUniform4f(vertexColorLocation, 0.0f, greenValue, 0.0f, 1.0f);

#elif MULTICOLOR


#endif

定時器更新計數:

void MyGLWidget::timerEvent(QTimerEvent *e)

{

Q_UNUSED(e);


if(m_timeout >= 1.0)

{

m_timeout = -1.0;

}


m_timeout = m_timeout + 0.05;


update();

}

效果視頻:

三角形顏色漸變:

矩形顏色漸變:

3.  頂點屬性傳遞顏色

GLfloat vertices[] = {

// 位置 // 顏色

0.5f, -0.5f, 0.0f, 1.0f, 0.0f, 0.0f, // 右下

-0.5f, -0.5f, 0.0f, 0.0f, 1.0f, 0.0f, // 左下

0.0f, 0.5f, 0.0f, 0.0f, 0.0f, 1.0f // 頂部

};


m_core->glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 6 * sizeof(GLfloat), nullptr);

m_core->glEnableVertexAttribArray(0); //以頂點屬性位置值作爲參數,啓用頂點屬性;頂點屬性默認是禁用的

m_core->glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 6 * sizeof(GLfloat), (void*)(3* sizeof(float)));

m_core->glEnableVertexAttribArray(1); //以頂點屬性位置值作爲參數,啓用頂點屬性;頂點屬性默認是禁用的

效果圖:

二、  總結

1、  小結

原教程中主要介紹了着色器的語法,改變顏色的三種方式。不同着色器間的輸入輸出、全局變量Uniform的使用、在頂點屬性中設置顏色等。

最後,如需完整工程可在公衆號後臺留言

學不可以已

相關文章