最近学习 opengl,看了一些简单的教程。发现一般都是到实现金字塔或者立方体就结束了。

纹理方面,对三维物体的多个面未做处理。参看了这些例子,做一个android 上的多纹理的立方体。

效果图:

1.

2.

以下是主要代码:

Activity负责初始化相关资源文件。重写了onTouchEvent()方法,实现鼠标翻转,方便观察。

public class Cube extends Activity {    GLRender render = new GLRender();    private float mPreviousX;    private float mPreviousY;    private final float TOUCH_SCALE_FACTOR = 180.0f / 320;    private final float TRACKBALL_SCALE_FACTOR = 36.0f;    /** Called when the activity is first created. */    @Override    public void onCreate(Bundle savedInstanceState) {    super.onCreate(savedInstanceState);GLImage.load(this.getResources());GLSurfaceView glView = new GLSurfaceView(this);glView.setRenderer(render);setContentView(glView);    }    public boolean onKeyUp(int keyCode, KeyEvent event){render.onKeyUp(keyCode, event);return false;} public boolean onTrackballEvent(MotionEvent e) { render.xrot += e.getX() * TRACKBALL_SCALE_FACTOR; render.yrot += e.getY() * TRACKBALL_SCALE_FACTOR;        return true;    } public boolean onTouchEvent(MotionEvent e) {        float x = e.getX();        float y = e.getY();        switch (e.getAction()) {        case MotionEvent.ACTION_MOVE:            float dx = x - mPreviousX;            float dy = y - mPreviousY;            render.xrot += dx * TOUCH_SCALE_FACTOR;            render.yrot += dy * TOUCH_SCALE_FACTOR;        }        mPreviousX = x;        mPreviousY = y;        return true;    }}class GLImage{public static Bitmap mBitmap1;public static Bitmap mBitmap2;public static Bitmap mBitmap3;public static Bitmap mBitmap4;public static Bitmap mBitmap5;public static Bitmap mBitmap6;public static void load(Resources resources){mBitmap1 = BitmapFactory.decodeResource(resources, R.drawable.icon1);mBitmap2 = BitmapFactory.decodeResource(resources, R.drawable.icon2);mBitmap3 = BitmapFactory.decodeResource(resources, R.drawable.icon3);mBitmap4 = BitmapFactory.decodeResource(resources, R.drawable.icon4);mBitmap5 = BitmapFactory.decodeResource(resources, R.drawable.icon5);mBitmap6 = BitmapFactory.decodeResource(resources, R.drawable.icon6);}}


Render负责opengl实体的初始化以及配置、画出等,相关光源,观察模型方面没有深入。

