threejs添加立方体_前端图形学(三十)——从源码去看threejs中的光照模型
歡迎來(lái)到【暢哥聊技術(shù)】前端圖形學(xué)相關(guān)技術(shù)文章,更多精彩內(nèi)容持續(xù)更新中,敬請(qǐng)關(guān)注。
上章節(jié)回顧
本章目標(biāo)
上一小節(jié)我們實(shí)現(xiàn)了一個(gè)自定義的兩個(gè)三角面,如下圖。
但是,大家很容易看出來(lái),兩個(gè)三角面之間相鄰的地方?jīng)]有棱角的感覺(jué),所有的都是一個(gè)顏色。如果沒(méi)有輔助線,仿佛看不出來(lái)是一個(gè)3d圖形。
這是什么原因呢?可能有人會(huì)說(shuō),因?yàn)槲覜](méi)有添加點(diǎn)光源,額,說(shuō)對(duì)了一半。如果我們單純的在場(chǎng)景中添加一個(gè)點(diǎn)光源,也是沒(méi)有效果的。因?yàn)檫€缺少一個(gè) ... 平面法向量
什么鬼....
法向量
什么是法向量?拿立方體來(lái)舉例。我們知道,它有六個(gè)平面。繪制需要12個(gè)三角形,36個(gè)頂點(diǎn)(這時(shí)不談頂點(diǎn)的復(fù)用)。
這里插一句,webgl中繪制平面的最小單位是三角形(三角面),那為什么不是矩形面呢?原因是在三維空間中,只有三個(gè)不同位置的點(diǎn),才能確定一個(gè)唯一的平面。所以在原生的webgl中,gl.drawArrays(gl.Lines)來(lái)是線條繪制,gl.TRIANGLE_FAN模式來(lái)繪制填充的平面。
回到正題,立方體6個(gè)面,那么每一個(gè)面的法向量就是垂直每個(gè)平面的向量。
比如上圖中的立方體的右面的法向量就是(1,0,0)
那么向量有什么用呢??那么就不得不得到光照了。
光照模型
光照照在物體上,正常來(lái)說(shuō)是有漫反射的。具體的可參考我之前寫的文章原生webgl中的光照 那么光照會(huì)和物體之間有一個(gè)入射角,這個(gè)入射角就是光照和平面的法向量的夾角。
搞清楚了法向量的概念,我們?cè)賮?lái)聊聊光照原理,前面的原生webgl光照原理中我有說(shuō)到,光打到物體表面后,我們看到的顏色并不是都是相同的,這時(shí)候我們就需要根據(jù)入射角度來(lái)計(jì)算反射后的顏色。
前面我們單純一個(gè)計(jì)算方式是將光的顏色*物體的顏色*入射角的余弦值,得到一個(gè)簡(jiǎn)單的光照模型。
那問(wèn)題又來(lái)了,那為什么我們?cè)趧?chuàng)建內(nèi)置的幾何圖形的時(shí)候沒(méi)有讓我們創(chuàng)建法向量呢,甚至都沒(méi)說(shuō)~
帶著這個(gè)問(wèn)題,我們?cè)偃ヌ揭幌铝⒎襟w的創(chuàng)建過(guò)程,看它內(nèi)部到底幫我們做了什么。
找到BoxBufferGeometry類的定義,截圖。
這兩個(gè)截圖足以說(shuō)明,和頂點(diǎn)數(shù)據(jù)一樣,threejs在創(chuàng)建內(nèi)置幾何體的時(shí)候,已經(jīng)根據(jù)我們傳遞進(jìn)去的參數(shù)生成了對(duì)應(yīng)的法向量~
多么痛的領(lǐng)悟,如果不看源碼,咋能知道這些??
接下來(lái)我們來(lái)加入法向量改造一下上面的示例:
創(chuàng)建法向量
將法向量數(shù)據(jù)傳遞給空的幾何圖形的法向量屬性
這樣幾何圖形的表面的顏色就不再是單一的了,我們可以很清楚的看到兩個(gè)三角面相鄰位置的棱角,背面沒(méi)有光的反射。
舉一反三
我們?cè)趖hreejs中,幾乎很少看到有需要我們?nèi)懼鞯牡胤?#xff0c;而我們好像也沒(méi)有看到過(guò)有著色器語(yǔ)言的地方。那么接下來(lái)我借著光照模型去找在threejs中光照模型的算法公式吧~
了解過(guò)原生的webgl的都知道,著色器語(yǔ)言需要webgl Api 去編譯然后到GPU中執(zhí)行,那我們就從渲染器的源碼中開始下手。
找了半天,我終于找到了一個(gè)方法initMaterial() //初始化材質(zhì),繼續(xù)往下走、
一眼就看到了ShaderLib這個(gè)對(duì)象,從字面上理解,它是一個(gè)著色器的類庫(kù),好,我們進(jìn)去看下。
好高興,看我發(fā)現(xiàn)了什么?
我們的示例中用到的材質(zhì),下面的是材質(zhì)對(duì)應(yīng)的頂點(diǎn)著色器和片元著色器,繼續(xù)深入ShaderChunk對(duì)象去找 ,這里我們要看材質(zhì)和光照的反應(yīng),所以我們找對(duì)應(yīng)的片元著色器
fragmentShader: ShaderChunk.meshlambert_frag終于找到他了 ./ShaderLib/meshlambert_frag.glsl.js,我們?nèi)ゴ蜷_這個(gè)文件。
這個(gè)js文件的源碼全是著色器語(yǔ)言,有相關(guān)基礎(chǔ)的應(yīng)該可以看個(gè)大概,來(lái)看我圈出來(lái)的部分,就是用來(lái)計(jì)算光照和材質(zhì)的反射后的光照,很明顯,這和我之前提供的光照算法差別很大了。
這些我也是完全看不懂,我們只需要知道,webgl中的光照原理其實(shí)就是物體和光源顏色經(jīng)過(guò)一定的算法得到就行了~
總結(jié):
1、通過(guò)webgl中光照引出了法向量的概念, 法向量垂直于平面
2、接入法向量改造我們的示例、產(chǎn)生真實(shí)的光照反應(yīng)
3、通過(guò)分析源碼知道,內(nèi)置的幾何圖形已經(jīng)幫我們?cè)O(shè)置好了法向量,自定義的圖形需要我們手動(dòng)添加
4、通過(guò)歸類,我們知道,頂點(diǎn)具有頂點(diǎn)的位置position,頂點(diǎn)的顏色color和頂點(diǎn)的法向量nomarl
5、webgl Api編譯著色器然后在GPU中執(zhí)行(原生webgl的知識(shí)點(diǎn))
6、一步步深入threejs中的光照和材質(zhì)的相互反應(yīng)在片元著色器中的基本算法
以上是今天所有的分享內(nèi)容。喜歡的請(qǐng)點(diǎn)贊關(guān)注,不喜歡的解散。。。
這里是【暢哥聊技術(shù)】前端圖形學(xué)相關(guān)技術(shù)文章,更多精彩內(nèi)容持續(xù)更新中。。。
未完待續(xù)。。。
總結(jié)
以上是生活随笔為你收集整理的threejs添加立方体_前端图形学(三十)——从源码去看threejs中的光照模型的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: 字典删除多个键值对方法_Life is
- 下一篇: html语言填充没有只有描边,HTML5