鲲鹏it教育android课件-30.opengl基础应用es简明开发教程_第1页
鲲鹏it教育android课件-30.opengl基础应用es简明开发教程_第2页
鲲鹏it教育android课件-30.opengl基础应用es简明开发教程_第3页
鲲鹏it教育android课件-30.opengl基础应用es简明开发教程_第4页
鲲鹏it教育android课件-30.opengl基础应用es简明开发教程_第5页
已阅读5页,还剩42页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

AndroidOpenGLES概apiDemosGraphicsOpenGLESOpenGLES要用来开发3D形应用的。OpenGLES(OpenGLforEmbeddedSystems)OpenGL图形API的子集,针对、PDA和游戏主机等嵌入式设备而设计。下面是百科中对应OpenGLES的简介OpenGLES是从OpenGL裁剪定制而来的,去除了glBegin/glEnd,OpenGLES1.x对固定管线硬件的,OpenGLES2.x对可编程管线硬件。OpenGLES1.0OpenGL1.3基础的,OpenGLES1.1是以OpenGL1.5规范为基础的,它们分别又支持commoncommonliteprofileliteprofilecommonprofileOpenGLES2.0OpenGL2.0范定义的,commonprofile2005-8,引入了对可编程管线的支持。AndroidApiDemosOpenGLESOpenGLES做个简明开发,可以帮助从未接触过3D开发的程序员了解OpenGL的开发的基本概念和方法,很多移动平台都提供了对OpenGLES开发包的支持,AndroidOpenGLES简明开发主要参考JaywayTeamBlog中OpenGLES开发,这是一个写的比较通俗易懂的开发,适合OpenGLES初学者。除了这个OpenGLES简明开发外,以后将专门针对OpenGLES写个由浅入深的开发,尽请关注。OpenGLESAndoridOpenGLViewAndroidOpenGLESAPIjava.nio等几个包中,其中类GLSurfaceView为这些包中的类OpenGLESAndroidViewOpenGLESAndroidActivityFramebuffer提供了方便使用的调试工具来OpenGLES函数调用以帮助检查错误OpenGLESGLSurfaceView开始,设置GLSurfaceViewOpenGLView1publicvoid setRenderer(GLSurfaceView.Rendererrenderer)1//Calledwhenthesurfaceiscreatedorrecreated.2publicvoidonSurfaceCreated(GL10gl,EGLConfigconfig)4//Calledtodrawthecurrentframe.5publicvoidonDrawFrame(GL10gl)67//Calledwhenthesurfacechanged8publicvoidonSurfaceChanged(GL10gl,intwidth,intonSurfaceCreated参数,比如:背景色,是否打开z-buffer onSurfaceChanged:在横向<->纵向互换时。此时可以重新设置绘制的比率。OpenGLESAndroid项目:OpenGLESTutorial,TutorialPartI.javapublicclassTutorialPartIextendsActivity//CalledwhentheactivityisfirstpublicvoidonCreate(BundlesavedInstanceState)this.requestWindowFeature(Window.FEATURE_NO_TITLE);//WindowManager.LayoutParams.FLAG_FULLSCREEN);//(NEW)GLSurfaceViewview=newview.setRenderer(new}publicclassOpenGLRendererimplementsRenderer{publicvoidonSurfaceCreated(GL10gl,EGLConfigconfig)//Setthebackgroundcolortoblack(rgbagl.glClearColor(0.0f,0.0f,0.0f, //OpenGL//EnableSmoothShading,defaultnotreallygl.glShadeModel(GL10.GL_SMOOTH);//OpenGL//Depthbuffergl.glClearDepthf(1.0f);//OpenGL//Enablesdepthgl.glEnable(GL10.GL_DEPTH_TEST);//OpenGL//Thetypeofdepthtestingtogl.glDepthFunc(GL10.GL_LEQUAL);//OpenGL//Reallynicegl.glHint(GL10.GL__CORRECTION_HINT,//OpenGL}publicvoidonDrawFrame(GL10gl)//Clearsthescreenanddepthgl.glClear(GL10.GL_COLOR_BUFFER_BIT|//OpenGL}publicvoidonSurfaceChanged(GL10gl,intwidth,intheight)//Setsthecurrentviewporttothenew

