C++自研3D教程OPENGL版本---動態批處理的基本實現

又開始找工作了,借機休息出去旅行兩個月,順便利用這段時間整理下以前寫的東西。
以下是一個簡單的動態批處理實現:

#include <GL/glew.h>
#include <GLFW/glfw3.h>
#include <iostream>
#include <vector>// 頂點結構體
struct Vertex {float x, y, z; // 位置float r, g, b; // 顏色
};// 動態批處理類
class DynamicBatch {
public:DynamicBatch() {// 初始化 VAO 和 VBOglGenVertexArrays(1, &VAO);glGenBuffers(1, &VBO);glBindVertexArray(VAO);glBindBuffer(GL_ARRAY_BUFFER, VBO);// 設置頂點屬性指針glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, sizeof(Vertex), (void*)offsetof(Vertex, x));glEnableVertexAttribArray(0);glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, sizeof(Vertex), (void*)offsetof(Vertex, r));glEnableVertexAttribArray(1);glBindVertexArray(0);}~DynamicBatch() {glDeleteVertexArrays(1, &VAO);glDeleteBuffers(1, &VBO);}// 添加頂點數據void AddVertex(const Vertex& vertex) {vertices.push_back(vertex);}// 更新頂點緩沖區void UpdateBuffer() {glBindBuffer(GL_ARRAY_BUFFER, VBO);glBufferData(GL_ARRAY_BUFFER, vertices.size() * sizeof(Vertex), vertices.data(), GL_DYNAMIC_DRAW);}// 渲染批處理void Render() {glBindVertexArray(VAO);glDrawArrays(GL_TRIANGLES, 0, vertices.size());glBindVertexArray(0);}// 清空頂點數據void Clear() {vertices.clear();}private:GLuint VAO, VBO; // 頂點數組對象和頂點緩沖區對象std::vector<Vertex> vertices; // 頂點數據
};

// 頂點著色器

const char* vertexShaderSource = R"(
#version 330 core
layout(location = 0) in vec3 aPos;
layout(location = 1) in vec3 aColor;
out vec3 ourColor;
void main() {gl_Position = vec4(aPos, 1.0);ourColor = aColor;
}
)";// 片段著色器
const char* fragmentShaderSource = R"(
#version 330 core
in vec3 ourColor;
out vec4 FragColor;
void main() {FragColor = vec4(ourColor, 1.0);
}
)";
// 編譯著色器
GLuint CompileShader(GLenum type, const char* source) {GLuint shader = glCreateShader(type);glShaderSource(shader, 1, &source, nullptr);glCompileShader(shader);GLint success;glGetShaderiv(shader, GL_COMPILE_STATUS, &success);if (!success) {char infoLog[512];glGetShaderInfoLog(shader, 512, nullptr, infoLog);std::cerr << "Shader compilation failed: " << infoLog << std::endl;}return shader;
}// 鏈接著色器程序
GLuint CreateShaderProgram(const char* vertexSource, const char* fragmentSource) {GLuint vertexShader = CompileShader(GL_VERTEX_SHADER, vertexSource);GLuint fragmentShader = CompileShader(GL_FRAGMENT_SHADER, fragmentSource);GLuint shaderProgram = glCreateProgram();glAttachShader(shaderProgram, vertexShader);glAttachShader(shaderProgram, fragmentShader);glLinkProgram(shaderProgram);GLint success;glGetProgramiv(shaderProgram, GL_LINK_STATUS, &success);if (!success) {char infoLog[512];glGetProgramInfoLog(shaderProgram, 512, nullptr, infoLog);std::cerr << "Shader program linking failed: " << infoLog << std::endl;}glDeleteShader(vertexShader);glDeleteShader(fragmentShader);return shaderProgram;
}int main() {// 初始化 GLFWif (!glfwInit()) {std::cerr << "Failed to initialize GLFW" << std::endl;return -1;}// 創建窗口GLFWwindow* window = glfwCreateWindow(800, 600, "Dynamic Batching Example", nullptr, nullptr);if (!window) {std::cerr << "Failed to create GLFW window" << std::endl;glfwTerminate();return -1;}glfwMakeContextCurrent(window);// 初始化 GLEWif (glewInit() != GLEW_OK) {std::cerr << "Failed to initialize GLEW" << std::endl;return -1;}// 創建著色器程序GLuint shaderProgram = CreateShaderProgram(vertexShaderSource, fragmentShaderSource);// 創建動態批處理對象DynamicBatch batch;// 主循環while (!glfwWindowShouldClose(window)) {glClear(GL_COLOR_BUFFER_BIT);// 添加頂點數據batch.Clear();batch.AddVertex({-0.5f, -0.5f, 0.0f, 1.0f, 0.0f, 0.0f});batch.AddVertex({0.5f, -0.5f, 0.0f, 0.0f, 1.0f, 0.0f});batch.AddVertex({0.0f, 0.5f, 0.0f, 0.0f, 0.0f, 1.0f});// 更新緩沖區并渲染batch.UpdateBuffer();glUseProgram(shaderProgram);batch.Render();// 交換緩沖區glfwSwapBuffers(window);glfwPollEvents();}// 清理glDeleteProgram(shaderProgram);glfwTerminate();return 0;
}

