日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 运维知识 > Android >内容正文

Android

【Android OpenGL ES 开发 (三)】Shader 扩展

發布時間:2023/12/3 Android 26 豆豆
生活随笔 收集整理的這篇文章主要介紹了 【Android OpenGL ES 开发 (三)】Shader 扩展 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

編譯Shader代碼

1.封裝一個編譯shader的接口

GLuint CompileShader(GLenum shaderType,const char *shaderCode){GLuint shader=glCreateShader(shaderType);glShaderSource(shader,1,&shaderCode,NULL);glCompileShader(shader);GLint compileResult=GL_TRUE;glGetShaderiv(shader,GL_COMPILE_STATUS,&compileResult);if(compileResult==GL_FALSE){char szLog[1024]={0};GLsizei logLen=0;glGetShaderInfoLog(shader,1024,&logLen,szLog);__android_log_print(ANDROID_LOG_INFO,"BattleFire","CompileShader %s\n%s\n",szLog,shaderCode);glDeleteShader(shader);shader=0;}return shader; }

2.調用編譯shader的接口

//編譯shaderint filesize=0;unsigned char *filecontent=LoadfileContent("test.vs",filesize);GLuint vsshader = CompileShader(GL_VERTEX_SHADER,(char*)filecontent);delete [] filecontent;filecontent=LoadfileContent("test.fs",filesize);GLuint fsshader = CompileShader(GL_VERTEX_SHADER,(char*)filecontent);delete [] filecontent;

生成GPU程序

1.實現生成GPU程序接口

GLuint CreateProgram(GLuint vs,GLuint fs){GLuint program=glCreateProgram();glAttachShader(program,vs);glAttachShader(program,fs);glLinkProgram(program);glDetachShader(program,vs);glDetachShader(program,fs);GLint nResult;glGetProgramiv(program,GL_LINK_STATUS,&nResult);if(nResult==GL_FALSE){char szLog[1024]={0};GLsizei logLen=0;glGetProgramInfoLog(program,1024,&logLen,szLog);__android_log_print(ANDROID_LOG_INFO,"BattleFire","CreateProgram %s\n",szLog);glDeleteProgram(program);program=0;}return program; }

2.編譯與生成GPU程序合并封裝