gl.glViewport(0,0,width,height);//OpenGL//Selecttheprojectionmatrixgl.glMatrixMode(GL10.GL_PROJECTION);//OpenGLdocs.//Resettheprojectionmatrixgl.glLoadIdentity();//OpenGLdocs.//CalculatetheaspectratioofthewindowGLU.glu(gl,45.0f,(float)width/(float)height,0.1f,100.0f);//Selectthemodelviewmatrixgl.glMatrixMode(GL10.GL_MODELVIEW);//OpenGLdocs.//Resetthemodelviewmatrixgl.glLoadIdentity();//OpenGLdocs.}AndroidOpenGLES应用的最基本的类和方法,可以看作是OpenGLES的”o,world”应用,后3D框架代码:可以作为你自己的OpenGL3D的初始代码3D绘图基本概AndroidOpenGLES3D3D(顶点,边,面,多边形)构成,每个Vertex(顶点3D3DCamera(Vertex)。AndroidAndroid1privatefloatvertices[]=2- 1.0f,//0,Top3-1.0f,-1.0f,//1,Bottom41.0f,-1.0f,//2,Bottom5 1.0f,//3,Topjava.ioBuffer1//afloatis4bytes,thereforewemultiplythe2//numberifverticeswith4.3ByteBuffervbb=ByteBuffer.allocateDirect(vertices.length*4);5FloatBuffervertexBuffer=vbb.asFloatBuffer();OpenGLES,OpenGLES一个成为”管道Pipeline”的机制,这个管道定义了一些“开关”来控制OpenGLESOpenGLESOpenGLOpenGLVertexbufferBuffer。2gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);//OpenGLdocs.3//Specifiesthelocationanddataformatofanarrayofvertex4//coordinatestousewhenrendering.6Whenyouaredonewiththebufferdon'tforgettodisableit.7//Disabletheverticesbuffer.8gl.glDisableClientState(GL10.GL_VERTEX_ARRAY);//OpenGLdocs.Edge(边3DOpenGLFace(面的变化影响到连接面的所有顶点和边,面多边形。下图黄域代表一个面。定义面的顶点的顺序很重要Polygon(多边形多边形由多个面(三角形)拼接而成,在三上,多边形并一定表示这个PolygonFront),下图黄域为一个多边形。Androidbuffer1privateshort[]indices={0,1,2,0,2,32Togainsomeperformancewealsoputthisonesinabyte3//shortis2bytes,thereforewemultiplythenumberifvertices5ByteBufferibb=ByteBuffer.allocateDirect(indices.length*7ShortBufferindexBuffer=Render渲染我们已定义好了多边形下面就要了解如和使用OpenGLES的API来绘(渲染)这个多边形了。OpenGLES voidglDrawArrays(intmode,intfirst,int VetexBuffervertexBufferpublicvoidglDrawElements(intmode,intcount,inttype,Bufferindices)indicesBuffer指定。前面我们已定义里顶点数组,因此采用glDrawElements来绘制多边形Square.java1package23import4import5import6import78import910publicclassSquare//Ourprivatefloatvertices[]=- 1.0f, //0,Top-1.0f,-1.0f, //1,Bottom1.0f,-1.0f, //2,Bottom 1.0f, //3,Top//Theorderweliketoconnectprivateshort[]indices={0,1,2,2,3//OurvertexprivateFloatBuffer//OurindexprivateShortBufferpublicSquare()//afloatis4bytes,therefore//multiplythenumber//verticeswith32ByteBuffer33=ByteBuffer.allocateDirect(vertices.length*vertexBuffer=//shortis2bytes,thereforewe//thenumber//verticeswithByteBuffer43=ByteBuffer.allocateDirect(indices.length*indexBuffer=}50*Thisfunctiondrawsoursquareon*@parampublicvoiddraw(GL10gl)//Counter-clockwise//Enableface//Whatfacestoremovewiththeface//Enabledtheverticesbufferfor//andtobeused////Specifiesthelocationanddataformat//anarrayof//coordinatestousewhengl.glVertexPointer(3,GL10.GL_FLOAT,gl.glDrawElements(GL10.GL_TRIANGLES,GL10.GL_UNSIGNED_SHORT,//Disablethevertices//Disableface

}OpenGLRendererSquare1//Initializeoursquare.2Squaresquare=newSquare();publicvoidonDrawFrame(GL10gl)1//Drawour来绘制这个正方形编译运行什么也没显示,这是为什么呢?这是因为OpenGLES从当前位置开始渲染,缺省坐标为(0,0,0),和Viewport的坐标一样,相当于把画面放在眼前,对应这种情况OpenGL不会渲染离viewPort很近的画面,1//Translates4unitsintothescreen.2gl.glTranslatef(0,0,-4);调用onDrawFrame时,每次都再向后移动4单位,需要加上重置Matrix1//ReplacethecurrentmatrixwiththeidentitymatrixpublicvoidonDrawFrame(GL10gl)//Clearsthescreenanddepthgl.glClear(GL10.GL_COLOR_BUFFER_BITgl.glTranslatef(0,0,-//Drawoursquare.draw(gl);//(NEW9本篇代码3D标变3Dtransformations。CoordinateSystem标系OpenGLTranslate平移变方法public voidglTranslatef(floatx,floaty,floatz)用在上个例子中我们把需要显示的正方形后移了4个单位就是使用的坐标的平移Rotate旋publicvoidglRotatef(floatangle,floatx,floaty,float比如你选择一个首先按下列顺31gl.glRotatef(90f,1.0f,0.0f,0.0f);2gl.glRotatef(90f,0.0f,1.0f,0.0f);3gl.glRotatef(90f,0.0f,0.0f,1gl.glRotatef(90f,-1.0f,0.0f,2gl.glRotatef(90f,0.0f,-1.0f,3gl.glRotatef(90f,0.0f,0.0f,-1gl.glRotatef(90f,0.0f,0.0f,-2gl.glRotatef(90f,0.0f,-1.0f,3gl.glRotatef(90f,-1.0f,0.0f,glRotatef(angle,x,y,z)glRotatef(-angle,x,y,z)是等价的,但选择变换的顺序直接影响最终坐标变换的结果。角度为正时表示逆时Translate&Rotate(平移和旋转组合变换Mesh(网格,构成三维形体的基本单位)标变换的顺序也直接影响最终的结果。MeshScale(缩放方法public voidglScalef(floatx,floaty,floatz)用于缩放gl.glScalef(2f,2f,2f)2.Translate&Scale(平移和缩放组合变换1gl.glTranslatef(2,0,0);2gl.glScalef(0.5f,0.5f,0.5f);1gl.glScalef(0.5f,0.5f,0.5f);2gl.glTranslatef(2,0,0);矩阵操作,单位 voidglLoadIdentity void和 voidglPopMatrix在进行坐标变换的一个好习惯是在变换前使用glPushMatrix保存当前矩阵,完glPopMatrix3A,B,C。进行缩放变换,使的BA50%,CB50%。然后以屏幕中心逆时针旋转A,BA心顺时针旋转,C以BonDrawFramepublicvoidonDrawFrame(GL10gl)//Clearsthescreenanddepth|//Replacethecurrentmatrixwiththeidentity//Translates10unitsintothegl.glTranslatef(0,0,-9//SQUARE//Savethecurrent//RotatesquareAcounter-gl.glRotatef(angle,0,0,//Drawsquare//Restorethelast20//SQUARE21//Savethecurrent//RotatesquareBbeforemoving//makingitrotatearoundgl.glRotatef(-angle,0,0,//Movesquaregl.glTranslatef(2,0,//Scaleitto50%ofsquaregl.glScalef(.5f,.5f,//Drawsquare//SQUARE//Savethecurrent//Maketherotationaroundgl.glRotatef(-angle,0,0,gl.glTranslatef(2,0,//Scaleitto50%ofsquaregl.glScalef(.5f,.5f,//Rotatearoundit'sowngl.glRotatef(angle*10,0,0,//Drawsquare//Restoretothematrixasitwas//Restoretothematrixasitwas//Incresethe}添加颜(网格)添加颜色。OpenGLESRGBA(红,绿,蓝,Hex0xFF00FF或十进制格式(255,0,255),0…100,1255(0xFF)最简单的上色方法叫做顶点(Vertxtcoloring),可以使用单色,也可以定义颜色渐变或者使用材质(Brush)。Flatcoloring(单色 voidglColor4f(floatred,floatgreen,floatblue,floatred,green,blue1,代表白色。这也是为什么前面显示的正方形都是1publicvoiddraw(GL10gl)2gl.glColor4f(0.5f,0.5f,1.0f,3OpenGLRenderersquareFlatColoredSquare1privateFlatColoredSquaresquare=newSmoothcoloring(平滑颜色渡当给每个顶点定义一个颜色时,OpenGL1//Thecolorsmappedtothevertices.2float[]colors={30415263Buffer1//floathas4bytes,colors(RGBA)*4bytes2ByteBuffercbb3=ByteBuffer.allocateDirect(colors.length*5colorBuffer=cbb.asFloatBuffer();1publicvoiddraw(GL10gl)2gl.glVertexPointer(3,GL10.GL_FLOAT,0,3//Enablethecolorarraybufferto//usedduring//Pointoutthewherethecolorbuffergl.glColorPointer(4,GL10.GL_FLOAT,0,911//Disablethecolorbuffer.真正的3D图OpenGLES3D(平面上也是有两个Mesh构成的。本篇将介绍使用Mesh构成四面体,椎体等基本空间形Design设OpenGL“CompositePattern”,本篇Mesh,Mesh(三角形网格),其基本定义如下:publicclassMesh//OurvertexprivateFloatBufferverticesBuffer=null;//OurindexprivateShortBufferindicesBuffer=null;//ThenumberofprivateintnumOfIndices=-//Flatprivatefloat[] =newfloat[]{1.0f,1.0f,1.0f,1.0f};//SmoothprivateFloatBuffercolorBuffer=null; //Translate publicfloatx= publicfloaty= publicfloatz=//Rotatepublicfloatrx=floatry=floatrz=voiddraw(GL10gl)//Counter-clockwise//Enableface//Whatfacestoremovewiththeface//Enabledtheverticesbufferforwriting//tobeused////Specifiesthelocationanddata//ofanarrayof//coordinatestousewhengl.glVertexPointer(3,GL10.GL_FLOAT,0,//Setflatgl.glColor4f(rgba[0],rgba[1],rgba[2],//Smoothif(colorBuffer!=null)//Enablethecolorarraybufferto//usedduringgl.glColorPointer(4,GL10.GL_FLOAT,0,}gl.glTranslatef(x,y,gl.glRotatef(rx,1,0,gl.glRotatef(ry,0,1,gl.glRotatef(rz,0,0,//Pointoutthewherethecolorbuffergl.glDrawElements(GL10.GL_TRIANGLES,GL10.GL_UNSIGNED_SHORT,//Disablethevertices//Disableface} protectedvoidsetVertices(float[]vertices)

