在学习D3D11的时候遇到一个问题,事情是这样的:


D3D11引入了常量缓存(const buffer)用来实现

B0%E6%8D%AE">数据的高速传输,这块儿buffer是CPU Only Write,GPU Only Read这样的特点,其他还是D3D9的惯例。在我调用完g_pD3DImmediateContext->Map的时候,出现了没有任何图像的问题,后经过改造后,显示终于正常了,先上代码:

 // 传入shader前,确保矩阵转置,这是D3D11的要求
 pMatrix->m_mxWorld  	= XMMatrixTranspose(pMatrix->m_mxWorld);
 pMatrix->m_mxPorjection = XMMatrixTranspose(pMatrix->m_mxPorjection);
 pMatrix->m_mxView   = XMMatrixTranspose(pMatrix->m_mxView);
 //把基本的3个3D变换矩阵放进显存去,当然对于GPU来说它是只读的,而CPU是只写的
 D3D11_MAPPED_SUBRESOURCE MappedResource = {};
 // 将矩阵缓冲的显存映射进来,设置矩阵数据先
 HRESULT hr = g_pD3DImmediateContext->Map(g_pMatrixBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &MappedResource);

 CopyMemory(MappedResource.pData,pMatrix,sizeof(ST_MATRIXBUFFER));
 g_pD3DImmediateContext->Unmap(g_pMatrixBuffer, 0);
 g_pD3DImmediateContext->VSSetConstantBuffers(0, 1, &g_pMatrixBuffer);

可以看到,pMatrix->m_mxWorld  ,pMatrix->m_mxPorjection ,pMatrix->m_mxView  三个矩阵都是在进行了转置之后才传入常量缓存的,之后画面显示正常了。为何要转置呢?经过一番打探原来事情是这个样子的:


首先我们要知道,矩阵分为行主序和列主序两种矩阵,比如:内存中使用一个二维数组m存储矩阵,第i行第j列的表示方法分别为:


行主序:m[i][j]


列主序:m[j][i]


线性代数意义的同一个矩阵,在D3D 和OpenGL 中的存储顺序:


线代:a11,a12,a13,a14


a21,a22,a23,a24


a31,a32,a33,a34


a41,a42,a43,a44


D3D :  a11,a12,a13,a14


a21,a22,a23,a24


a31,a32,a33,a34


a41,a42,a43,a44


OpenGL: a11,a21,a31,a41


a12,a22,a32,a42


a13,a23,a33,a43


a14,a24,a34,a44


D3D是左手定则,OpenGL是右手定则,另外提一句,OGRE用的也是列主序,我们发现只要把行主序和列主序的行列对调就可以了,也就是转置一下就一样了,也就是说D3D和OpenGL如果想转换的话只需要转置一下就ok,那D3D11这里为什么要转置呢,因为D3D11的constant buffer里面shader读取是列主序的读取,所以想在const buffer使用的话还是要转换成列主序,或者也可以编译shader的时候调用D3D10_SHADER_PACK_MATRIX_ROW_MAJOR这个来编译,其实效果是一样的,只不过转换做在了内部,其实早在D3D11之前GPU也是一直读取列主序的矩阵的,只不过转换在D3D驱动内部进行了而已。


或者还有一种方法就是声明这个矩阵的时候直接声明为列主序的矩阵:row_major。


还有一个方法就是在shader里面mul矩阵的时候用矩阵在前,向量在后的方法也可以:


float4 transformedPosition = somePosition * someMatrix;
        float4 transformedPosition = someMatrix * somePosition;


另外还要注意const buffer的desc权限 是 cpu only write &gpu only read。