代碼說明
DynamicBatch 類:

負責管理頂點數據、更新頂點緩沖區和渲染。使用 std::vector 存儲動態頂點數據。
通過 glBufferData 將頂點數據上傳到 GPU。
頂點和片段著色器:簡單的著色器,用于渲染帶顏色的三角形。
主循環:每一幀清空批處理數據,添加新的頂點數據,更新緩沖區并渲染。
動態更新:使用 GL_DYNAMIC_DRAW 標志更新頂點緩沖區,適用于頻繁變化的頂點數據。

運行結果
運行程序后,你會看到一個彩色的三角形。每一幀都會動態更新頂點數據并渲染。

優化建議
減少內存分配:
如果頂點數據頻繁變化,可以預先分配足夠的內存,避免頻繁調用 glBufferData。
使用實例化渲染:
如果需要渲染大量相同對象,可以使用實例化渲染(Instanced Rendering)進一步優化性能。
多線程更新:
在多線程環境中,可以將頂點數據的更新和渲染分離到不同的線程中。
通過動態批處理,你可以有效地減少繪制調用,提高渲染性能,特別是在需要渲染大量小對象的場景中。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/894883.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/894883.shtml
英文地址,請注明出處:http://en.pswp.cn/news/894883.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

61. Linux內核啟動流程簡介

一、vmlinux.lds簡介 從arch/arm/kernel/vmlinux.lds分析Linux內核第一行啟動代碼。找到ENTRY(stext) 入口函數是stext&#xff0c;image和zImage是經過壓縮的&#xff0c;Linux內核會先進行解壓縮&#xff0c;解壓縮完成以后就要運行Linux內核。要求&#xff1a; 1、MMU關閉 …

汽車智能座艙的技術演進與用戶體驗重構 —— 基于多模態交互與 AI 融合的范式創新

摘要&#xff1a; 汽車智能座艙作為人 - 車 - 環境交互的核心載體&#xff0c;正經歷從功能驅動到體驗驅動的范式變革。本文通過技術解構與用戶行為分析&#xff0c;深入揭示智能座艙在異構計算、多模態感知、服務生態等維度的創新路徑。研究表明&#xff0c;智能座艙的競爭焦…

使用 Let‘s Encrypt 和 OpenResty 實現域名轉發與 SSL 配置

在搭建網站或服務時&#xff0c;確保域名的安全性和正確的流量轉發是非常重要的。本文將介紹如何使用 Let’s Encrypt 獲取免費的 SSL 證書&#xff0c;并將其配置到 OpenResty 中&#xff0c;同時實現特定的域名轉發規則。這不僅可以提升網站的安全性&#xff0c;還能優化流量…

SpringBoot3整合Swagger3時出現Type javax.servlet.http.HttpServletRequest not present錯誤

目錄 錯誤詳情 錯誤原因 解決方法 引入依賴 修改配置信息 創建文件 訪問 錯誤詳情 錯誤原因 SpringBoot3和Swagger3版本不匹配 解決方法 使用springdoc替代springfox&#xff0c;具體步驟如下&#xff1a; 引入依賴 在pom.xml文件中添加如下依賴&#xff1a; <…

ChatGPT提問技巧:行業熱門應用提示詞案例-文案寫作

ChatGPT 作為強大的 AI 語言模型&#xff0c;已經成為文案寫作的得力助手。但要讓它寫出真正符合你需求的文案&#xff0c;關鍵在于如何與它“溝通”&#xff0c;也就是如何設計提示詞&#xff08;Prompt&#xff09;。以下是一些實用的提示詞案例&#xff0c;幫助你解鎖 ChatG…

供排水水工公司開展企業獲得用水營商環境滿意度調查

為了持續提升企業的供水服務品質&#xff0c;進一步優化當地的營商環境&#xff0c;深圳市供排水公司水工公司緊密結合其實際工作情況&#xff0c;特別委托民安智庫開展了2023年度優化營商環境調查專項工作。該項目的核心目的是深入了解并評估市各類獲得用水企業的用水環境滿意…

【Elasticsearch】分桶聚合功能概述

這些聚合功能可以根據它們的作用和應用場景分為幾大類&#xff0c;以下是分類后的結果&#xff1a; 1.基礎聚合&#xff08;Basic Aggregations&#xff09; ? Terms&#xff08;字段聚合&#xff09; 根據字段值對數據進行分組并統計。 例子&#xff1a;按產品類別統計銷…

mysql的cpu使用率100%問題排查

背景 線上mysql服務器經常性出現cpu使用率100%的告警&#xff0c; 因此整理一下排查該問題的常規流程。 1. 確認CPU占用來源 檢查系統進程 使用 top 或 htop 命令&#xff0c;確認是否是 mysqld 進程導致CPU滿載&#xff1a;top -c -p $(pgrep mysqld)2. 實時分析MySQL活動 …

