OpenGL ES(第一篇绘制方式) 学习

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/xiatiandefeiyu/article/details/78778608

OpenGL ES入门确实有点困难,以我个人感觉是这个技术中包括太多以前没有接触过的名词(比如光照,雾化等等),以及线性数学的知识,但是好在这个技术出了很长时间了,所以这方面的书籍很多,可以辅助我们看文档。好了现在正式进入OpenGL ES的世界,本文主要讲解基本图元画法的所有方式,在OpenGL ES的世界里基本图元只有点、线、三角形,不管画任何图形都是以这三种基本图元拼接,但是不管画基本图元的任何一种,它都有规定的自己的type类型,根据type类型的不同,顶点连线的方式也不一样。在android的应用层,有直接提供的OpenGL ES的api供我们调用。

在android的应用层使用OpenGL

    第一步视图层需要继承GLSurfaceView这个类

  第二步为视图层设置渲染器Renderer实现接口,调用setRenderer(renderer)设置渲染器,然后设置渲染模式,这里主要有两种渲染模式,如下

  //RENDERMODE_CONTINUOUSLY 主动渲染  主动调用 onDrawFrame  消耗性能
  //RENDERMODE_WHEN_DIRTY   等待渲染  刷新界面 requestRender();

  接下来在渲染器的onSurfaceCreated方法中做初始化操作

  //关闭抗抖动(对于可用颜色较少的系统,可以牺牲分辨率,通过颜色抖动来增加的颜色数量)
  //gl.glDisable(GL10.GL_DITHER);//关闭
  //设置背景(RGB A)
  gl.glClearColor(0, 0, 0, 0);(这里设置的为黑色)
  //开启深度检测
  gl.glEnable(GL10.GL_DEPTH_TEST)

  这里如果只是画二维图形的话没有必要开启深度检测,但是画三维图形的话必须开启深度检测


  然后在onSurfaceChanged方法中设置视图怎么显示

  //设置视口(手机屏幕和近平面做对接)
   gl.glViewport(0, 0, //手机原点坐标
        width, height);//视口大小
  //设置投影矩阵
  gl.glMatrixMode(GL10.GL_PROJECTION);
  //将投影矩阵设置为单位矩阵
  gl.glLoadIdentity();
  //得到宽高比
  float r = (float) width / height;
  //设置视角大小
  gl.glFrustumf(-r, r, -1, 1, 1, 20);

  最后在onDrawFrame方法中进行图元的绘制

 //清空上一次绘制的缓存,颜色缓存和深度缓存

  gl.glClear(GL10.GL_COLOR_BUFFER_BIT| GL10.GL_DEPTH_BUFFER_BIT);

  p.drawSelf(gl);

这里注意一下gl.glFrustumf意在设置平截头体的近平面和远平面,前四个参数设置近平面的大小,后两个参数设置近平面和远平面距离摄像机的位置,也就是z轴深度,默认相机位置为手机屏幕位置,最终设置的顶点坐标都会经过透视除法将用户设置的坐标转化为近平面坐标系坐标,当然透视除法是OpenGL内部自己做的,假如近平面设置了(-1,1,-1,1)由于手机屏幕宽高不一致的情况,在屏幕翻转的情况下,同一个物体在单位1下的像素分布不均匀,所以会产生拉伸的情况,所以此处设置的宽高比就起到了作用。


 第三步准备顶点图元和顶点颜色

 int vcount = 4;
        int UNIT_SIZE = 10000;//缩放比例
        //顶点数据(xyz)
        int ver[] = new int[]{
                -2 * UNIT_SIZE, -1,
                1 * UNIT_SIZE, 1 ,
                -1 * UNIT_SIZE, -2 * UNIT_SIZE,
                2 * UNIT_SIZE, -3 * UNIT_SIZE

        };
        //创建顶点缓冲
        verBuffer = getIntBuffer(ver);

        //顶点颜色
        int one = 65535;//支持65535色彩通道
        //顶点颜色数据(R GB A)
        int color[] = new int[]{
                one, 0, 0, 0,
                one, 0, 0, 0,
                one, 0, 0, 0,
                one, 0, 0, 0

        };
        //创建顶点颜色缓冲
        colorBuffer = getIntBuffer(color);
        byte indices[] = new byte[]{
                0, 3, 2, 1
        };
        //创建索引缓冲
        indBuffer = getByteBuffer(indices);
这里设置四个顶点,然后设置顶点颜色为红色,最后执行下面的方法进行绘制

//启用顶点坐标数组
        gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);
        //启用顶点颜色数组
        gl.glEnableClientState(GL10.GL_COLOR_ARRAY);
       // gl.glColor4f( 1, 0, 0, 0);
        //设置画笔
        //为画笔指定顶点坐标数据
        gl.glVertexPointer(2, //坐标个数( xyz)
                GL10.GL_FIXED,//顶点的数据类型
                0, //连续顶点坐标数据的间隔
                verBuffer);//顶点数据缓冲

        //为画笔指定顶点颜色数据
        gl.glColorPointer(4, //颜色值组成( RGBA)
                GL10.GL_FIXED,//数据类型
                0, //连续顶点坐标数据的间隔
                colorBuffer);//顶点颜色数据缓冲
        gl.glPointSize(10);///设置绘制的顶点大小
        //绘制(索引法)
        gl.glDrawElements(GL10.GL_POINTS, //绘制模型(点 线段 三角形 )
                4,//索引个数
                GL10.GL_UNSIGNED_BYTE,//数据类型
                indBuffer);//索引数据缓冲
画顶点的时候先要开启 glEnableClientState(GL10.GL_VERTEX_ARRAY)顶点坐标能用,然后指定顶点坐标数据,最后调用索引画法进行画图,这里注意最后的画图函数 g lDrawElements的第一个参数指定怎么样画顶点。

GL10.GL_POINTS:绘制单独的点,每个顶点单独绘制不产生关系


GL_LINES:两个点进行连线,两个点一组进行点的绘制(比如1,2,3,4个顶点,1和2相连,3和4相连,如果只有一个点就会舍弃这个点


GL_LINE_STRIP:按照顶点顺序连接顶点(比如1,2,3,4个顶点,1和2相连,2和3相连,3和4相连)


GL_LINE_LOOP:按照顶点顺序连接顶点,最后一个点连接第一点(比如1,2,3,4个顶点,1和2相连,2和3相连,3和4相连,4和1相连)


GL_TRIANGLES:(三角形)三个点一组,如果不够三个点就会舍弃 多余的点


GL_TRIANGLE_STRIP:顶点按照顺序依次 组成三角形绘制,最后实际形成的是一个三角型带



GL_TRIANGLE_FAN:将第一个点作为中心点,其他点作为边缘点,绘制一系列的组成扇形的三角形





猜你喜欢

转载自blog.csdn.net/xiatiandefeiyu/article/details/78778608