//afloatis4bytes,//wemultiplythenumber//verticeswith4.ByteBuffervbb=ByteBuffer.allocateDirect(vertices.length*4);verticesBuffer=vbb.asFloatBuffer();}protectedvoidsetIndices(short[]indices)//shortis2bytes,thereforewe//thenumber//verticeswith2.ByteBufferibb=ByteBuffer.allocateDirect(indices.length*2);indicesBuffer=ibb.asShortBuffer();numOfIndices=}protectedvoidsetColor(floatred,floatgreen,floatblue,floatalpha){//Settingtheflatcolor.rgba[0]=red;rgba[1]=green;rgba[2]=blue;rgba[3]=}protectedvoidsetColors(float[]colors)//floathas4bytes.ByteBuffercbb=ByteBuffer.allocateDirect(colors.length*4);colorBuffer=cbb.asFloatBuffer();}setVerticessetIndicessetColor/setColorsx,y,zrx,ry,rz义为沿XZ轴方向长度,高度为YSegments游戏场景中,构造地貌,使的Z0.10.1SegmentsOpenGLSegments//Letyoudecidethesizeoftheplanebutstillonlyonesegment.publicPlane(floatwidth,floatheight)//ForallayourpublicPlane(floatwidth,floatheight,intwidthSegments,int1unit1unit4Segments,使用图形表示如segmentsPlanepublicclassPlaneextendsMeshpublicPlane()this(1,1,1,}5publicPlane(floatwidth,floatheight)this(width,height,1,}9publicPlane(floatwidth,floatheight,intintheightSegments)float[]13=newfloat[(widthSegments+*(heightSegments+1)*short[]16=newshort[(widthSegments+17*(heightSegments+1)*floatxOffset=width/-floatyOffset=height/-floatxWidth=width/floatyHeight=height/intcurrentVertex=intcurrentIndex=shortw=(short)(widthSegments+for(inty=0;y<heightSegments+1;y++)for(intx=0;x<widthSegments+1;x++)vertices[currentVertex]=xOffset+x*vertices[currentVertex+1]=yOffset+y*vertices[currentVertex+2]=currentVertex+=33intn=y*(widthSegments+1)+x;if(y<heightSegments&&x<widthSegments)//Faceindices[currentIndex]=(short)+=++=+//Face+=++=+1+=+1wcurrentIndex+=}}}

}PlaneSegments1publicclassCubeextendsMesh2Cube(floatwidth,floatheight,floatdepth)3/=4/=5/=6floatvertices[]={-width,-height,-depth,//width,-height,-depth,// height,-depth,//- height,-depth,//-width,- depth,//width,- depth,// depth,//- depth,//17shortindices[]={0,4,

}Group可以用来管理多个空间几何形体如果把Mesh比作Android的View,Group可以看作AndroidViewGroupAndroidView的设计也是采用的“CompositeGroupGroup(draw)Group对应的操作(draw)。publicclassGroupextendsMeshprivateVector<Mesh>children=newVector<Mesh>();publicvoiddraw(GL10gl)intsize=for(inti=0;i<size;}11*@param*@param*@seejava.util.Vector#add(int,publicvoidadd(intlocation,Meshobject)children.add(location,}20*@param**@seepublicbooleanadd(Meshobject)return}29**@seepublicvoidclear()}37*@param**@seepublicMeshget(intlocation)return}46*@param**@seepublicMeshremove(intlocation)