为何D3D11的几个矩阵需要转置?的更多相关文章

  1. C语言 矩阵的转置及矩阵的乘法

    C语言 矩阵的转置及矩阵的乘法 //凯鲁嘎吉 - 博客园 http://www.cnblogs.com/kailugaji/ 1.矩阵的转置 #include<stdio.h> #defi ...

  2. C语言两种方式实现矩阵的转置

    #include"stdio.h" typedef struct{ int i,j; int v; }Triple; typedef struct{ Triple date[]; ...

  3. 关于python中矩阵的实现和矩阵的转置

    python中矩阵的实现是靠序列,,, 序列有很多形式, 其实矩阵是现实生活中的东西,把现实生活中的结构转换到程序中. 就需要有个实现的方法,而这种路径是多种多样的. 下面给出一个把矩阵转换成pyth ...

  4. C++写矩阵的转置

    (2019年2月19日注:这篇文章原先发在自己github那边的博客,时间是2017年2月5日) 对于任意非n阶矩阵的转置,用c++应该怎么写代码,思考了一下,发现并没有那么简单,上网找到了一个比较好 ...

  5. C语言-实现矩阵的转置-随机函数产生随机数并赋予数组中-190222

    //编写程序,实现矩阵的转置(行列互换). #include <stdio.h> #include <conio.h> #include <stdlib.h> ][ ...

  6. c++数组-矩阵的转置

    #include <iostream> using namespace std; int main(){ ][]={{,,},{,,}}; ][]; ;j<;j++){ ;i< ...

  7. <矩阵的基本操作:矩阵相加,矩阵相乘,矩阵转置>

    //矩阵的基本操作:矩阵相加,矩阵相乘,矩阵转置 #include<stdio.h> #include<stdlib.h> #define M 2 #define N 3 #d ...

  8. [置顶] [MATLAB技术贴]漫谈MATLAB矩阵转置

    矩阵转置是matlab最基本的操作了,但这个基本操作,也是很多初学者容易出现问题的地方.本帖通过几个实例演示matlab矩阵转置的操作. 方法一:'  运算符与  .'  运算符 >>a ...

  9. 矩阵转置 O(1)空间

    题目:用O(1)的空间实现矩阵的转置 为了方便,使用一维数组来分析.所谓矩阵转置,行变列,列变行.在转置的过程中,有的元素位置是不变的:对于变化位置的元素,要求O(1)空间完成,那么这些位置的变化一定 ...

随机推荐

  1. qbao

    # -*- coding: utf-8 -*- import Image, cStringIO, webbrowser, re, time, math import urllib, urllib2, ...

  2. photoshop正确的打开方式

    首先这边我先贴一个地址:https://www.adobe.com/cn/products/photoshop.html 安装软件,这里就不赘述了,真的不会,可以百度^_^我当初就是百度的,哈哈 说到 ...

  3. lower_bounder()和upper_bound()的函数

    lower_bound() .upper_bound()都运用于有序区间的二分查找. ForwardIter lower_bound(ForwardIter first, ForwardIter la ...

  4. SaaS加速器 I 商业中心:提供商业助力 共享商业成功

    摘要: 商业中心:通过阿里商业生态(如阿里云市场.钉钉市场.淘宝市场.B2B等)帮助合作伙伴实现商业变现和闭环, 思考:今天我们一起换个视角,从平台的角度考虑如何去构建生态,如何制定平台的规则以及如何 ...

  5. Charles配置信息

    1.下载Charles https://www.charlesproxy.com/download/ 2.破解 https://www.zzzmode.com/mytools/charles/ 或者 ...

  6. 用select提取List元素自身序号

    var cs = currentCitys.Select((c, i) => new { id = c.CITY_ID, 序号 = (i + 1).ToString(), 城市类型 = c.IS ...

  7. 【批量添加】-SqlBulkCopy语句 标签: sql批量添加 2015-12-20 14:39 1367人阅读 评论(33)

    上篇博客我们介绍了通过拼接sql字符串的方法来对sql数据库进行批量添加,但是通过语句拼接insert语句有个缺点,就是每次最多只能添加1000条.当时我们另外一个界面也用到了批量添加,但是这个界面轻 ...

  8. MySQL性能分析, mysql explain执行计划详解

    MySQL性能分析 MySQL性能分析及explain用法的知识是本文我们主要要介绍的内容,接下来就让我们通过一些实际的例子来介绍这一过程,希望能够对您有所帮助. 1.使用explain语句去查看分析 ...

  9. @loj - 2483@「CEOI2017」Building Bridges

    目录 @desription@ @solution@ @accepted code@ @details@ @another solution@ @another code@ @desription@ ...

  10. laravel框架手机发送验证码

    https://blog.csdn.net/sunny_lg/article/details/52471225 现在登录注册时 我们的验证方法 不在单一化  手机发送验证码 已经成为常态 让我们 一起 ...