Shader的学习方法总结
最近网友candycat1992的新书《Unity Shader入门精要》出版了,估计万千的中国unity开发者又要掀起一波学Shader热潮了。我也想把自己这几年学习Shader的一些历程和心得记录下来。一来当给自己的学习做个记录,二来是给更多的后来人留些参考。
写之前先声明几点:
1. 本文标题中的Shader并不特指Unity Shader,本文也不涉及任何代码细节,仅是讨论学习方法。
2. 图形技术的水很深,我还只是个小学生,只是单纯的分享自己的学习历程,大神看到了别见怪。
3. 每个人的性格,思想都不一样,所以学习方法这种东西向来不是照搬照抄的,所以我说的不一定适合你,还需要自己取舍。
个人历程
容我讲讲自己学习Shader的经历,你会发现,入门并没有那么难,只要你肯下功夫。
毕业后的第一份工作就是从事Unity客户端开发,当然了作为新人也就是写写UI,作作逻辑。恰巧当时项目的一个同事W君有Shader的经验,就每周都挑两天下班后的时间给我们上课,从最开始的矩阵变换到他离职前最后一课辉光效果。因为大学里的图形学课基本上也没怎么太认真(现在很后悔呀)。也就是这大概十几节课,让我对图形渲染有了最初的认识。就从这段时间开始,我断断续续的开始了学习Shader的路。那时候国内还没有一本专门讲UnityShader的书。而我对图形渲染的认识也是很肤浅的,只能去网上找资料,看代码例子,问同事,恰巧我有一个同事Y君,是学图形的研究生毕业,所以很多事情都可以向他请教,所以他也算是我在这方面的老师了。也是他推荐我看的《GPU编程与CG语言之阳春白雪下里巴人》,以及《Cg教程_可编程实时图形权威指南》(后来第二本书我还想尽了办法弄到一本正版实体书收藏了)。就是这两本书,还有网上那些我已经忘却名字的很多前辈的分享,我开始一点一点的去了解Shader,了解图形渲染,渐渐的也就成了我的一个兴趣点。
到了第二年,工作上得心应手一些,我就花更多的业余时间在Shader上,一个问题想不明白就不停的想,直到能说服自己为止,也差不多就是那段时间郭浩瑜的那本《Unity 3D ShaderLab开发实战详解》出版了,要知道当初我和Y君可是每天都在关注出版进度,托了大半年终于出了,赶紧买来看。这本书现在看来别的不说,至少布局结构是极其不合理的,相当不适合新人,该详不详,该略不略。很多地方代码一扔,也不解释。不过,话说回来,因为我这人学东西如果一个地方看不懂就得想办法搞懂,所以这本书也让我知道了很多。这时候我也开始在Blog上写了第一篇Shader教程(2014年2月份,其实那时候自己也刚刚入门)。就这样边写边学,渐渐到隐藏在unityShader背后的图形渲染世界,不断的读书,写作,练习,我几乎是没有在项目里实际写Shader的,因为一般由Y君负责,但基本上所有的Shader我都会看,然后不理解的就要和Y君讨论弄明白。这样发现那段时间自己成长很快,尤其是写Blog,因为你要写给别人看,要讲的通俗易懂,还要剖析原理,写的每一句话都要负责,所以一定要搞懂。这期间还读了刘鹏翻译韩国人写的《计算机图形学-基于3D图形开发技术》,这本书其实很早就读过,那时候实在是水平不够,看不懂还怨人家翻译差,后来再看了解了不少东西。
大概一年前,很巧合有一个机会来到了现在的公司进行了游戏引擎的开发。换工作之前也是想了很多,自己的图形渲染知识都是工作后自学的,之前两年的工作基本都是做Unity的逻辑开发工作,而且写引擎要用C++。当时还有很多机会,继续做Unity的开发工作,但还是横下心来做引擎,因为这是我这几年一直的想法,不论怎么样,有这机会就抓住,即使发现自己不适合,也会是一段很好的锻炼经历。笔试面试最后也过了。也算是对自己之前两年默默努力的一个回馈吧。
做引擎开发者一年以来,得以有机会近距离看到游戏引擎的原理,对OGL也有了更好的了解。也知道了所有的游戏引擎核心原理没什么大的不同。但这一年来,由于没有再接触Unity,所以blog里的Shader教程长期没有更新。最近又打算重新开写了。因为渲染这东西重要的是原理和引擎是无关的。有时间我会继续更新。
好吧,啰嗦了这么长(谁爱听啊!)。下面进入正题:
正确的理解Shader
很多人对Shader的理解都不同,特别是初学者,往往对Shader的认知是很肤浅的。大都认为Shader就是UnityShader,就是Unity引擎里一个用来创造画面效果的一种文件格式。
这也是我当初刚接触Shader的时候的认知。这当然是一叶障目,不见泰山了。如果要学好Shader,用好Shader,就不能只停留在了解和使用UnityShaderLab的语法的层次。这是远远不够的,因为当你深入学习的时候你就会发现,由于你不理解Unity为你提供的某一个ShaderLab参数的具体原理,导致你也不能正常使用,即使是可以使用也不能举一反三。
当然作为一个初学者,认知上的缺陷是难免的,但希望你在看到了这篇文章后,能看的更深远一些。Shader不只是指Unity的ShaderLab,也并不代表图形渲染的全部,它只是渲染流程上的一环,或者说是关键的一环。是很多很多步骤的结合作用才最终把画面正确的呈现出来。如果你真的想吃透Shader,用好Shader,这些东西都是你要去掌握理解的。那些渲染管线流程图什么的我就不拿过来粘贴了,本文只做学习方法总结,不讨论具体技术。
综上,饭要一口一口吃,知识也肯定是一点一点学,循序渐进持之以恒,但如果一开始就能比较全面和整体的理解Shader的定位,那么也会在学习过程中,也就不会太自以为是,学的太肤浅。
如何起步
其实现在比几年前好多了,有了不少资源,很多热心网友写的教程,也有几本还能看的书。
我还是谈谈我的建议,首先找个游戏引擎(当然你也可以不用引擎直接自己写OGL或DX),一本合适的书。unity当然是现在最容易上手的了,书的话用来入门了解的有几本是我觉得可以看的,但适不适合要看你自己了:
1. 《GPU编程与CG语言之阳春白雪下里巴人》,严格说这不是一本书,是网上盛传的新人学习的必读物。
2. 《Cg Programming in Unity》,这是Wiki上的一系列UnityShader教程,不过现在可能需要FQ看了。
3. 《Cg教程_可编程实时图形权威指南》,因为Unity的Shader大部分还是用CG语言来写的,这本书虽然年代有点早,但还是值得一看的,而且Nvidia的网站上有最最新的英文版。
4. 《Unity Shader入门精要》candycat1992,小姑娘这本书绝对的值得一看的,虽然是面向入门级的,但是里面涉及了很多底层的,原理的性的内容。国内Unity书总算有本值得买的了。
别问我为啥不推荐那本《Unity 3D ShaderLab开发实战详解》,前面已经说了。
有了书,打开引擎开始学,你需要的就是耐心和恒心了,我想学其他的知识也是一样吧。Shader的水很深,做好打持久战的准备,不断的练习,不断的尝试,不断的总结。
在学习过程中遇到问题是必然的,合理的使用搜索引擎,去论坛和站点和大家交流。保持一颗谦卑的心,别人总有比你强的地方,虚心的学习,慢慢的积累。如果你身边有一个可以请教的人,那就太好。就像我遇到Y君一样。
当你觉得自己入了一点门以后,就可以尝试着分析项目里的Shader代码了,结合着游戏中的实际效果,看看代码里用到了哪些你不知道的技术,或者说有什么你觉得不合理的地方。如果有机会,就尝试着申请在项目里实际写Shader的工作。这样的锻炼是难得的。可惜我当初做Unity时候没有这样的机会。
起步的一开始一定会是有些无从下手的感觉,度过这段时间,找到适合自己的节奏,就会有个很快速的学习积累过程。要坚持。
如何提高
刚接触Shader时候会有个迷茫期,其实当你学了一段时间,感觉自己学到了很多东西以后,也会有个迷茫期,不知道怎么进一步的提高自己,感觉自己该掌握的都已经掌握了,但是又写不出什么东西。
正如我在前面说的,我们总觉得自己好像该学的都学了,又感觉哪里好像没吃透。这说明我们还是没有触碰到我们学习内容的全貌,才只看到整个知识体系的冰山一角。所以一定会经历这个从觉得自己什么都会了,到感觉自己什么都不会了的转变。这个转变是必要的,它意味着你将了解到更深更广的知识。
废话不说了,一般我们入了门以后还要去理解更多的知识,我总结一下,大概有几方面:
1. 首先要对渲染管线有个透彻的了解,至少要知道每一步发生了什么。很多学Unity从业者说会Shader也就只停留在前面那个语法层次了。如果连渲染管线都不知道,就不要再往简历写会Shader了。这方面的资料很多,candyCat1992那本书以及《计算机图形学-基于3D图形开发技术》都有,还有Trace大神搬运过来的一套教程。了解渲染管线,能让你对Shader里的很多用法都能有更深入的认识。
2. 去学习OpenGL或者DirectX的知识(如果你经历足够可以双管齐下),看好,不是说HLSL或者GLSL这些Shader语法,而是OGL和DX。了解了渲染管线之后,再去了解一下图形API,试着动手写写,你才能真正的理解渲染管线的实际流程,以及那些被游戏引擎所隐藏起来的渲染逻辑。你也就能了解到Unity中的FBX模型里到底都放了什么数据,场景模型上的MeshFilter组件和MeshRenderer组件都是起什么作用的,等等。对这些图形API有了一定的掌握,不仅可以对渲染流程有更深入的了解,甚至可以自己开发一个简单的渲染引擎了。这方面的学习资料就太多了,学OGL就是红宝书,DX的话自然就是龙书。
3. 再有很重要的一块就是图形算法,想要在通过Shader做出各种惊艳或者特殊的渲染效果,可不是只学会写Shader语法就可以做到的,就像大学里学程序设计后还要学习算法是一样的,图形渲染中也有大量的算法,从最基础的光照算法,到HDR,FXAA,Toon。再到最近次时代流行的PBR等等。有很多已经很成熟的算法,但这些算法不一定完全适合你的项目或者平台,所以必须了解他们改进它们,甚至研究出新的算法。这个过程估计是最痛苦的了,因为国内的资料不多,讨论的人也不多,算法中往往还涉及到大量的数学和物理知识。如果能持续不断的坚持学习和实践,那你也许就会是万千游戏开发大军中的的佼佼者。这方面的书虽然不多,基础类的我就不说了,很多书上都有,有一些大部头的经典如:《GPU Gems》系列,《Real-Time Rendering》,《Physically Based Rendering》。国内能读完这些书的人应该是是很少的。我自己还不到这个层次,不过也准备要开始塌下心来学习。还有一个论坛OpenGPU,也推荐给大家,不过这个不是入门向的,里面的大神太多了,不要在里面提太没营养的问题,会被鄙视的。
4. 补补数学再学点物理知识吧。线性代数的重要性就不用我说了,如果能力和精力允许的话,就多补一补,我这数学渣就不多说话了,不过我也有时间会学一学的。这方面也有一些好的资料。我手头就有一本《Mathematics for 3D Game Programming and Computer Graphics》。这个我就不多说了,没事多学学,省着用到了挠头。
...
其实还有很多,比如把C++好好学一学,不过已经不要紧了,路很长,要怎么走还是要靠你自己。我也只是个一定意义上的入门者,不想误导别人。大家一起提高,互相帮助吧。
最后几句心里话
其实无论别人看别人多少文章,多少教程,多少书,学习的路上往往都是没有捷径的,总要经历些坎坷和挫折。否则牛人怎么才是牛人呢,自己这几年的学习历程也是经历了很多,写这篇文章并不是能给大家提供什么捷径和速成法,只是给大家些勇气,希望大家少一些磕磕绊绊。像我这样的都能入个门,大家也一定可以的。
也希望大家,能乐于分享,让大环境更成熟起来,也希望能涌现更多的牛人。
尊重他人智慧成果,欢迎转载,请注明作者esfog,原文地址http://www.cnblogs.com/Esfog/p/5537624.html
Shader的学习方法总结的更多相关文章
- Shader
Shader的学习方法总结 http://www.cnblogs.com/Esfog/p/How_To_Learn_Shader.html [Shader 着色器]学习shader之前必须知道的东西之 ...
- 学习游戏渲染(Shader)的用处
本文在讨论的主题并不限于具体引擎或具体语言,为了说明方便可能会提到Unity的一些内容. 最近渐渐发现很多从事游戏开发的新人,对于学会写Shader似乎总是有几分神往,但一般入了门或者学了一段时间后 ...
- Unity3D教程宝典之Shader篇
教程目录 基础讲:Shader学习方法基础讲:基础知识特别讲:常见问题解答特别讲:CG函数 第一讲: Shader总篇第二讲: Fixed Function Shader 第三讲: Vertex&am ...
- OpenGL shader 中关于顶点坐标值的思考
今天工作中需要做一个事情: 在shader内部做一些空间距离上的计算,而且需要对所有的点进行计算,符合条件的显示,不符合条件的点不显示. 思路很简单,在vertex shader内知道顶点坐标,进行计 ...
- CSharpGL(14)用geometry shader渲染模型的法线(normal)
+BIT祝威+悄悄在此留下版了个权的信息说: CSharpGL(14)用geometry shader渲染模型的法线(normal) +BIT祝威+悄悄在此留下版了个权的信息说: 2016-08-13 ...
- 【译】Unity3D Shader 新手教程(6/6) —— 更好的卡通Shader
本文为翻译,附上原文链接. 转载请注明出处--polobymulberry-博客园. 动机 如果你想了解以下几件事,我建议你阅读以下这篇教程: 想知道如何写一个multipass的toon shade ...
- 【译】Unity3D Shader 新手教程(5/6) —— Bumped Diffuse Shader
本文为翻译,附上原文链接. 转载请注明出处--polobymulberry-博客园. 动机 如果你满足以下条件,我建议你阅读这篇教程: 你想学习片段着色器(Fragment Shader). 你想实现 ...
- 【译】Unity3D Shader 新手教程(4/6) —— 卡通shader(入门版)
本文为翻译,附上原文链接. 转载请注明出处--polobymulberry-博客园. 暗黑系 动机 如果你满足以下条件,我建议你阅读这篇教程: 你想了解更多有关表面着色器的细节知识. 你想实现一个入门 ...
- 【译】Unity3D Shader 新手教程(3/6) —— 更加真实的积雪
本文为翻译,附上原文链接. 转载请注明出处--polobymulberry-博客园. 如果你满足以下条件,我建议你阅读这篇教程: 你想知道如何在表面着色器中进行混色(blend colour) 你想实 ...
随机推荐
- 烂泥:Postfix邮件服务器搭建之软件安装与配置
本文由ilanniweb提供友情赞助,首发于烂泥行天下 想要获得更多的文章,可以关注我的微信ilanniweb Postfix邮件服务器的搭建需要使用到几个软件,分别是cyrus-sasl.postf ...
- C++ 用宏实现swap(a,b)
#include <iostream> using namespace std; #define SWAP(a,b) a^=b,b^=a,a^=b int main(void){ int ...
- spark streaming kafka example
// scalastyle:off println package org.apache.spark.examples.streaming import kafka.serializer.String ...
- [麦先生]TP3.2之微信开发那点事[基础篇](获取access_token)
在微信文档中一共提供了两个access_token:一个是伪全局配置的Access_token;一个是在微信网页授权时的小Access_token 很多刚刚接触微信开发的人经常会混淆这两个的作用: 我 ...
- Node webkit启动最大化窗口
<!DOCTYPE html> <html> <head> </head> <body> <p style=" ...
- .net Global.asax文件使用
一.Application_start: 第一个访问网站的用户会触发该方法. 通常会在该方法里定义一些系统变量,如聊天室的在线总人数统计,历史访问人数统计的初始化等等均可在这里定义. Applicat ...
- vijos P1780 【NOIP2012】 开车旅行
描述 小\(A\)和小\(B\)决定利用假期外出旅行,他们将想去的城市从\(1\)到\(N\)编号,且编号较小的城市在编号较大的城市的西边,已知各个城市的海拔高度互不相同,记城市\(i\)的海拔高度为 ...
- 【转】【C#】迭代器
迭代器模式是设计模式中行为模式(behavioral pattern)的一个例子,他是一种简化对象间通讯的模式,也是一种非常容易理解和使用的模式.简单来说,迭代器模式使得你能够获取到序列中的所有元素而 ...
- ASP.NET(C#) Web Api通过文件流下载文件到本地实例
下载文件到本地是很多项目开发中需要实现的一个很简单的功能.说简单,是从具体的代码实现上来说的,.NET的文件下载方式有很多种,本示例给大家介绍的是ASP.NET Web Api方式返回HttpResp ...
- QString, string, int, char* 之间相互转换
这三种数据类型在实际运用中经常需要互相转换,那么这里小结下它们之间的转换方法: - Qstring & string Qt中封装的类十分强大,其成员函数数量之多比STD有过之而无不及,许多程序 ...