人工智能賦能企業系統架構設計:以ERP與CRM系統為例

一、引言 1.1 研究背景與意義 在數字化時代&#xff0c;信息技術飛速發展&#xff0c;人工智能&#xff08;Artificial Intelligence, AI&#xff09;作為一項具有變革性的技術&#xff0c;正深刻地影響著各個領域。近年來&#xff0c;AI 在技術上取得了顯著突破&#xff0c;…

使用jmeter進行壓力測試

使用jmeter進行壓力測試 jmeter安裝 官網安裝包下載&#xff0c;選擇二進制文件&#xff0c;解壓。 tar -xzvf apache-jmeter-x.tgz依賴jdk安裝。 yum install java-1.8.0-openjdk環境變量配置&#xff0c;修改/etc/profile文件&#xff0c;添加以下內容。 export JMETER/…

深入理解流(Streams)—— 聲明式數據處理的藝術

1. 引言 大家好&#xff01;歡迎來到本系列博客的第三篇。在前兩篇文章中&#xff0c;我們已經領略了 Java 8 中 行為參數化 和 Lambda 表達式 的魅力。 在第 1 章 Java行為參數化&#xff1a;從啰嗦到簡潔的代碼進化中&#xff0c;我們了解到如何通過將行為&#xff08;代碼…

【Linux】之【Get√】nmcli device wifi list 與 wpa_cli scan 和 wpa_cli scan_result 區別

nmcli device wifi list 是 NetworkManager 的命令行工具 nmcli 的一部分&#xff0c;它用于列出當前可用的無線網絡。它的作用和 wpa_cli 的掃描功能類似&#xff0c;但有一些不同點。 1. nmcli device wifi list 功能&#xff1a; nmcli device wifi list 命令用于顯示當前…

【藍橋杯嵌入式】6_定時器輸入捕獲

全部代碼網盤自取 鏈接&#xff1a;https://pan.baidu.com/s/1PX2NCQxnADxYBQx5CsOgPA?pwd3ii2 提取碼&#xff1a;3ii2 這是兩個信號發生器&#xff0c;可以通過調節板上的兩個電位器R39和R40調節輸出頻率。 將PB4、PA15選擇ch1&#xff0c;兩個信號發生器只能選擇TIM3和TIM…

詳解SQLAlchemy的函數relationship

在 SQLAlchemy 中&#xff0c;relationship 是一個非常重要的函數&#xff0c;用于定義模型之間的關系。它用于在 ORM 層面上表示數據庫表之間的關聯關系&#xff08;如 1 對 1、1 對多和多對多&#xff09;。relationship 的主要作用是提供一個高級接口&#xff0c;用于在模型…

分桶函數的使用

除了 NTILE 函數&#xff0c;SQL 中還有其他一些與 分桶&#xff08;bucketization&#xff09;相關的函數&#xff0c;雖然它們的實現方式不同&#xff0c;但都涉及將數據分成多個區間或組。以下是一些常用的分桶函數&#xff1a; 1. CASE 語句 雖然 CASE 不是開窗函數&…

iOS 音頻錄制、播放與格式轉換

iOS 音頻錄制、播放與格式轉換:基于 AVFoundation 和 FFmpegKit 的實現 在 iOS 開發中,音頻處理是一個非常常見的需求,比如錄音、播放音頻、音頻格式轉換等。本文將詳細解讀一段基于 AVFoundation 和 FFmpegKit 的代碼,展示如何實現音頻錄制、播放以及 PCM 和 AAC 格式之間…

數據結構與算法(test1)

一、樹和二叉樹 1. 看圖&#xff0c;完成以下填空 (1).樹的度為________。 (2).樹中結點的最大層次&#xff0c;稱為樹的_____或樹的______&#xff0c;值是______。 (3).結點A和B的度分別為________ 和 ________。 (4).結點A是結點B的________。 (5).結點B是結點A的________…

新版AndroidStudio 修改 jdk版本

一、問題 之前&#xff0c;在安卓項目中配置JDK和Gradle的過程非常直觀&#xff0c;只需要進入Android Studio的File菜單中的Project Structure即可進行設置&#xff0c;十分方便。 如下圖可以在這修改JDK: 但是升級AndroidStudio之后&#xff0c;比如我升級到了Android Stu…

litemall,又一個小商場系統

litemall Spring Boot后端 Vue管理員前端 微信小程序用戶前端 Vue用戶移動端 代碼地址&#xff1a;litemall: 又一個小商城。 litemall Spring Boot后端 Vue管理員前端 微信小程序用戶前端 Vue用戶移動端

cursor 開發java項目教程簡單上手

1.官網下載 Cursor - The AI Code Editor 下載完后注冊賬號&#xff0c;可以使用無限郵的方式 注冊完之后 設置中文 可以選擇設置為中文 Ctrl Shift X 進入設置頁面輸入chinese 然后重啟 更改jdk跟maven倉庫設置 ctrlshiftp 打開輸入框后輸入json&#xff0c;把下面代碼…