PSSM(Parallel Split Shadow Map)平行分割阴影图,是一种根据距离远近采用多个深度纹理渲染阴影的方法

适合用于室外大场景中的平行光比如太阳形成的阴影

本系列需要读者了解基本的深度阴影渲染方面的知识

1 视锥划分

如下图,以采用三个划分为例:

这里将视锥体平行划分为3个区域,代号分别为1、2、3

这三个区域在渲染阴影的时候分别采用不同的阴影图sm1、 sm2、sm3

这样将1、2、3对应的距离数据打包为一个float3变量splits.xyz,传入片段shader,然后通过以下的代码实现阴影图的选择:

if (z <= splits.x)
{
shadow = depthShadow(sm1,...);
}
else if (z <= splits.y)
{
shadow = depthShadow(sm2,...);
}
else if (z <= splits.z)
{
shadow = depthShadow(sm3,...);
}

这里z 、depthShadow函数和单个深度纹理阴影的实现类似,区别是相关参数都变成了三份

图上的三个划分并没有包含全部的渲染区域,因为没有必要渲染特别远的阴影

各个阴影区域的大小可以根据需要选择合理的算法

根据实际情况也可以将阴影区域划分为两个或者更多个

为了平滑 ,最后一级阴影(本例的3)可根据z值做线性淡入淡出

2 投影矩阵计算

渲染阴影前需要分别渲染三个深度纹理

对每一个阴影区域都需要计算对应的正投影矩阵

计算正投影矩阵可以理解为计算正投影相机的位置、投影大小和相机的up矢量

下面以单个投影区域为例说明如何计算这三个要素

如上图,彩色阴影部分为视锥体的单个划分区域

根据当前相机的位置、FOV、纵横比和远近截面距离可以算出该视锥体的八个顶点(这里为了简化仅画出四个)

根据光照方向可以用任一垂直矢量作为投影相机up矢量,不过不同的up矢量得到的投影体大小不同,你可以设计专门的算法计算最优的up矢量

然后再通过光照方向和up矢量的叉积计算出right矢量

任选一参照点(此例为左下的O点),通过up\right矢量和光照方向可以计算出其它7个点在投影相机空间相对于O点的最大、最小值也就是最小包围盒

如图所示,相机的位置应在AB的中点D所在的中心线上,其相对于D点的距离为AC的长度加上阴影可能的投影距离(视锥体外的物体投影)

投影体的长为AB的长度,宽为right方向得到的长度(此图没画出来)

也可以将视锥体的八个顶点直接转到相机空间计算轴对称包围盒、相机位置,然后再将相机位置变换回世界空间

不过当场景很大时,正反两次变换造成的误差会非常的大,直接在世界坐标系内计算则不会有这种问题

