Android OpenGLES濾鏡開發之貼紙效果

2021-08-31 21:18:41 字數 3624 閱讀 6244

前言

思路1、貼紙肯定也是需要定位到人臉的

2、找到貼紙需要放置的位置

3、將貼紙紋理和人本身紋理進行融合

實現人臉定位啥的,我就不說了,不清楚的可以去前面的文章看看,主要來看看貼紙是如何貼上去的

1. 建立貼紙的紋理

//opengl 紋理

mtextureid =

newint[1

];//openglutils是個opengl的工具類,具體的前面也有寫

openglutils.

glgentextures

(mtextureid)

; gles20.

glbindtexture

(gles20.gl_texture_2d,mtextureid[0]

);//將bitmap與紋理的id繫結起來

glutils.

teximage2d

(gles20.gl_texture_2d,

0,mbitmap,0)

;//解綁

gles20.

glbindtexture

(gles20.gl_texture_2d,0)

;

2. 畫貼紙

在畫貼紙之前,是已經將之前攝像頭那些紋理已經畫上去過了,然後再來畫貼紙。

gles20.

glenable

(gles20.gl_blend)

;//設定貼圖模式

源圖因子 要畫的是源(耳朵)

已經畫好的目標,也就是我們要往哪兒畫,也就是其他filter的影象

原本是什麼樣子,就畫成什麼樣子

_minus_src_alpha,表示用1.0減去源顏色alpha的值來作為因子

gles20.

glblendfunc

(gles20.gl_one,gles20.gl_one_minus_src_alpha)

;因為在opengl中如果不開啟混合模式,就會把之前的紋理覆蓋掉,這裡就不會顯示上乙個紋理了。

什麼是混合?混合就是把某乙個畫素點的位置原來的顏色與將要畫上去的顏色,以某種方式混合在一起,從而達到某種特殊的效果。我們這裡就需要將貼紙的紋理和人臉的紋理進行乙個混合。

glblendfunc的引數設定有多種模式,第乙個引數表示的是源圖因子,也就是我們要畫上去的貼紙,第二個引數是目標因子,也就是我們要把貼紙畫到哪兒去。這兩個引數有多種值:

gl_zero:表示使用0.0作為因子,實際上相當於不使用這種顏色參與混合運算。

gl_one: 表示使用1.0作為因子,實際上相當於完全的使用了這種顏色參與混合運算。

gl_src_alpha:表示使用源顏色的alpha值來作為因子。

gl_dst_alpha:表示使用目標顏色的alpha值來作為因子。

gl_one_minus_src_alpha:表示用1.0減去源顏色的alpha值來作為因子。

gl_one_minus_dst_alpha:表示用1.0減去目標顏色的alpha值來作為因子。

這個源圖因子使用的是完全使用,也就是貼紙是完全展示出來的,目標因子是用1.0 - 貼紙的alpha值來作為因子的。

下面就是計算出貼紙所要顯示的位置,然後將座標資訊傳遞給著色器

//畫耳朵,是需要往人臉上畫,不是全屏畫

float x = mface.landmarks[0]

;float y =mface.landmarks[1]

;//轉換為要畫到螢幕上的寬、高

x = x / mface.imgwidth * moutputwidth;

y = y/ mface.imgheight * moutputheight;

//貼紙需要顯示的位置

//1.需要顯示到螢幕上的x座標,2.y座標

//3.需要顯示的貼紙的寬 4.高,這兩個引數需要不斷的除錯,然後獲得比較合適的

gles20.

glviewport((

int)x,

(int

)y-mbitmap.

getheight()

/2,(

int)((

float

)mface.width /mface.imgwidth * moutputwidth)

,mbitmap.

getheight()

);les20.

glbindframebuffer

(gles20.gl_framebuffer,mframebuffers[0]

);gles20.

gluseprogram

(mglprogramid)

;//傳遞座標

mglvertexbuffer.

position(0

);gles20.

glvertexattribpointer

(vposition,

2, gles20.gl_float,

false,0

, mglvertexbuffer)

; gles20.

glenablevertexattribarray

(vposition)

; mgltexturebuffer.

position(0

);gles20.

glvertexattribpointer

(vcoord,

2, gles20.gl_float,

false,0

, mgltexturebuffer)

; gles20.

glenablevertexattribarray

(vcoord)

;//啟用紋理,傳遞紋理給著色器

gles20.

glactivetexture

(gles20.gl_texture0)

; gles20.

glbindtexture

(gles20.gl_texture_2d,mtextureid[0]

);gles20.

gluniform1i

(vtexture,0)

;//畫畫

gles20.

gldrawarrays

(gles20.gl_********_strip,0,

4);// 解綁紋理

gles20.

glbindtexture

(gles20.gl_texture_2d,0)

;//解綁framebuffer

gles20.

glbindframebuffer

(gles20.gl_framebuffer,0)

;//最後使用完畢以後需要關閉這個融合

gles20.

gldisable

(gles20.gl_blend)

;

很多都在**裡進行了注釋,應該都可以看得懂,下面就看一下效果圖吧~~

效果圖就差不多是這樣的效果,是因為我手機問題所有才模糊不清楚的,前置攝像頭完成沒有問題的。

Android OpenGL ES 開發入門

本系列文章圍繞關於使用opengl es繪圖的android開發者文件為主線,結合opengl程式設計指南來講述android opengl es開發入門。如果你沒有opengl相關知識,在閱讀opengl es demo 時,可能對圖形的繪製過程不太理解,以至於看完之後,也不知道如何繪製圖形。出於...

Android OpenGLES濾鏡開發之大眼效果

前言 在很多美顏相機啊,抖音啊,都會有一些放大眼睛的效果,今天就來實現如何放大眼睛。思路1 首先使用opencv定位到人臉 2 根據定位到的人臉去檢測人臉關鍵點,進而獲取到人眼睛的位置。3 根據眼睛位置,對眼睛進行放大。實現定位人臉 人臉的定位追蹤,在之前文章中已經寫過opencv實現人臉追蹤 當時...

Android OpenGL ES之新增動作

本文譯自 在螢幕上繪製物件是opengl的最基本功能,你可以使用其他的android圖形框架類,如 canvas 和drawable 物件來完成這些功能。opengles提供了一些用於在三維空間中移動和變換被繪製的物件的能力,以及其他的建立良好使用者體驗的獨特方式。在本文中,你需要使用前面幾篇博文中...