public class GLRender implements Renderer{boolean key = true;float xrot = 0.0f;float yrot = 0.0f;float xspeed, yspeed;float z = -5.0f;int one = 0x10000;//光线参数FloatBuffer lightAmbient = FloatBuffer.wrap(new float[]{0.5f,0.5f,0.5f,1.0f}); FloatBuffer lightDiffuse = FloatBuffer.wrap(new float[]{1.0f,1.0f,1.0f,1.0f}); FloatBuffer lightPosition = FloatBuffer.wrap(new float[]{0.0f,0.0f,2.0f,1.0f}); int [] texture;IntBuffer vertices = IntBuffer.wrap(new int[]{-one,-one,one,one,-one,one,one,one,one,-one,one,one,-one,-one,-one,-one,one,-one,one,one,-one,one,-one,-one,-one,one,-one,-one,one,one,one,one,one,one,one,-one,-one,-one,-one,one,-one,-one,one,-one,one,-one,-one,one,one,-one,-one,one,one,-one,one,one,one,one,-one,one,-one,-one,-one,-one,-one,one,-one,one,one,-one,one,-one,});IntBuffer normals = IntBuffer.wrap(new int[]{0,0,one,0,0,one,0,0,one,0,0,one,0,0,one,0,0,one,0,0,one,0,0,one,0,one,0,0,one,0,0,one,0,0,one,0,0,-one,0,0,-one,0,0,-one,0,0,-one,0,one,0,0,one,0,0,one,0,0,one,0,0,-one,0,0,-one,0,0,-one,0,0,-one,0,0,});IntBuffer texCoords = IntBuffer.wrap(new int[]{one,0,0,0,0,one,one,one,0,0,0,one,one,one,one,0,one,one,one,0,0,0,0,one,0,one,one,one,one,0,0,0,0,0,0,one,one,one,one,0,one,0,0,0,0,one,one,one,});ByteBuffer indices1 = ByteBuffer.wrap(new byte[]{0,1,3,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,});ByteBuffer indices2 = ByteBuffer.wrap(new byte[]{0,0,0,0,4,5,7,6,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,});ByteBuffer indices3 = ByteBuffer.wrap(new byte[]{0,0,0,0,0,0,0,0,8,9,11,10,0,0,0,0,0,0,0,0,0,0,0,0,});ByteBuffer indices4 = ByteBuffer.wrap(new byte[]{0,0,0,0,0,0,0,0,0,0,0,0,12,13,15,14,0,0,0,0,0,0,0,0,});ByteBuffer indices5 = ByteBuffer.wrap(new byte[]{0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,16,17,19,18,0,0,0,0,});ByteBuffer indices6 = ByteBuffer.wrap(new byte[]{0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,20,21,23,22,});@Overridepublic void onDrawFrame(GL10 gl){// 清除屏幕和深度缓存gl.glClear(GL10.GL_COLOR_BUFFER_BIT | GL10.GL_DEPTH_BUFFER_BIT);gl.glMatrixMode(GL10.GL_MODELVIEW);// 重置当前的模型观察矩阵gl.glLoadIdentity();gl.glEnable(GL10.GL_LIGHTING);////////////////gl.glTranslatef(0.0f, 0.0f, z);//设置旋转gl.glRotatef(xrot, 0.0f, 1.0f, 0.0f);gl.glRotatef(yrot, 1.0f, 0.0f, 0.0f);gl.glNormalPointer(GL10.GL_FIXED, 0, normals);gl.glVertexPointer(3, GL10.GL_FIXED, 0, vertices);gl.glTexCoordPointer(2, GL10.GL_FIXED, 0, texCoords);gl.glEnableClientState(GL10.GL_NORMAL_ARRAY);gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);gl.glEnableClientState(GL10.GL_TEXTURE_COORD_ARRAY);//绘制四边形gl.glBindTexture(GL10.GL_TEXTURE_2D, texture[0]);gl.glDrawElements(GL10.GL_TRIANGLE_STRIP, 4,  GL10.GL_UNSIGNED_BYTE, indices1);gl.glBindTexture(GL10.GL_TEXTURE_2D, texture[1]);gl.glDrawElements(GL10.GL_TRIANGLE_STRIP, 8,  GL10.GL_UNSIGNED_BYTE, indices2);gl.glBindTexture(GL10.GL_TEXTURE_2D, texture[2]);gl.glDrawElements(GL10.GL_TRIANGLE_STRIP, 12,  GL10.GL_UNSIGNED_BYTE, indices3);gl.glBindTexture(GL10.GL_TEXTURE_2D, texture[3]);gl.glDrawElements(GL10.GL_TRIANGLE_STRIP, 16,  GL10.GL_UNSIGNED_BYTE, indices4);gl.glBindTexture(GL10.GL_TEXTURE_2D, texture[4]);gl.glDrawElements(GL10.GL_TRIANGLE_STRIP, 20,  GL10.GL_UNSIGNED_BYTE, indices5);gl.glBindTexture(GL10.GL_TEXTURE_2D, texture[5]);gl.glDrawElements(GL10.GL_TRIANGLE_STRIP, 24,  GL10.GL_UNSIGNED_BYTE, indices6);    gl.glDisableClientState(GL10.GL_TEXTURE_COORD_ARRAY);    gl.glDisableClientState(GL10.GL_VERTEX_ARRAY);    gl.glDisableClientState(GL10.GL_NORMAL_ARRAY);    //修改旋转角度//    xrot+=0.3f; //    yrot+=0.2f;        //混合开关    if (key){    gl.glEnable(GL10.GL_BLEND);// 打开混合    gl.glDisable(GL10.GL_DEPTH_TEST);// 关闭深度测试}    else     {    gl.glDisable(GL10.GL_BLEND);// 关闭混合    gl.glEnable(GL10.GL_DEPTH_TEST);// 打开深度测试}}@Overridepublic void onSurfaceChanged(GL10 gl, int width, int height){float ratio = (float) width / height;//设置OpenGL场景的大小gl.glViewport(0, 0, width, height);//设置投影矩阵gl.glMatrixMode(GL10.GL_PROJECTION);//重置投影矩阵gl.glLoadIdentity();// 设置视口的大小gl.glFrustumf(-ratio, ratio, -1, 1, 1, 10);// 选择模型观察矩阵gl.glMatrixMode(GL10.GL_MODELVIEW);// 重置模型观察矩阵gl.glLoadIdentity();}@Overridepublic void onSurfaceCreated(GL10 gl, EGLConfig config){gl.glDisable(GL10.GL_DITHER);// 告诉系统对透视进行修正gl.glHint(GL10.GL_PERSPECTIVE_CORRECTION_HINT, GL10.GL_FASTEST);// 黑色背景gl.glClearColor(0, 0, 0, 0);gl.glEnable(GL10.GL_CULL_FACE);// 启用阴影平滑gl.glShadeModel(GL10.GL_SMOOTH);// 启用深度测试gl.glEnable(GL10.GL_DEPTH_TEST);//设置光线,,1.0f为全光线,a=50%gl.glColor4f(1.0f,1.0f,1.0f,0.5f);// 基于源象素alpha通道值的半透明混合函数gl.glBlendFunc(GL10.GL_SRC_ALPHA,GL10.GL_ONE);//纹理相关IntBuffer textureBuffer = IntBuffer.allocate(6);gl.glGenTextures(6, textureBuffer);texture = textureBuffer.array();gl.glBindTexture(GL10.GL_TEXTURE_2D, texture[0]);GLUtils.texImage2D(GL10.GL_TEXTURE_2D, 0, GLImage.mBitmap1, 0);gl.glTexParameterx(GL10.GL_TEXTURE_2D,GL10.GL_TEXTURE_MAG_FILTER,GL10.GL_NEAREST); gl.glTexParameterx(GL10.GL_TEXTURE_2D,GL10.GL_TEXTURE_MIN_FILTER,GL10.GL_NEAREST); gl.glBindTexture(GL10.GL_TEXTURE_2D, texture[1]);GLUtils.texImage2D(GL10.GL_TEXTURE_2D, 0, GLImage.mBitmap2, 0);gl.glTexParameterx(GL10.GL_TEXTURE_2D,GL10.GL_TEXTURE_MAG_FILTER,GL10.GL_NEAREST);gl.glTexParameterx(GL10.GL_TEXTURE_2D,GL10.GL_TEXTURE_MIN_FILTER,GL10.GL_NEAREST);gl.glBindTexture(GL10.GL_TEXTURE_2D, texture[2]);GLUtils.texImage2D(GL10.GL_TEXTURE_2D, 0, GLImage.mBitmap3, 0);gl.glTexParameterx(GL10.GL_TEXTURE_2D,GL10.GL_TEXTURE_MAG_FILTER,GL10.GL_NEAREST); gl.glTexParameterx(GL10.GL_TEXTURE_2D,GL10.GL_TEXTURE_MIN_FILTER,GL10.GL_NEAREST); gl.glBindTexture(GL10.GL_TEXTURE_2D, texture[3]);GLUtils.texImage2D(GL10.GL_TEXTURE_2D, 0, GLImage.mBitmap4, 0);gl.glTexParameterx(GL10.GL_TEXTURE_2D,GL10.GL_TEXTURE_MAG_FILTER,GL10.GL_NEAREST); gl.glTexParameterx(GL10.GL_TEXTURE_2D,GL10.GL_TEXTURE_MIN_FILTER,GL10.GL_NEAREST); gl.glBindTexture(GL10.GL_TEXTURE_2D, texture[4]);GLUtils.texImage2D(GL10.GL_TEXTURE_2D, 0, GLImage.mBitmap5, 0);gl.glTexParameterx(GL10.GL_TEXTURE_2D,GL10.GL_TEXTURE_MAG_FILTER,GL10.GL_NEAREST); gl.glTexParameterx(GL10.GL_TEXTURE_2D,GL10.GL_TEXTURE_MIN_FILTER,GL10.GL_NEAREST); gl.glBindTexture(GL10.GL_TEXTURE_2D, texture[5]);GLUtils.texImage2D(GL10.GL_TEXTURE_2D, 0, GLImage.mBitmap6, 0);gl.glTexParameterx(GL10.GL_TEXTURE_2D,GL10.GL_TEXTURE_MAG_FILTER,GL10.GL_NEAREST); gl.glTexParameterx(GL10.GL_TEXTURE_2D,GL10.GL_TEXTURE_MIN_FILTER,GL10.GL_NEAREST); //深度测试相关gl.glClearDepthf(1.0f);gl.glDepthFunc(GL10.GL_LEQUAL);gl.glHint(GL10.GL_PERSPECTIVE_CORRECTION_HINT, GL10.GL_NICEST);gl.glEnable(GL10.GL_TEXTURE_2D);//设置环境光    gl.glLightfv(GL10.GL_LIGHT1, GL10.GL_AMBIENT, lightAmbient);    //设置漫射光    gl.glLightfv(GL10.GL_LIGHT1, GL10.GL_DIFFUSE, lightDiffuse);    //设置光源位置    gl.glLightfv(GL10.GL_LIGHT1, GL10.GL_POSITION, lightPosition);        //开启一号光源    gl.glEnable(GL10.GL_LIGHT1);        //开启混合    gl.glEnable(GL10.GL_BLEND);}public boolean onKeyUp(int keyCode, KeyEvent event){key = !key;return false;}}


最后,说说最主要的部分:onSurfaceCreated()方法中的纹理初始化。onDrawFrame()方法中绘制每个四边形的时候用不同的纹理填充。

更多相关文章

  1. Android中Matrix的pre post set方法理解
  2. Android(安卓)OpenGL ES学习笔记之常用API
  3. 深度揭秘android摄像头的autoFocus-----循环自动聚焦的实现(Andro
  4. Android应用程序开发以及背后的设计思想深度剖析
  5. 图片缓存库之深度剖析
  6. Android(安卓)API Guides---OpenGL ES
  7. ETC1压缩纹理格式详解
  8. Android画图学习总结(四)——Animation(中)
  9. [转]Android中Matrix的pre post set方法理解

随机推荐

  1. 关于android:configChanges="keyboardHid
  2. 享受 Android 应用程序的 Java 技术盛宴
  3. react native for android 包名修改
  4. Android Studio运行main方法报错 SourceS
  5. android中的布局简要介绍
  6. android 存储数据与文件
  7. Android短信编解码方式
  8. Android(安卓)Studio witing for debugge
  9. android 与c#服务端DES加密不一致问题解
  10. Activity的布局