GLSL语言基础

2023-11-12

定义:GLSL释义叫做OpenGL着色器编程语言。是为图形计算量身定制的,它包含一些针对向量和矩阵操作的有用特性。

变量名字:变量名称的命名规范与C语言相同:可以使用字母,数字,以及下划线来组成变量的名字。但数字不能作为变量名称的第一个字符。此外由于在GLSL里连续的下划线是保留使用的,所以变量名称也不能包含连续的下划线。

变量的类型:常见类型如下:
1.基础数据类型:包含uint,int,float,double,bool。其中int可以隐式转换成uint;int或者uint隐式转换成float;以及int,uint,float隐式转换成double。其他基础数据类型的转换就只能通过构造函数转换了,如:

float value = 0.5;
int a = int(value);

2.聚合类型:包含有基础数据类型组合而成的向量和矩阵。
组合形式如图所示:
在这里插入图片描述
常见的操作如下所示:
初始化向量:可以指定每个分量值来初始化。代码如下:

vec3 velocity = vec3(0.0, 2.0, 3.0);

也可以使用构造函数来等价或者截取或者加长一个向量。代码如下:

// 等价向量初始化
vec3 velocity = vec3(0.0, 2.0, 3.0);
ivec3 steps = ivec3(velocity);

// 截取向量初始化
vec4 color;
vec3 RGB = vec3(color); // 只有RGB三个分量被截取出来

// 加长向量初始化
vec3 white = vec3(1.0); // white = (1.0, 1.0, 1.0)
vec4 translucent = vec4(white, 0.5);  // white新加一个0.5进行组合生成vec4变量

访问向量:可以通过分量的名称或者数组下标来访问向量。其中分量的名称通常含有与位置相关的分量(x, y, z, w),与颜色相关的分量(r, g, b, a)以及与纹理坐标相关的分量(s, t, p, q),在使用时可以灵活的取分量名称进行组合。代码如下:

// 只要保证取值的分量名存在,赋值的分量名存在且类型可以接收即可。
vec3 lumiance = color.rrr;

初始化矩阵:矩阵mat(mxn)中m代表列数,n代表行数,所以在初始化矩阵时,先初始化列再初始化行。可以传递一个数值来构建对角矩阵。代码如下:

// 由于矩阵大括号不好打出来,此处按照三列进行分割就可以得到具体形式
mat3 m = mat3(4.0) = (4.0, 0, 0,0, 4.0, 0, 0, 0, 4.0)

也可以传递所有数值来构建。代码如下:

// 由于矩阵大括号不好打出来,此处按照三列进行分割就可以得到具体形式
mat3 m = mat3(1.0, 2.0, 3.0, 4.0, 5.0, 6.0, 7.0, 8.0, 9.0) = (1.0, 4.0, 7.0, 2.0, 5.0, 8.0,3.0, 6.0, 9.0)

访问矩阵:通过数组下标进行访问矩阵。其中第一个下标代表取整列数据,第二个下标表示整列数据中指定的行数据。代码如下:

mat4 m = mat4(2.0);    // 初始化一个对角矩阵
vec4 zVec = m[2];     // 获取矩阵第三整列数据
float yScale = m[1][1];   // 获取矩阵第二整列数据中第二行数据,等价于m[1].y

3.结构体和数组:定义和使用方式与C语言类似,这里不再过多赘述。

存储限制符:用来改变数据类型的行为。常见的限制符如下所示:
1.const:用来设置变量为只读类型。与C语言使用规则一致。
2.out:用来定义着色器阶段的输出变量。可以是顶点着色器中的齐次坐标,也可以是片元着色器中的最终颜色。
3.in:用来定义着色器阶段的输入变量。可以是顶点着色器中的顶点属性,此时数据通过用户程序附加顶点属性的方式传递到变量上。设置代码如下所示:

// 顶点着色器
#version 450 core
layout (location = 0) in vec3 aPos;   // 位置变量的属性位置值为 0 
layout (location = 1) in vec3 aColor; // 颜色变量的属性位置值为 1

void main()
{
    gl_Position = vec4(aPos, 1.0);
}

// 用户程序附加顶点方式传递数据
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 6 * sizeof(float), (void*)0);
glEnableVertexAttribArray(0);   // 位置属性

glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 6 * sizeof(float), (void*)(3* sizeof(float)));
glEnableVertexAttribArray(1);  // 颜色属性

当然也可以是前一个着色器的输出变量,此时输出变量和当前着色器的输入变量不仅数据类型要相同,而且变量名也要相同。设置代码如下所示:

// 顶点着色器
#version 450 core
out vec4 vertexColor; // 为片段着色器指定一个颜色输出

void main()
{
    gl_Position = vec4(1.0);
    vertexColor = vec4(0.5, 0.0, 0.0, 1.0); // 把输出变量设置为暗红色
}

