『壹』 android OpenGLES2.0(十六)——3D模型貼圖及光照處理(obj+mtl)
在Android OpenGLES2.0(十四)——Obj格式3D模型載入中實現了Obj格式的3D模型的載入,載入的是一個沒有貼圖,沒有光照處理的帽子,為了呈現出立體效果,「手動」加了光照,擁有貼圖的紋理及光照又該怎麼載入呢?
本篇博客例子中載入的是一個卡通形象皮卡丘,資源是在網上隨便找的一個。載入出來如圖所示:
obj內容格式如下:
mtl文件內容格式如下:
關於Obj的內容格式,在上篇博客中已經做了總結,本篇博客中使用的obj,可以看到f後面的不再跟的是4個數字,而是 f 2/58/58 3/59/59 17/60/60 這種樣子的三組數,每一組都表示為頂點坐標索引/貼圖坐標點索引/頂點法線索引,三個頂點組成一個三角形。而頭部的 mtllib pikachu.mtl 則指明使用的材質庫。
而mtl格式文件中,主要數據類型為:
模型載入和之前的模型載入大同小異,不同的是,這次我們需要將模型的貼圖坐標、頂點法線也一起載入,並傳入到shader中。其他參數,有的自然也要取到。
模型載入以obj文件為入口,解析obj文件,從中獲取到mtl文件相對路徑,然後解析mtl文件。將材質庫拆分為諸多的單一材質。obj對象的 載入,根據具使用材質不同來分解為多個3D模型。具體載入過程如下:
頂點著色器
片元著色器
完成了以上准備工作,就可以調用 readMultiObj 方法,將obj文件讀成一個或多個帶有各項參數的3D模型類,然後將每一個3D模型的參數傳入shader中,進而進行渲染:
『貳』 android 用png圖像做opengl紋理時出現黑邊怎麼解決
誒呀,你這種用法大錯特錯了呀!texImage2D不能亂用呀,他是把資源導入GL用的,有點像玩游戲時的Loading.你應該在你的程序初始化時先glGentexture生成多個紋理句柄然後BindTexture,再把你需要的圖片依次輸入這時GL已經擁有了你全部的圖片資源,然後在繪制的時候,用到哪張紋理就先Bind這個紋理,然後DrawArray,再Bind再DrawArray/DrawElement..哪有你這樣每次draw都要texImage2D的?這不要慢死了推薦你去powervr的網站下載Opengles的pc端SDK,裡面好多demo
『叄』 Android OpenGLES 實時美顏(磨皮)的優化(二)
在前一篇文章 Android OpenGLES 實時美顏(磨皮)的優化 ,我們已經介紹了關於實時美顏(磨皮)的一些優化點。但在實際的優化測試中發現,當處理器發熱之後,就無法保證預覽幀率了,主要還是高斯模糊處理的數據量比較大導致。因此,我們需要尋找新的磨皮余鉛方法豎早好。
目前市面上關於磨皮方法有好多種,使用PS磨皮經常用到的方法包括高反差保留、高低頻、中性灰以及雙線性等。其中中性灰和雙線性的效率一般,因此,我們從高反差保留、高低頻這兩種方法中選擇。這里選擇使用高反差保留法做磨皮處理,PS中的高反差保留法進行磨皮,隨手一搜便能找到很多文章,比如:
https://jingyan..com/article/455a99504d568fa1662778d6.html
接下來,我們嘗試著實現文章中講到的過程。
關於高斯模糊的優化,可以參考本人的文章:
OpenGLES濾鏡開發匯總 —— 高斯模糊實現以及優化
對於人像進行高斯模糊,我們設計一個11x11的高斯運算元對圖像進行高斯模糊,shader如下:
vertex shader :
fragment shader:
經過以上的shader進行高斯模糊處理之後,我們得到這樣一張高斯模糊圖像:
在PS的高反差保留磨皮方睜並法中,高反差保留磨皮混合採用的是強光模式,計算公式為:color = 2 * color1 * color2。因此,我們設計出這樣一個高通濾波器,其shader如下:
fragment shader:
經過高通濾波器之後,我們得到這樣一個紋理圖像:
可以看到,經過三通道強光混合處理後,痘印、邊沿等地方都清晰起來了。強光的程度,一般是3的倍數,這里取24倍。
到這一步,其實我們已經得到了需要過濾顏色值,但在這一張圖中,也把邊沿的顏色差值包含進來了。我們接下來需要過濾掉邊沿的顏色差值。這樣在後續的處理中,我們可以保留邊沿的細節不被模糊掉。因此接下來,我們需要將經過高通濾波得到的紋理,再做一次高斯模糊。不過這一次不能11 x11 這么大的高斯運算元,我們選擇一個 5 x 5 大小的高斯運算元。高斯模糊的shader 如下:
vertex shader:
fragment shader:
將高通濾波器得到的紋理,經過高斯模糊處理後,得到這樣一張紋理:
對比高通濾波器處理後的紋理,邊沿細節變得模糊了,而且,需要過濾的顏色差值仍舊保留著。到這一步,我們就得到了做磨皮處理的前置紋理。接下來就是高反差保留磨皮的最後也是最重要的一步。
經過前面的處理,我們得到一張輸入圖片的高斯模糊紋理,以及一張高反差保留的高斯模糊紋理。我們使用這兩張紋理,通過比較藍色通道,計算出需要磨皮的實際強度值,與原圖進行混合處理,然後輸出最終的紋理。shader如下所示:
經過上面的處理之後,我們就得到磨皮處理的結果如下:
可以看到,經過高反差保留磨皮後的結果,磨皮效果還不錯,而且720P磨皮處理時,在高通驍龍625處理器上,經過高反差保留磨皮之後,預覽幀率能夠保持在30FPS左右。我們可以看到,邊沿細節還是不夠明顯,所以,我們可以使用USM銳化增強邊沿細節部分。這篇文章就不講解USM銳化的實現了。
詳細實現過程,可以參考本人的開源相機項目:
CainCamera
CainCamera的FilterLibrary中有經過優化後的實時美顏(磨皮)實現。