return}@param@seepublicbooleanremove(Objectobject){returnchildren.remove(object);}@seepublicintsize(){returnchildren.size();}其它建本例示例代 ,显示结果如下材质渲创建Bitmap对BitmapBitmap文件中或是从网络或是使用代码构造为简单起见本例从资源中:1Bitmapbitmap=要注意的是,有些设备对使用的Bitmap的大小有要求,要求Bitmap的宽度和长创建材质(GeneratingaOpenGL(TextureTextureId。1//Createanintarraywiththenumberoftextureswewant,2//inthiscase1.3int[]textures=new4//lOpenGLtogeneratetextures.5gl.glGenTextures(1,textures,0);texturesTextureID,TextureIdTexture:1//Deleteatexture.2gl.glDeleteTextures(1,textures,0)TextureIdOpenGLTexture:1gl.glBindTexture(GL10.GL_TEXTURE_2D,设置Texture参数TextureTextureTextureOpenGL1//Scaleupifthetextureifsmaller.56//scalelinearlywhenimagesmalledthantextureGL10.GL_LINEARGL10.GL_NEARESTGL10.GL_LINEARUVOpenGLBitmapMesh定义UV坐UVMap指将Bitmap的像素映射到Mesh上的顶点UV坐标定义为左上(0,0),右下角(1,1)(2DTexture),UVUV(0,1)0,(1,1)21floattextureCoordinates[]={0.0f,21.0f,30.0f,41.0f,0.0f1floattextureCoordinates[]={0.0f,20.5f,30.0f,40.5f,0.0fTexture1floattextureCoordinates[]={0.0f,22.0f,30.0f,42.0f,0.0fUV),OpenGLTextureGL_REPEATTextureGL_CLAMP_TO_EDGE只靠边线绘制一次。BitmapTexture1GLUtils.texImage2D(GL10.GL_TEXTURE_2D,0,bitmap,使用为了能够使用上面定义的Texture,需要创建一Buffer来UV坐标:1FloatBufferbyteBuf=ByteBuffer.allocateDirect(texture.length*4);3textureBuffer=byteBuf.asFloatBuffer();//lingOpenGLtoenable//lOpenGLwhereourtextureisgl.glBindTexture(GL10.GL_TEXTURE_2D,//lOpenGLtoenabletheuseofUV//lingOpenGLwhereourUVcoordinatesgl.glTexCoordPointer(2,GL10.GL_FLOAT,0,910//...heregoestherenderingofthemesh...12//DisabletheuseofUVcoordinates.14//Disabletheuseoftextures.本例代码是在一个平面上(SimplePlane)TextureMeshUV//OurUVtextureprivateFloatBuffermTextureBuffer;4*Setthetexture**@paramprotectedvoidsetTextureCoordinates(float[]textureCoords)//floatis4bytes,thereforewemultiplythenumber//verticeswithByteBufferbyteBuf=textureCoords.length*mTextureBuffer=

BitmapTexture//OurtextureprivateintmTextureId=-3//ThebitmapwewanttoloadasaprivateBitmapmBitmap;7*Setthebitmaptoloadintoa**@param12publicvoidloadBitmap(Bitmapbitmap)

this.mBitmap=bitmap;mShouldLoadTexture=true;*Loadsthe**@param22privatevoidloadGLTexture(GL10gl)//Generateonetextureint[]textures=newgl.glGenTextures(1,textures,mTextureId

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论