// 片段着色器
#version 330 core
out vec4 FragColor;

in vec4 vertexColor; // 从顶点着色器传来的输入变量(名称相同、类型相同)

void main()
{
    FragColor = vertexColor;
}

4.uniform:用来定义着色器之间共享的全局变量。这个uniform修饰的变量不能被着色器写入,只能被用户程序进行写入操作。在着色器程序进行链接着色器时会对所有着色器中的uniform变量生成一张索引列表。常用接口如下:
GLint glGetUniformLocation(GLuint program, const char* name):获取着色器程序中指定Uniform变量名字在索引列表中的索引值。
.program表示着色器程序标志。
.name表示uniform变量名字。

void glUniform{1234}{fdi ui}(GLint location, TYPE value);
void glUniform{1234}{fdi ui}v(GLint location, GLsizei count, GLboolean transpose, const TYPE* value);
void glUniformMatrix{234}{fd}v(GLint location, GLsizei count, GLboolean transpose, const GLfloat* value);
void glUniformMatrix{2x3,2x4,3x2,3x4,4x2,4x3}{fd}v(GLint location, GLsizei count, GLboolean transpose, const GLfloat* value)

:设置指定索引值location处的uniform变量值。
.函数格式:这里的f表示float;d表示double;i表示int;ui表示uint;v表示vec;mxn表示m列n行。
.location表示Uniform变量位置。
.count表示用户数据个数。
.transpose表示矩阵中是否逆向取值,为GL_TRUE时表示取行列,否则表示取列行。
.value表示用户数据源。

5.buffer:用来定义着色器和用户程序之间共享的一片可读写内存缓存。
6.shared:用来在计算着色器中建立本地工作组共享的内存。

GLSL操作符:按照优先级降序排列的操作符如图所示:
在这里插入图片描述

GLSL流控制语句:常见的流控制语句如图所示:
在这里插入图片描述

GLSL参数限制符:GLSL中的函数与C++类似,但是参数没有引用和指针类型。常见的参数限制符如图所示:
在这里插入图片描述

计算的不变性:GLSL可以通过invariant或者precise限制符来确保着色器之间计算的不变性。使用方式如下:
1.invariant限制符:用来设置着色器中的输出变量。当不同着色器之间使用该变量的初始值相同以及该变量参与计算的表达式也相同时,那么得到的计算结果是保持一致的。在着色器中要将所有变量设置成invariant的话,只需要使用以下代码即可:

#pragma STDGL invariant(all)

2.precise限制符:用来设置任何变量和函数返回值的不变性。也就是说不管表达式中的计算变量怎么变化,最终表达式的计算结果是不变的。

预处理器命令:GLSL第一步解析的就是预处理器命令。常见命令如下:
1.#define,#undef:控制常量与宏的定义,与C语言的预处理器命令类似。
2.#if,#ifdef,#ifndef,#else,#elif,#endif:代码的条件编译。条件表达式中只可以使用整数表达式或者#define定义的值。
3.#error text:强迫编译器将text内容插入到着色器的信息日志中。
4.#pragma options:控制编译器的特定选项。常见的选项如下:

选项 描述
optimize 表示编译器优化选项,默认为开启。设置方式为:#pragma optimize(on或者off)
debug 表示编译器调试选择,默认为关闭。设置方式为:#pragma debug(on或者off)

5.#extension options:设置编译器支持特定GLSL扩展功能。设置方式代码如下:

// 操作某一具体扩展功能
#extension extension_name : <direcetve>
// 操作所有扩展功能
#extension all : <direcetve>

其中direcetve表示扩展命令修饰符。常见修饰符如下:

命令 描述
require 如果无法支持给定的扩展功能,或者被设置为all,则提示错误
enable 如果无法支持给定的扩展功能,则给出警告;如果被设置为all,则提示错误
warn 如果无法支持给定的扩展功能,或者在编译过程中使用了任何扩展,则给出警告
disable 禁止支持给定的扩展;如果被设置为all,则禁止所有的扩展。当在代码中涉及使用 禁止的扩展时,就会提示警告和错误

6.#version number:设置当前使用的GLSL版本名称。
7.#line options:设置诊断行号。

预定义宏:GLSL中的宏定义跟C语言中的宏定义类似,但是GLSL中的宏不支持字符串替换以及预编译连接符。常用的预定义宏如下:
1.LINE:行号,默认为已经处理的所有换行符的个数加一,也可以通过#line命令修改。
2.FILE:当前处理的源字符串编号。
3.VERSION:OpenGL着色语言的整数表示形式。

数据接口块:由于篇幅较多,以经另外写了篇博客来阐述。参考https://blog.csdn.net/zjz520yy/article/details/83662520

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

