您的位置:首页 > 移动开发 > Android开发

一个简单的Android OpenES Demo

2010-07-05 11:31 555 查看
这个例子是根据APIDemo 中的例子更改而来,主要是加入了我对透视投影和坐标系的理解。

1. Activity

@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);

mGLView = new GLSurfaceView(this);
mGLView.setEGLConfigChooser(false);
mGLView.setRenderer(new StaticTriangleRenderer(this));
setContentView(mGLView);
}


2. RenderView, GLSurface

public class StaticTriangleRenderer extends GLSurfaceView implements GLSurfaceView.Renderer{

private Context mContext;
private Triangle mTriangle;
private int mTextureID;
private GL11 mGL;

public StaticTriangleRenderer(Context context) {
super(context);

mContext = context;
mTriangle = new Triangle();
// We want an 8888 pixel format because that's required for
// a translucent window.
// And we want a depth buffer.
setBackgroundDrawable(null);
setFocusable(true);
setEGLConfigChooser(8, 8, 8, 8, 16, 0);
setRenderer(this);
setRenderMode(GLSurfaceView.RENDERMODE_WHEN_DIRTY);
// Use a surface format with an Alpha channel:
getHolder().setFormat(PixelFormat.TRANSLUCENT);
}

public void onSurfaceCreated(GL10 gl, EGLConfig config) {
/*
* By default, OpenGL enables features that improve quality
* but reduce performance. One might want to tweak that
* especially on software renderer.
*/
//gl.glDisable(gl.GL_DITHER);

/*
* Some one-time OpenGL initialization can be made here
* probably based on features of this particular context
*/
gl.glHint(gl.GL_PERSPECTIVE_CORRECTION_HINT,
gl.GL_FASTEST);

gl.glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
gl.glShadeModel(gl.GL_SMOOTH);
gl.glEnable(gl.GL_DEPTH_TEST);
gl.glEnable(GL_TEXTURE_2D);

/*
* Create our texture. This has to be done each time the
* surface is created.
*/

int[] textures = new int[1];
gl.glGenTextures(1, textures, 0);

mTextureID = textures[0];
gl.glBindTexture(GL_TEXTURE_2D, mTextureID);

gl.glTexParameterf(GL_TEXTURE_2D, gl.GL_TEXTURE_MIN_FILTER,
gl.GL_NEAREST);
gl.glTexParameterf(GL_TEXTURE_2D,
gl.GL_TEXTURE_MAG_FILTER,
gl.GL_LINEAR);

gl.glTexParameterf(GL_TEXTURE_2D, gl.GL_TEXTURE_WRAP_S,
gl.GL_CLAMP_TO_EDGE);
gl.glTexParameterf(GL_TEXTURE_2D, gl.GL_TEXTURE_WRAP_T,
gl.GL_CLAMP_TO_EDGE);

gl.glTexEnvx(gl.GL_TEXTURE_ENV, gl.GL_TEXTURE_ENV_MODE,
GL11.GL_REPLACE);

Bitmap bmp =
BitmapFactory.decodeResource(mContext.getResources(), R.drawable.myvideo);

int width = bmp.getWidth();
int height = bmp.getHeight();

Matrix matrix = new Matrix();

float scaleWidth = ((float) 128) / width;
float scaleHeight = ((float) 128) / height;

matrix.postScale(scaleWidth, scaleHeight);
Bitmap newbmp = Bitmap.createBitmap(bmp, 0, 0, width, height,
matrix, true);
GLUtils.texImage2D(GL10.GL_TEXTURE_2D, 0, newbmp, 0);
}

public void onDrawFrame(GL10 gl) {
/*
* By default, OpenGL enables features that improve quality
* but reduce performance. One might want to tweak that
* especially on software renderer.
*/
gl.glDisable(gl.GL_DITHER);

/*
* Usually, the first thing one might want to do is to clear
* the screen. The most efficient way of doing this is to use
* glClear().
*/

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

/*
* Now we're ready to draw some 3D objects
*/

gl.glMatrixMode(gl.GL_MODELVIEW);
gl.glLoadIdentity();

//portalDrawFrame(gl);
GLU.gluLookAt(gl, 	0, 0, 4,		// The position of the eye
0f, 0f, 0f,		// Eye to see the pointer
0f, 1.0f, 0.0f);// The direction of the see

gl.glEnableClientState(gl.GL_VERTEX_ARRAY);
gl.glEnableClientState(gl.GL_TEXTURE_COORD_ARRAY);

long time = SystemClock.uptimeMillis() % 4000L;
float angle = 0.090f * ((int) time);
gl.glRotatef(angle, 0, 0, 1.0f);

gl.glEnable(GL_TEXTURE_2D);
gl.glBindTexture(GL11.GL_TEXTURE_2D, mTextureID);

mTriangle.draw(gl);
}

public void onSurfaceChanged(GL10 gl, int w, int h) {
gl.glViewport(0, 0, w, h);

/*
* Set our projection matrix. This doesn't have to be done
* each time we draw, but usually a new projection needs to
* be set when the viewport is resized.
*/

float ratio = (float) w / h;
gl.glMatrixMode(gl.GL_PROJECTION);
gl.glLoadIdentity();
GLU.gluPerspective(gl, 90, ratio, 4, 100);
}

static class Triangle {
public Triangle() {

// Buffers to be passed to gl*Pointer() functions
// must be direct, i.e., they must be placed on the
// native heap where the garbage collector cannot
// move them.
//
// Buffers with multi-byte datatypes (e.g., short, int, float)
// must have their byte order set to native order

ByteBuffer vbb = ByteBuffer.allocateDirect(VERTS * 3 * 4);
vbb.order(ByteOrder.nativeOrder());
mFVertexBuffer = vbb.asFloatBuffer();

ByteBuffer tbb = ByteBuffer.allocateDirect(VERTS * 2 * 4);
tbb.order(ByteOrder.nativeOrder());
mTexBuffer = tbb.asFloatBuffer();

ByteBuffer ibb = ByteBuffer.allocateDirect(VERTS * 2);
ibb.order(ByteOrder.nativeOrder());
mIndexBuffer = ibb.asShortBuffer();

// A unit-sided equilateral triangle centered on the origin.
float[] coords = {
// X,  Y, Z
-2.0f, 	-3.0f, 	-4.0f,
2.0f, 	-3.0f, 	-4.0f,
2.0f,  3.0f, 	-4.0f,
-2.0f, 3.0f, 	-4.0f};

float[] texture = {
0.0f, 0.0f,
0.0f, 1.0f,
1.0f, 1.0f,
1.0f, 0.0f};

mFVertexBuffer.put(coords);
mTexBuffer.put(texture);

for(int i = 0; i < VERTS; i++) {
mIndexBuffer.put((short) i);
}

mFVertexBuffer.position(0);
mTexBuffer.position(0);
mIndexBuffer.position(0);
}

public void draw(GL10 gl) {
gl.glVertexPointer(3, GL_FLOAT, 0, mFVertexBuffer);
glTexCoordPointer(2, GL_FLOAT, 0, mTexBuffer);
gl.glDrawElements(GL11.GL_TRIANGLE_FAN, VERTS, GL_UNSIGNED_SHORT, mIndexBuffer);
//gl.glDrawArrays(GL11.GL_TRIANGLE_FAN, 0, VERTS);
}

private final static int VERTS = 4;
private FloatBuffer mFVertexBuffer;
private FloatBuffer mTexBuffer;
private ShortBuffer mIndexBuffer;
}
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: