日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

OpenGL:纹理Textures

發布時間:2023/12/20 编程问答 28 豆豆
生活随笔 收集整理的這篇文章主要介紹了 OpenGL:纹理Textures 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

參考資料:https://learnopengl-cn.github.io/01%20Getting%20started/06%20Textures/
學習筆記,不一當作參考教程,上面的參考資料是比較詳細的參考教程

文章目錄

      • 生成紋理
        • 生成紋理對象
        • 綁定紋理對象
        • 為綁定的紋理對象設置環繞,過濾方式
          • 設置環繞
            • 嘗試使用只對一個軸操作,和對兩個軸操作的不同之處
          • 設置過濾方式
            • 鄰近過濾
            • 線性過濾
            • 多級紋理
        • 加載并生成紋理
      • 應用紋理
        • 頂點著色器處理
        • 片段著色器處理
        • 設置多個紋理
      • 補充

生成紋理

首先看一下生成紋理的代碼片段,有個整體認識。

//生成紋理對象 unsigned int texture; glGenTextures(1, &texture); //綁定紋理對象 glBindTexture(GL_TEXTURE_2D, texture); // 為當前綁定的紋理對象設置環繞、過濾方式 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); // 加載并生成紋理 int width, height, nrChannels; unsigned char *data = stbi_load("container.jpg", &width, &height, &nrChannels, 0); if (data) {glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, width, height, 0, GL_RGB, GL_UNSIGNED_BYTE, data);glGenerateMipmap(GL_TEXTURE_2D); } else {std::cout << "Failed to load texture" << std::endl; } stbi_image_free(data);

生成紋理對象

同樣使用唯一ID引用的方法(需要了解以下怎么通過ID唯一引用的),和MFC的函數調用方式像不像

//生成紋理對象 unsigned int texture; glGenTextures(1, &texture);

綁定紋理對象

//綁定紋理對象 glBindTexture(GL_TEXTURE_2D, texture);

為綁定的紋理對象設置環繞,過濾方式

設置環繞

當紋理坐標超過了0-1范圍之后,OpenGL對紋理的處理。提供了四種方法,默認是GL_REPEAT重復紋理。

實現這個紋理環繞需要通過以下函數

glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_MIRRORED_REPEAT); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_MIRRORED_REPEAT);

glTexParameter*函數對單獨的一個坐標軸設置(s、t(如果是使用3D紋理那么還有一個r)它們和x、y、z是等價的)。

嘗試使用只對一個軸操作,和對兩個軸操作的不同之處
設置過濾方式
鄰近過濾

線性過濾

多級紋理


加載并生成紋理

需要使用一個第三方函數stb_image.hl這里幫忙加載紋理圖片,讀取數據。
注意使用這個頭文件時應該如下:

#define STB_IMAGE_IMPLEMENTATION #include "stb_image.h" ... int width, height, nrChannels; unsigned char *data = stbi_load("container.jpg", &width, &height, &nrChannels, 0); if (data) {glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, width, height, 0, GL_RGB, GL_UNSIGNED_BYTE, data);glGenerateMipmap(GL_TEXTURE_2D); } else {std::cout << "Failed to load texture" << std::endl; } stbi_image_free(data);

注意讀入圖片的代碼有的會這樣寫,但是可能會報錯:

unsigned char *data = stbi_load(FileSystem::getPath("resources/textures/container.jpg").c_str(), &width, &height, &nrChannels, 0);

應用紋理

要想將生成的紋理應用到圖形上,首先需要告訴OpenGL紋理映射坐標(紋理圖像坐標),其次是利用采樣器在對應位置采樣紋理。

頂點著色器處理

在頂點上增加紋理映射坐標信息,頂點屬性結構如下:

用以下兩行代碼讀取紋理坐標信息:

glVertexAttribPointer(2, 2, GL_FLOAT, GL_FALSE, 8 * sizeof(float), (void*)(6 * sizeof(float))); glEnableVertexAttribArray(2);

頂點著色器代碼如下,同樣增加一個紋理坐標屬性。

#version 330 core layout (location = 0) in vec3 aPos; layout (location = 1) in vec3 aColor; layout (location = 2) in vec2 aTexCoord;//紋理坐標out vec3 ourColor; out vec2 TexCoord;void main() {gl_Position = vec4(aPos, 1.0);ourColor = aColor;TexCoord = aTexCoord; }

片段著色器處理

片段著色器接受紋理坐標,以及全局變量,紋理圖像。

#version 330 core out vec4 FragColor;in vec3 ourColor; in vec2 TexCoord;uniform sampler2D ourTexture;void main() {FragColor = texture(ourTexture, TexCoord); }

Sample采樣器,通過后綴1D 2D 3D決定是幾維圖像。

設置多個紋理

紋理單元:把紋理存在不同的位置(最多可以存16個)
通過激活不同的紋理單元實現對多個紋理的使用,需要按照對應順序激活紋理。
一個紋理的默認紋理單元是0,它是默認的激活紋理單元,

// bind textures on corresponding texture unitsglActiveTexture(GL_TEXTURE0);glBindTexture(GL_TEXTURE_2D, texture1);glActiveTexture(GL_TEXTURE1);glBindTexture(GL_TEXTURE_2D, texture2);

多個紋理下的片段著色器:

#version 330 core ...uniform sampler2D texture1; uniform sampler2D texture2;void main() {FragColor = mix(texture(texture1, TexCoord), texture(texture2, TexCoord), 0.2); }

補充

創作挑戰賽新人創作獎勵來咯,堅持創作打卡瓜分現金大獎

總結

以上是生活随笔為你收集整理的OpenGL:纹理Textures的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。