GLSL语言基础 的相关文章

  • 解决ERROR 2003 (HY000): Can‘t connect to MySQL server on ‘localhost:3306‘ (10061)

    ERROR 2003 HY000 Can t connect to MySQL server on localhost 3306 10061 1 安装成功之后输入MYSQL报出ERROR 2003 HY000 Can t connect t
  • 【OpenCV图像处理入门学习教程六】基于Python的网络爬虫与OpenCV扩展库中的人脸识别算法比较

    OpenCV图像处理入门学习教程系列 上一篇第五篇 基于背景差分法的视频目标运动侦测 一 网络爬虫简介 Python3 网络爬虫 大家应该不陌生了 接下来援引一些Jack Cui在专栏 Python3网络爬虫入门 中的内容来帮助初学者理解
  • QT 如何修改工程(项目)名?

    前因 我们有时候一开始起的项目名到后面并不合乎心意时 而且项目里面的大多数类都是重复的 此时我们只想修改一下工程名即可 步骤如下 在这里假设我原来的工程名字是test 想要修改成名字为demo 第一步 打开工程文件夹 除了test pro以
  • 【JVM】JVM垃圾回收机制GC

    文章目录 JVM垃圾回收机制 一 堆内存区域划分 1 1内存分配策略 1 2永久代 Permanent Generation 1 3元空间 MetaSpace 二 标记算法 2 1引用计数算法 2 2可达性分析算法 2 3引用 强引用 Ha
  • Matlab中读取excel表格数据

    一 Matlab中读取excel表格数据步骤讲解 第二步 第三步 第四步 第五步 第六步 第七步 输入之后按回车键 就会出现相应的波形 效果图
  • 链接、装载与库——编译与链接

    从第二章开始不再按照目录的顺序总结 而是将大块知识点总结在一起 第二章 编译和链接 集成开发环境 IDE 一般都将编译和链接的过程一步完成 此过程成为构建 Bulid 但其掩盖了系统软件运行机制 gcc hello c a out 一个可执
  • win10离线安装ros-melodic-desktop_full

    在线安装最容易出现安装包下载不了导致的安装失败问题 本篇文章续上篇在线安装 安装在线包 下载ros melodic desktop full 下载地址 ros melodic离线包下载地址 开始菜单中 右键 x64 Native Tools
  • Codeforces Round 875 (Div. 1) A. Copil Copac Draws Trees

    题意 Copil Copac 给定了一个由 n 1 条边组成的列表 该列表描述了一棵由 n 个顶点组成的树 他决定用下面的算法来绘制它 步骤 0 绘制第一个顶点 顶点1 转到步骤1 步骤 1 对于输入中的每一条边 依次 如果该边连接一个已经
  • 【完全开源】小安派-Cam-U 摄像头核心板

    一 概述 小安派 Cam U AiPi Cam U 是安信可开源团队专门为Ai M61 32S设计的一款开发板 支持WiFi6 BLE5 3 所搭载的Ai M61 32S 模组具有丰富的外设接口 具体包括 DVP MJPEG Dispaly
  • [4G&5G专题-120]:培训-跟小朋友聊通信

    用小孩子的语言与小朋友聊通信
  • 【算法 -- LeetCode】(025) K 个一组翻转链表

    1 题目 给你链表的头节点 head 每 k 个节点一组进行翻转 请你返回修改后的链表 k 是一个正整数 它的值小于或等于链表的长度 如果节点总数不是 k 的整数倍 那么请将最后剩余的节点保持原有顺序 你不能只是单纯的改变节点内部的值 而是