GLuint CreateStanarProgram(const char *vertex_shader_path,const char * fragment_shader_path) {//編譯shaderint filesize=0;unsigned char *filecontent=LoadfileContent(vertex_shader_path,filesize);GLuint vsShade = CompileShader(GL_VERTEX_SHADER,(char*)filecontent);delete [] filecontent;filecontent=LoadfileContent(fragment_shader_path,filesize);GLuint fsShader = CompileShader(GL_VERTEX_SHADER,(char*)filecontent);delete [] filecontent;GLuint program=CreateProgram(vsShade,fsShader);glDeleteShader(vsShade);glDeleteShader(fsShader);return program; }

配置好屬性組并進行繪制

extern "C" JNIEXPORT void JNICALL Java_com_example_learnogles_MainActivity_Render(JNIEnv* env,jobject /* this */) {//__android_log_print(ANDROID_LOG_INFO,HANGYU_LOG_TAG,"Render");glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT|GL_STENCIL_BUFFER_BIT);glBindBuffer(GL_ARRAY_BUFFER,vbo);//設置狀態機glUseProgram(program);glUniformMatrix4fv(modelMatrixLocation,1,GL_FALSE,glm::value_ptr(modelMatrix));//模型矩陣glUniformMatrix4fv(viewMatrixLocation,1,GL_FALSE,glm::value_ptr(viewMatrix));//視口矩陣glUniformMatrix4fv(projectionMatrixLocation,1,GL_FALSE,glm::value_ptr(projectionMatrix));//投影矩陣//set attribute//激活屬性組glEnableVertexAttribArray(positionLocation);//激活屬性位置glVertexAttribPointer(positionLocation,4,GL_FLOAT,GL_FALSE,sizeof(Vectice),0); // glEnableVertexAttribArray(colorLocation); // glVertexAttribPointer(colorLocation,4,GL_FLOAT,GL_FALSE,sizeof(float)*8,(void*)(sizeof(float)*4));glDrawArrays(GL_TRIANGLES,0,3);//從第0個點繪制,繪制三個點,會從vbo中取值glBindBuffer(GL_ARRAY_BUFFER,0);glUseProgram(0);}

屬性在shader間的傳遞

1.VS

attribute vec4 position; attribute vec4 color; uniform mat4 U_ModelMatrix; uniform mat4 U_ViewMatrix; uniform mat4 U_ProjectionMatrix; varying vec4 V_Color; void main(){V_Color=color;gl_Position=U_ProjectionMatrix*U_ViewMatrix*U_ModelMatrix*position; }

2.FS

#ifdef GL_ES precision mediump float; #endif varying vec4 V_Color; void main(){gl_FragColor=V_Color; }

模型矩陣的使用

1.在世界坐標Z為0的時候,由于平行不能看見任何東西。在這種情況我們可以使用模型矩陣整體平移(原理:是uniform變量,會影響所有點)

//平移 modelMatrix=glm::translate(0.0f,0.0f,-2.0f) //縮放 glm::scale(0.5f,0.5f,0.5f) //旋轉 glm::rotate(30.0f,0.0f,0.0f,1.0f);//旋轉角度,旋轉哪個軸修改哪個軸

正交投影與2DUI元素的繪制

備注:透視投影,進大遠小。

1.根據屏幕像素坐標來寫繪圖數據,而不需要3D坐標,使用前提必須寫成以下內容才可以正確使用。

float half_width=float(width)/2.0f; //畫布的寬 float half_height=float(height)/2.0f;//畫布的高 //左邊界,有邊界,下邊界,上邊界,最近點,最遠點 projectionMatrix=glm::ortho(-half_width,half_width,-half_height,half_height,0.1f,100.0f);

控制UI前后關系的方法之一

1.通過修改模型矩陣來修改UI前后關系。

2.可以通過修改Z的坐標來確定誰覆蓋誰,前提是需要開啟深度緩沖區才能管理物體遠近關系。

glEnable(GL_DEPTH_TEST)

使用索引數據繪制UI

1.定義一個 GLuint ibo;//index buffer object ,element array buffer object

unsigned short indexes[]={ 0,1,2,1,3,2};glGenBuffers(1,&ibo);glBindBuffer(GL_ELEMENT_ARRAY_BUFFER,ibo);glBufferData(GL_ELEMENT_ARRAY_BUFFER,sizeof(unsigned short)*6, nullptr,GL_STATIC_DRAW);//alloc gpuglBufferSubData(GL_ELEMENT_ARRAY_BUFFER,0,sizeof(unsigned short)*6,indexes);//cpu -> gpu//glBufferData(GL_ARRAY_BUFFER,sizeof(Vertice)*3,vertices,GL_STATIC_DRAW);//cpu -> gpuglBindBuffer(GL_ELEMENT_ARRAY_BUFFER,0);

2.繪制修改,改變的是繪制三角形的方式

glBindBuffer(GL_ELEMENT_ARRAY_BUFFER,ibo);glDrawElements(GL_TRIANGLES,6,GL_UNSIGNED_SHORT,0);//glDrawArrays(GL_TRIANGLE_STRIP,0,4);glUniformMatrix4fv(modelMatrixLocation,1,GL_FALSE,glm::value_ptr(modelMatrix2));glDrawElements(GL_TRIANGLES,6,GL_UNSIGNED_SHORT,0);//glDrawArrays(GL_TRIANGLE_STRIP,0,4);glBindBuffer(GL_ELEMENT_ARRAY_BUFFER,0);

封裝VBO和IBO相關API

GLuint CreateBufferObject(GLenum type,void * data,int size,GLenum usage){GLuint object_to_ret;glGenBuffers(1,&object_to_ret);glBindBuffer(type,object_to_ret);glBufferData(type,size,data,usage);//cpu -> gpuglBindBuffer(type,0);return object_to_ret; } void UpdateBufferObject(GLuint object,GLenum type,void * data,int size,int offset){glBindBuffer(type,object);glBufferSubData(type,offset,size,data);//cpu -> gpuglBindBuffer(type,0); }

?

創作挑戰賽新人創作獎勵來咯,堅持創作打卡瓜分現金大獎

總結

以上是生活随笔為你收集整理的【Android OpenGL ES 开发 (三)】Shader 扩展的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。