实时阴影渲染(一):PSSM平行分割阴影图的更多相关文章

  1. Unity3D手游开发日记(1) - 移动平台实时阴影方案

    阴影这个东西,说来就话长了,很多年前人们就开始研究出各种阴影技术,但都存在各种瑕疵和问题,直到近几年出现了PSSM,也就是CE3的CSM,阴影技术才算有个比较完美的解决方案.Unity自带的实时阴影, ...

  2. Unity局部高效实时阴影的思考和实现

    http://game.ceeger.com/forum/read.php?tid=23305&fid=2 无意间看到一篇文章,说是Unity5 demo中为了实现角色的良好阴影,单独给角色设 ...

  3. .NET实时2D渲染入门·动态时钟

    .NET实时2D渲染入门·动态时钟 从小以来"坦克大战"."魂斗罗"等游戏总令我魂牵梦绕.这些游戏的基础就是2D实时渲染,以前没意识,直到后来找到了Direct ...

  4. 【实时渲染】实时3D渲染如何加速汽车线上体验应用推广

    在过去,一支优秀的广告片足以让消费者对一辆汽车产生兴趣.完美的底盘线条或引擎的轰鸣声便会让潜在买家跑到经销商那里试驾.现在,广告还是和往常一样,并没有失去其特性,但86%的买家在与销售交流之前会在网上 ...

  5. (转)阴影锥(Shadow Volume)

    转自:http://blog.csdn.net/zjull/article/details/11819923 Shadow Map和Shadow Volume是当今比较流行的实时阴影渲染方法,跟Sha ...

  6. Unity Shader 卡通渲染 基于退化四边形的实时描边

    从csdn转移过来,顺便把写过的文章改写一下转过来. 一.边缘检测算法 3D模型描边有两种方式,一种是基于图像,即在所有3D模型渲染完成一张图片后,对这张图片进行边缘检测,最后得出描边效果.一种是基于 ...

  7. Shadow Map阴影贴图技术之探 【转】

    这两天勉勉强强把一个shadowmap的demo做出来了.参考资料多,苦头可不少.Shadow Map技术是目前与Shadow Volume技术并行的传统阴影渲染技术,而且在游戏领域可谓占很大优势.本 ...

  8. 剖析虚幻渲染体系(14)- 延展篇:现代渲染引擎演变史Part 1(萌芽期)

    目录 14.1 本篇概述 14.1.1 游戏引擎简介 14.1.2 游戏引擎模块 14.1.3 游戏引擎列表 14.1.3.1 Unreal Engine 14.1.3.2 Unity 14.1.3. ...

  9. Introduction to 3D Game Programming with DirectX 12 学习笔记之 --- 第二十章:阴影贴图

    原文:Introduction to 3D Game Programming with DirectX 12 学习笔记之 --- 第二十章:阴影贴图 本章介绍一种在游戏和应用中,模拟动态阴影的基本阴影 ...

随机推荐

  1. $_SERVER 相关变量

    PHP编程中经常需要用到一些服务器的一些资料,特把$_SERVER的详细参数整理下,方便以后使用. $_SERVER['PHP_SELF'] #当前正在执行脚本的文件名,与 document root ...

  2. JAVA获取当前时间加一天

    01.获取当前时间 SimpleDateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); return df.for ...

  3. 剑指offer系列27--表示数值的字符串

    [题目]请实现一个函数用来判断字符串是否表示数值(包括整数和小数). 例如,字符串”+100”,”5e2”,”-123”,”3.1416”和”-1E-16”都表示数值. 但是”12e”,”1a3.14 ...

  4. php 查询出来的字段名全是小写或者大写

    PHP PDO预定义常量 PDO::CASE_LOWER -- 强制列名是小写PDO::CASE_NATURAL -- 列名按照原始的方式PDO::CASE_UPPER -- 强制列名为大写 修改此参 ...

  5. 7. redis优化

    一. redis使用上的优化 精简键名和键值 键名:尽量精简,但是也不能单纯为了节约空间而使用不易理解的键名. 键值:对于键值的数量固定的话可以使用0和1这样的数字来表示,(例如:male/femal ...

  6. System.InvalidOperationException: Sequence contains no elements

    foreach (var keyCode in unexpectedKeyCodesDetected) { string unexpected = expectedCapturedKeyCodes.W ...

  7. [CSS]理解line-height

    字面意思 "行高"顾名思意指一行文字的高度.具体来说是指两行文字间基线之间的距离.基线实在英文字母中用到的一个概念,我们刚学英语的时使用的那个英语本子每行有四条线,其中底部第二条线 ...

  8. DBA_Oracle Erp重启Database/Application/Concurrent/Apache(案例)

    2014-12-27 Created By BaoXinjian

  9. UVA116 单向 DSP(多段图最短路)

    单向 DSP [题目链接]单向 DSP [题目类型]dp &题解: 紫书P271 这块的字典序排序我觉得挺厉害的,每次都把那3步sort一下,之后if (v< d[i][j]) 这块的小 ...

  10. git的使用(3) 多分支情况下的pull

    当你存在多个分支的时候,你需要pull下来分支上面的内容,你需要指定分支进行同步命令: git pull origin branch (branch 是你的分支的名字)