随机推荐

  • 什么是钩子函数

    钩子函数 钩子函数 钩子函数是在一个事件触发的时候 在系统级捕获到了他 然后做一些操作 一段用以处理系统消息的程序 钩子 就是在某个阶段给你一个做某些处理的机会 钩子函数 1 是个函数 在系统消息触发时被系统调用 2 不是用户自己触发的 钩
  • Highcharts中更新series的5种方法

    用Highcharts画图时 经常需要更新所画的图表 最常见的就是改变数据以更新图表 在Highcarts中 数据对应的参数是series 这儿就以图1的柱状图为例 列举如何更新series的5种方法 以供参考 源代码可从这儿访问 图1 1
  • 嵌入式Linux驱动开发(LCD屏幕专题)(四)

    单Buffer的缺点与改进方法 1 单Buffer的缺点 如果APP速度很慢 可以看到它在LCD上缓慢绘制图案 即使APP速度很高 LCD控制器不断从Framebuffer中读取数据来显示 而APP不断把数据写入Framebuffer 假设
  • [从零开始学DeepFaceLab-9]: 使用-命令行八大操作步骤-第6步:模型的选择与训练 - 模型选择

    目录 总体流程 步骤6 模型的选择与训练 模型选择 6 1 模型的差别 6 2 SAEHD模型的超参数
  • spring-integration-redis中分布式锁RedisLockRegistry的使用

    pom依赖
  • Java技术从零到CTO路线图

    在技术方面无论我们怎么学习 总感觉需要提升自已不知道自己处于什么水平了 但如果有清晰的指示图供参考还是非常不错的 这样我们清楚的知道我们大概处于那个阶段和水平 Java程序员 高级特性 反射 泛型 注释符 自动装箱和拆箱 枚举类 可变 参数
  • 毕业设计-基于机器油菜虫害图像识别方法研究 -YOLO

    目录 前言 课题背景和意义 实现技术思路 相关基础理论与技术 1 人工神经网络 2 卷积神经网络 3 基于卷积神经网络的目标检测识别模型 4 YOLO 系列算法 实现效果图样例 最后 前言 大四是整个大学期间最忙碌的时光 一边要忙着备考或实
  • 韩式多用动态图(甜蜜女孩)

  • 离线在Jenkins安装CoBOT安装插件

    最近在某金融客户做POC 把CoBOT安装在Jenkins上面 当前Jenkins版本没有任何插件 安装后由于是云桌面没有连接互联网或已经设置访问策略 无法进行在线安装插件 所以只能下载插件后再安装 在网络上搜索Jenkins插件 下载到两
  • 【SpringCloud】application.yml和 bootstrap.yml 区别

    1 首先yml和properties文件都是属于配置文件 功能一样 主要是区别于application和bootstrap的加载顺序 Bootstrap yml bootstrap properties 在application yml a
  • caffe问题Check failed: registry.count(type) == 1 (0 vs. 1) Unknown layer type: Python

    caffe中输入层使用python时 出现问题 Check failed registry count type 1 0 vs 1 Unknown layer type Python 解决方法 在caffe目录下Makefile confi
  • va_start和va_end使用详解

    本文主要介绍va start和va end的使用及原理 介绍这两个宏之前先看一下C中传递函数的参数时的用法和原理 1 在C中 当我们无法列出传递函数的所有实参的类型和数目时 可以用省略号指定参数表 void foo void foo par
  • 手机抓包fiddler配置及使用教程

    本文基于Fiddler4讲解基本使用 fiddler抓包原理 注意 Fiddler 是以代理web服务器的形式工作的 它使用代理地址 127 0 0 1 端口 8888 当Fiddler退出的时候它会自动注销 这样就不会影响别的 程序 不过
  • libsvm库简介及使用

    libsvm是基于支持向量机 support vector machine SVM 实现的开源库 由台湾大学林智仁 Chih Jen Lin 教授等开发 它主要用于分类 支持二分类和多分类 和回归 它的License是BSD 3 Claus
  • Terdata 基础 第三课(参数宏)

    1 宏不是ANSI标准支持的 但大部分RDBMS都支持宏 在Teradata中 在ANSI和BTET缺省模式下都可以创建和执行宏 只不过在ANSI模式下会给出警告信息 1 1 参数宏 宏中可以包含可替代值的变量 CREATE MACRO d
  • linux shell 按行循环读入文件方法

    linux shell 按行循环读入文件常用代码如下 bin bash printf n echo cat file whiel read line cat test txt while read line do echo line don
  • wofstream,wcout无法输出unicode的真相

    之前我转载过一篇ofstream和wofstream与中文输出问题 让我初步知道如何解决这类问题 第一次我没有在意 按照文章中做的方法去做 然后程序就运行正常了 我试图去记住这些规则 但是我后来发现 太难了 以至于我在最近一次使用到 std
  • 程序编程代码大全_CNC加工中心程序代码大全,数控加工必备!

    数控机床的可编程功能分为两类 一类用来实现刀具轨迹控制即各进给轴的运动 如直线 圆弧插补 进给控制 坐标系原点偏置及变换 尺寸单位设定 刀具偏置及补偿等 这一类功能被称为准备功能 以字母G以及两位数字组成 也被称为G代码 另一类功能被称为辅
  • 免费赠票

    Cloud Ace 受邀参加 GTC2022 全球流量大会 助力中国企业扬帆出海 大会将在 2023 年 2 月 28 日 3 月 1 日举行 地点就在福田会展中心 6 号展馆 大会门票实行收费制 您可以扫码填写 Cloud Ace 的报名
  • GLSL语言基础

    定义 GLSL释义叫做OpenGL着色器编程语言 是为图形计算量身定制的 它包含一些针对向量和矩阵操作的有用特性 变量名字 变量名称的命名规范与C语言相同 可以使用字母 数字 以及下划线来组成变量的名字 但数字不能作为变量名称的第一个字符