美文网首页
OpenGL(3) —— OpenGL 的矩阵变换

OpenGL(3) —— OpenGL 的矩阵变换

作者: 你可记得叫安可 | 来源:发表于2020-01-27 16:08 被阅读0次

基本计算

向量之间的计算有 点积叉积
矩阵之间的计算有加减数乘矩阵间乘法

矩阵的缩放

矩阵缩放
OpenGL 中,我们用 4 维向量来表示 3 维空间的数据,其中多出来的 w 维适用于透视投影的,因此在缩放中 w 依然为 1,因为在 3 维空间中变换 w 值没有意义。

位移

位移矩阵
这里就表现出了 w 分量的意义,如果没有 w 分量,上面的向量 (x, y, z) 就不能位移,这个坐标就只能表示方向向量。

旋转

一个向量在三维空间中旋转,主要受两个条件影响:1. 旋转角度;2. 旋转轴。


沿 x 轴旋转 沿 y 轴旋转 沿 z 轴旋转

上面我们只能沿着某个单位轴进行旋转,但是更方便的情况是,我们希望能够沿着任意方向轴旋转,这个有点复杂了,待研究。

组合变换

矩阵可以进行组合,达到用一个矩阵就进行多种变换的效果。假设有顶点 (x, y, z),我们将其放大两倍,然后位移 (1, 2, 3),那么我们需要一个位移矩阵和一个缩放矩阵来完成这个事。

组合变换
矩阵相乘不满足交换律,因此参加计算的矩阵位置顺序很重要。当矩阵相乘时,最右边的矩阵是第一个与向量计算的矩阵,因此上图中的矩阵乘法我们应该从右往左读。即先放大两倍,然后平移的。如果我们交换顺序,就会变为先平移,再放大,那么平移的量就也会被放大。
组合变换最终计算式

OpenGL 中相关 API

  • Matrix#setIdentityM(float[] sm, int smOffset),创建一个单位矩阵。其中第一个参数是创建出来的单位矩阵存储的地方,第二个参数是单位矩阵在 sm 数组中的偏移量。生成的结果按照列优先存储
  • Matrix#translateM(float[] m, int mOffset, float x, float y, float z),第一个参数是需要变换的矩阵,第二个参数是偏移量。后面三个分别是 (x, y, z) 三个方向的位移量。
  • Matrix#rotateM(float[] m, int smOffset, float a, float x, float y, float z)a 表示旋转的角度,角度制(0º ~ 360º)。x, y, z 分别代表旋转的轴,如果 x = 0, y = 0, z = 1 代表围绕 z 轴旋转。
  • Matrix#scaleM(float[] m, int smOffset, float x, float y, float z),在某个轴方向进行缩放。

代码中的写法

  1. 定义模型矩阵:
private float[] modelMatrix = new float[16];

这里使用长度为 16 的 float 数组,这是因为我们上面已经解释了,这里使用的矩阵都是 4x4 的矩阵。

  1. onSurfaceChanged() 中初始化模型矩阵:
@Override
public void onSurfaceChanged(GL10 gl10, int width, int height) {
    glViewport(0, 0, width, height);
    setIdentityM(modelMatrix, 0);
    Matrix.translateM(modelMatrix, 0, 0.5f, 0, 0); // 沿 x 轴平移 0.5 个单位
    // Matrix.rotateM(modelMatrix, 0, 90, 0f, 0, 1); // 沿 z 轴旋转 90º
    // Matrix.scaleM(modelMatrix, 0, 0.5f, 1.0f, 0); // x 轴缩放 0.5 倍,y轴不变。注意这里 y 轴如果写 0.0f,就会把 y 轴直接缩放没了(0 倍)
}
  1. Shader 中使用矩阵进行变换:
attribute vec4 a_Position;
uniform mat4 u_Matrix;

void main(){

    gl_Position = u_Matrix * a_Position;
}

申明一个 uniform mat4 的 4x4 矩阵 u_Matrix,按照上面的教程,我们左乘这个矩阵。

  1. onSurfaceCreated() 中获得 u_MatrixGPU
    中的地址,然后在 onDrawFrame() 中使用这个模型矩阵:
uMatrixLocation = glGetUniformLocation(program, U_MATRIX);
...
glUniformMatrix4fv(uMatrixLocation, 1, false, modelMatrix, 0);

上面 glUniformMatrix4fv() 中第一个参数表示数据所要传输到 GPU 中的地址,第二个参数表示需要加载的数据数量(会按照 u_Matrix 类型进行加载),第三个表示内存中数据是列优先(false)还是行优先(true),第四个参数表示要传输到 GPU 中的内存数据,第五个参数表示 modelMatrix 的偏移量。


https://github.com/fightyz/OpenGLPlayground checkout 1fecc7a6cb2ec61fe45ee7e781e6a3cc74dad0a8

相关文章

  • 音视频开发之旅(11) OpenGL ES矩阵变换与坐标系统

    目录 矩阵与矩阵变换 坐标系统 OpenGL的矩阵与矩阵变换 实践:平移、旋转、缩放、3D 资料 收获 一、矩阵与...

  • OpenGL(3) —— OpenGL 的矩阵变换

    基本计算 向量之间的计算有 点积、叉积。矩阵之间的计算有加减、数乘、矩阵间乘法。 矩阵的缩放 位移 旋转 一个向量...

  • OpenGL(五)-- OpenGL中矩阵的变换

    OpenGL(五)-- OpenGL中矩阵的变换 前言 照常提出几个问题,希望通过阅读可以找到答案。 对物体3维的...

  • OpenGL-矩阵压栈出栈浅析

    OpenGL绘制图形需要经过变化才能达到用户目的,而变换是通过矩阵进行操作的。 OpenGL一般通过视图变换、模型...

  • OpenGL 矩阵变换

    视图变换 视图变换是指定观察者的位置,是应用到场景中的第一种变换,它用来确定场景中的有利位置。 在默认情况下,透视...

  • OpenGL--向量和矩阵

    在我们OpenGL中涉及到图形变换的时候经常会运用到向量/矩阵的运算。今天我们就来了解下OpenGL中的向量、矩阵...

  • OpenGL(五)-矩阵变换

    关键函数讲解 平移 旋转 缩放 案例1 : 利用矩阵的平移、旋转、综合变化等, 实现矩阵的移动. 效果图: 注: ...

  • OpenGL 向量 矩阵 变换

    向量 单位向量 标量:只有大小,例如:1,2,3...向量:既有大小又有方向。单位向量:向量长度(向量的模)为1的...

  • OpenGL坐标系与几何变换

    title: OpenGL坐标系date: 2015-3-14tags: OpenGL 坐标系统 想要弄懂几何变换...

  • GL01-10:OpenGL中3D对象控制

    本文主题是3D对象的状态控制(位置,大小,方向),在OpenGL中3D对象的状态控制用矩阵变换实现,但是为了更加精...

网友评论

      本文标题:OpenGL(3) —— OpenGL 的矩阵变换

      本文链接:https://www.haomeiwen.com/subject/rapjthtx.html