1cfd74d65d832137e20e193c960802afba73b5d38sm/* 23c1e67e433728684b5f228c5d4f3e5b1457bb271sm * Copyright (C) 2010 The Android Open Source Project 3cfd74d65d832137e20e193c960802afba73b5d38sm * 4cfd74d65d832137e20e193c960802afba73b5d38sm * Licensed under the Apache License, Version 2.0 (the "License"); 5cfd74d65d832137e20e193c960802afba73b5d38sm * you may not use this file except in compliance with the License. 6cfd74d65d832137e20e193c960802afba73b5d38sm * You may obtain a copy of the License at 7cfd74d65d832137e20e193c960802afba73b5d38sm * 8cfd74d65d832137e20e193c960802afba73b5d38sm * http://www.apache.org/licenses/LICENSE-2.0 9cfd74d65d832137e20e193c960802afba73b5d38sm * 10cfd74d65d832137e20e193c960802afba73b5d38sm * Unless required by applicable law or agreed to in writing, software 11cfd74d65d832137e20e193c960802afba73b5d38sm * distributed under the License is distributed on an "AS IS" BASIS, 12cfd74d65d832137e20e193c960802afba73b5d38sm * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13cfd74d65d832137e20e193c960802afba73b5d38sm * See the License for the specific language governing permissions and 14cfd74d65d832137e20e193c960802afba73b5d38sm * limitations under the License. 15cfd74d65d832137e20e193c960802afba73b5d38sm */ 16cfd74d65d832137e20e193c960802afba73b5d38sm 17cfd74d65d832137e20e193c960802afba73b5d38smpackage com.replica.replicaisland; 18cfd74d65d832137e20e193c960802afba73b5d38sm 19cfd74d65d832137e20e193c960802afba73b5d38smimport java.nio.Buffer; 20cfd74d65d832137e20e193c960802afba73b5d38smimport java.nio.ByteBuffer; 21cfd74d65d832137e20e193c960802afba73b5d38smimport java.nio.ByteOrder; 22cfd74d65d832137e20e193c960802afba73b5d38smimport java.nio.CharBuffer; 23cfd74d65d832137e20e193c960802afba73b5d38smimport java.nio.FloatBuffer; 24cfd74d65d832137e20e193c960802afba73b5d38smimport java.nio.IntBuffer; 25cfd74d65d832137e20e193c960802afba73b5d38sm 26cfd74d65d832137e20e193c960802afba73b5d38smimport javax.microedition.khronos.opengles.GL10; 27cfd74d65d832137e20e193c960802afba73b5d38smimport javax.microedition.khronos.opengles.GL11; 28cfd74d65d832137e20e193c960802afba73b5d38sm 296cb78e547641bcab6f18ec34badca0840e000992Keun young Parkimport android.util.Log; 306cb78e547641bcab6f18ec34badca0840e000992Keun young Park 31cfd74d65d832137e20e193c960802afba73b5d38sm/** 32cfd74d65d832137e20e193c960802afba73b5d38sm * A 2D rectangular mesh. Can be drawn textured or untextured. 33cfd74d65d832137e20e193c960802afba73b5d38sm * This version is modified from the original Grid.java (found in 34cfd74d65d832137e20e193c960802afba73b5d38sm * the SpriteText package in the APIDemos Android sample) to support hardware 35cfd74d65d832137e20e193c960802afba73b5d38sm * vertex buffers and to insert edges between grid squares for tiling. 36cfd74d65d832137e20e193c960802afba73b5d38sm */ 37cfd74d65d832137e20e193c960802afba73b5d38smclass Grid { 38cfd74d65d832137e20e193c960802afba73b5d38sm private static final int FLOAT_SIZE = 4; 39cfd74d65d832137e20e193c960802afba73b5d38sm private static final int FIXED_SIZE = 4; 40cfd74d65d832137e20e193c960802afba73b5d38sm private static final int CHAR_SIZE = 2; 41cfd74d65d832137e20e193c960802afba73b5d38sm 42cfd74d65d832137e20e193c960802afba73b5d38sm private FloatBuffer mFloatVertexBuffer; 43cfd74d65d832137e20e193c960802afba73b5d38sm private FloatBuffer mFloatTexCoordBuffer; 44cfd74d65d832137e20e193c960802afba73b5d38sm private IntBuffer mFixedVertexBuffer; 45cfd74d65d832137e20e193c960802afba73b5d38sm private IntBuffer mFixedTexCoordBuffer; 46cfd74d65d832137e20e193c960802afba73b5d38sm private CharBuffer mIndexBuffer; 47cfd74d65d832137e20e193c960802afba73b5d38sm 48cfd74d65d832137e20e193c960802afba73b5d38sm private Buffer mVertexBuffer; 49cfd74d65d832137e20e193c960802afba73b5d38sm private Buffer mTexCoordBuffer; 50cfd74d65d832137e20e193c960802afba73b5d38sm private int mCoordinateSize; 51cfd74d65d832137e20e193c960802afba73b5d38sm private int mCoordinateType; 52cfd74d65d832137e20e193c960802afba73b5d38sm 53cfd74d65d832137e20e193c960802afba73b5d38sm private int mVertsAcross; 54cfd74d65d832137e20e193c960802afba73b5d38sm private int mVertsDown; 55cfd74d65d832137e20e193c960802afba73b5d38sm private int mIndexCount; 56cfd74d65d832137e20e193c960802afba73b5d38sm private boolean mUseHardwareBuffers; 57cfd74d65d832137e20e193c960802afba73b5d38sm private int mVertBufferIndex; 58cfd74d65d832137e20e193c960802afba73b5d38sm private int mIndexBufferIndex; 59cfd74d65d832137e20e193c960802afba73b5d38sm private int mTextureCoordBufferIndex; 60cfd74d65d832137e20e193c960802afba73b5d38sm 61cfd74d65d832137e20e193c960802afba73b5d38sm public Grid(int quadsAcross, int quadsDown, boolean useFixedPoint) { 62cfd74d65d832137e20e193c960802afba73b5d38sm final int vertsAcross = quadsAcross * 2; 63cfd74d65d832137e20e193c960802afba73b5d38sm final int vertsDown = quadsDown * 2; 64cfd74d65d832137e20e193c960802afba73b5d38sm if (vertsAcross < 0 || vertsAcross >= 65536) { 65cfd74d65d832137e20e193c960802afba73b5d38sm throw new IllegalArgumentException("quadsAcross"); 66cfd74d65d832137e20e193c960802afba73b5d38sm } 67cfd74d65d832137e20e193c960802afba73b5d38sm if (vertsDown < 0 || vertsDown >= 65536) { 68cfd74d65d832137e20e193c960802afba73b5d38sm throw new IllegalArgumentException("quadsDown"); 69cfd74d65d832137e20e193c960802afba73b5d38sm } 70cfd74d65d832137e20e193c960802afba73b5d38sm if (vertsAcross * vertsDown >= 65536) { 71cfd74d65d832137e20e193c960802afba73b5d38sm throw new IllegalArgumentException("quadsAcross * quadsDown >= 32768"); 72cfd74d65d832137e20e193c960802afba73b5d38sm } 73cfd74d65d832137e20e193c960802afba73b5d38sm 74cfd74d65d832137e20e193c960802afba73b5d38sm mUseHardwareBuffers = false; 75cfd74d65d832137e20e193c960802afba73b5d38sm 76cfd74d65d832137e20e193c960802afba73b5d38sm mVertsAcross = vertsAcross; 77cfd74d65d832137e20e193c960802afba73b5d38sm mVertsDown = vertsDown; 78cfd74d65d832137e20e193c960802afba73b5d38sm int size = vertsAcross * vertsDown; 79cfd74d65d832137e20e193c960802afba73b5d38sm 80cfd74d65d832137e20e193c960802afba73b5d38sm 81cfd74d65d832137e20e193c960802afba73b5d38sm if (useFixedPoint) { 82cfd74d65d832137e20e193c960802afba73b5d38sm mFixedVertexBuffer = ByteBuffer.allocateDirect(FIXED_SIZE * size * 3) 83cfd74d65d832137e20e193c960802afba73b5d38sm .order(ByteOrder.nativeOrder()).asIntBuffer(); 84cfd74d65d832137e20e193c960802afba73b5d38sm mFixedTexCoordBuffer = ByteBuffer.allocateDirect(FIXED_SIZE * size * 2) 85cfd74d65d832137e20e193c960802afba73b5d38sm .order(ByteOrder.nativeOrder()).asIntBuffer(); 86cfd74d65d832137e20e193c960802afba73b5d38sm 87cfd74d65d832137e20e193c960802afba73b5d38sm mVertexBuffer = mFixedVertexBuffer; 88cfd74d65d832137e20e193c960802afba73b5d38sm mTexCoordBuffer = mFixedTexCoordBuffer; 89cfd74d65d832137e20e193c960802afba73b5d38sm mCoordinateSize = FIXED_SIZE; 90cfd74d65d832137e20e193c960802afba73b5d38sm mCoordinateType = GL10.GL_FIXED; 91cfd74d65d832137e20e193c960802afba73b5d38sm 92cfd74d65d832137e20e193c960802afba73b5d38sm } else { 93cfd74d65d832137e20e193c960802afba73b5d38sm mFloatVertexBuffer = ByteBuffer.allocateDirect(FLOAT_SIZE * size * 3) 94cfd74d65d832137e20e193c960802afba73b5d38sm .order(ByteOrder.nativeOrder()).asFloatBuffer(); 95cfd74d65d832137e20e193c960802afba73b5d38sm mFloatTexCoordBuffer = ByteBuffer.allocateDirect(FLOAT_SIZE * size * 2) 96cfd74d65d832137e20e193c960802afba73b5d38sm .order(ByteOrder.nativeOrder()).asFloatBuffer(); 97cfd74d65d832137e20e193c960802afba73b5d38sm 98cfd74d65d832137e20e193c960802afba73b5d38sm mVertexBuffer = mFloatVertexBuffer; 99cfd74d65d832137e20e193c960802afba73b5d38sm mTexCoordBuffer = mFloatTexCoordBuffer; 100cfd74d65d832137e20e193c960802afba73b5d38sm mCoordinateSize = FLOAT_SIZE; 101cfd74d65d832137e20e193c960802afba73b5d38sm mCoordinateType = GL10.GL_FLOAT; 102cfd74d65d832137e20e193c960802afba73b5d38sm } 103cfd74d65d832137e20e193c960802afba73b5d38sm 104cfd74d65d832137e20e193c960802afba73b5d38sm 105cfd74d65d832137e20e193c960802afba73b5d38sm 106cfd74d65d832137e20e193c960802afba73b5d38sm 107cfd74d65d832137e20e193c960802afba73b5d38sm int quadCount = quadsAcross * quadsDown; 108cfd74d65d832137e20e193c960802afba73b5d38sm int indexCount = quadCount * 6; 109cfd74d65d832137e20e193c960802afba73b5d38sm mIndexCount = indexCount; 110cfd74d65d832137e20e193c960802afba73b5d38sm mIndexBuffer = ByteBuffer.allocateDirect(CHAR_SIZE * indexCount) 111cfd74d65d832137e20e193c960802afba73b5d38sm .order(ByteOrder.nativeOrder()).asCharBuffer(); 112cfd74d65d832137e20e193c960802afba73b5d38sm 113cfd74d65d832137e20e193c960802afba73b5d38sm /* 114cfd74d65d832137e20e193c960802afba73b5d38sm * Initialize triangle list mesh. 115cfd74d65d832137e20e193c960802afba73b5d38sm * 116cfd74d65d832137e20e193c960802afba73b5d38sm * [0]------[1] [2]------[3] ... 117cfd74d65d832137e20e193c960802afba73b5d38sm * | / | | / | 118cfd74d65d832137e20e193c960802afba73b5d38sm * | / | | / | 119cfd74d65d832137e20e193c960802afba73b5d38sm * | / | | / | 120cfd74d65d832137e20e193c960802afba73b5d38sm * [w]-----[w+1] [w+2]----[w+3]... 121cfd74d65d832137e20e193c960802afba73b5d38sm * | | 122cfd74d65d832137e20e193c960802afba73b5d38sm * 123cfd74d65d832137e20e193c960802afba73b5d38sm */ 124cfd74d65d832137e20e193c960802afba73b5d38sm 125cfd74d65d832137e20e193c960802afba73b5d38sm { 126cfd74d65d832137e20e193c960802afba73b5d38sm int i = 0; 127cfd74d65d832137e20e193c960802afba73b5d38sm for (int y = 0; y < quadsDown; y++) { 128cfd74d65d832137e20e193c960802afba73b5d38sm final int indexY = y * 2; 129cfd74d65d832137e20e193c960802afba73b5d38sm for (int x = 0; x < quadsAcross; x++) { 130cfd74d65d832137e20e193c960802afba73b5d38sm final int indexX = x * 2; 131cfd74d65d832137e20e193c960802afba73b5d38sm char a = (char) (indexY * mVertsAcross + indexX); 132cfd74d65d832137e20e193c960802afba73b5d38sm char b = (char) (indexY * mVertsAcross + indexX + 1); 133cfd74d65d832137e20e193c960802afba73b5d38sm char c = (char) ((indexY + 1) * mVertsAcross + indexX); 134cfd74d65d832137e20e193c960802afba73b5d38sm char d = (char) ((indexY + 1) * mVertsAcross + indexX + 1); 135cfd74d65d832137e20e193c960802afba73b5d38sm 136cfd74d65d832137e20e193c960802afba73b5d38sm mIndexBuffer.put(i++, a); 137cfd74d65d832137e20e193c960802afba73b5d38sm mIndexBuffer.put(i++, b); 138cfd74d65d832137e20e193c960802afba73b5d38sm mIndexBuffer.put(i++, c); 139cfd74d65d832137e20e193c960802afba73b5d38sm 140cfd74d65d832137e20e193c960802afba73b5d38sm mIndexBuffer.put(i++, b); 141cfd74d65d832137e20e193c960802afba73b5d38sm mIndexBuffer.put(i++, c); 142cfd74d65d832137e20e193c960802afba73b5d38sm mIndexBuffer.put(i++, d); 143cfd74d65d832137e20e193c960802afba73b5d38sm } 144cfd74d65d832137e20e193c960802afba73b5d38sm } 145cfd74d65d832137e20e193c960802afba73b5d38sm } 146cfd74d65d832137e20e193c960802afba73b5d38sm 147cfd74d65d832137e20e193c960802afba73b5d38sm mVertBufferIndex = 0; 148cfd74d65d832137e20e193c960802afba73b5d38sm } 149cfd74d65d832137e20e193c960802afba73b5d38sm 150cfd74d65d832137e20e193c960802afba73b5d38sm public void set(int quadX, int quadY, float[][] positions, float[][] uvs) { 151cfd74d65d832137e20e193c960802afba73b5d38sm if (quadX < 0 || quadX * 2 >= mVertsAcross) { 152cfd74d65d832137e20e193c960802afba73b5d38sm throw new IllegalArgumentException("quadX"); 153cfd74d65d832137e20e193c960802afba73b5d38sm } 154cfd74d65d832137e20e193c960802afba73b5d38sm if (quadY < 0 || quadY * 2 >= mVertsDown) { 155cfd74d65d832137e20e193c960802afba73b5d38sm throw new IllegalArgumentException("quadY"); 156cfd74d65d832137e20e193c960802afba73b5d38sm } 157cfd74d65d832137e20e193c960802afba73b5d38sm if (positions.length < 4) { 158cfd74d65d832137e20e193c960802afba73b5d38sm throw new IllegalArgumentException("positions"); 159cfd74d65d832137e20e193c960802afba73b5d38sm } 160cfd74d65d832137e20e193c960802afba73b5d38sm if (uvs.length < 4) { 161cfd74d65d832137e20e193c960802afba73b5d38sm throw new IllegalArgumentException("quadY"); 162cfd74d65d832137e20e193c960802afba73b5d38sm } 163cfd74d65d832137e20e193c960802afba73b5d38sm 164cfd74d65d832137e20e193c960802afba73b5d38sm int i = quadX * 2; 165cfd74d65d832137e20e193c960802afba73b5d38sm int j = quadY * 2; 166cfd74d65d832137e20e193c960802afba73b5d38sm 167cfd74d65d832137e20e193c960802afba73b5d38sm setVertex(i, j, positions[0][0], positions[0][1], positions[0][2], uvs[0][0], uvs[0][1]); 168cfd74d65d832137e20e193c960802afba73b5d38sm setVertex(i + 1, j, positions[1][0], positions[1][1], positions[1][2], uvs[1][0], uvs[1][1]); 169cfd74d65d832137e20e193c960802afba73b5d38sm setVertex(i, j + 1, positions[2][0], positions[2][1], positions[2][2], uvs[2][0], uvs[2][1]); 170cfd74d65d832137e20e193c960802afba73b5d38sm setVertex(i + 1, j + 1, positions[3][0], positions[3][1], positions[3][2], uvs[3][0], uvs[3][1]); 171cfd74d65d832137e20e193c960802afba73b5d38sm } 172cfd74d65d832137e20e193c960802afba73b5d38sm 173cfd74d65d832137e20e193c960802afba73b5d38sm 174cfd74d65d832137e20e193c960802afba73b5d38sm private void setVertex(int i, int j, float x, float y, float z, float u, float v) { 175cfd74d65d832137e20e193c960802afba73b5d38sm if (i < 0 || i >= mVertsAcross) { 176cfd74d65d832137e20e193c960802afba73b5d38sm throw new IllegalArgumentException("i"); 177cfd74d65d832137e20e193c960802afba73b5d38sm } 178cfd74d65d832137e20e193c960802afba73b5d38sm if (j < 0 || j >= mVertsDown) { 179cfd74d65d832137e20e193c960802afba73b5d38sm throw new IllegalArgumentException("j"); 180cfd74d65d832137e20e193c960802afba73b5d38sm } 181cfd74d65d832137e20e193c960802afba73b5d38sm 182cfd74d65d832137e20e193c960802afba73b5d38sm final int index = mVertsAcross * j + i; 183cfd74d65d832137e20e193c960802afba73b5d38sm 184cfd74d65d832137e20e193c960802afba73b5d38sm final int posIndex = index * 3; 185cfd74d65d832137e20e193c960802afba73b5d38sm final int texIndex = index * 2; 186cfd74d65d832137e20e193c960802afba73b5d38sm 187cfd74d65d832137e20e193c960802afba73b5d38sm 188cfd74d65d832137e20e193c960802afba73b5d38sm if (mCoordinateType == GL10.GL_FLOAT) { 189cfd74d65d832137e20e193c960802afba73b5d38sm mFloatVertexBuffer.put(posIndex, x); 190cfd74d65d832137e20e193c960802afba73b5d38sm mFloatVertexBuffer.put(posIndex + 1, y); 191cfd74d65d832137e20e193c960802afba73b5d38sm mFloatVertexBuffer.put(posIndex + 2, z); 192cfd74d65d832137e20e193c960802afba73b5d38sm 193cfd74d65d832137e20e193c960802afba73b5d38sm mFloatTexCoordBuffer.put(texIndex, u); 194cfd74d65d832137e20e193c960802afba73b5d38sm mFloatTexCoordBuffer.put(texIndex + 1, v); 195cfd74d65d832137e20e193c960802afba73b5d38sm } else { 196cfd74d65d832137e20e193c960802afba73b5d38sm mFixedVertexBuffer.put(posIndex, (int)(x * (1 << 16))); 197cfd74d65d832137e20e193c960802afba73b5d38sm mFixedVertexBuffer.put(posIndex + 1, (int)(y * (1 << 16))); 198cfd74d65d832137e20e193c960802afba73b5d38sm mFixedVertexBuffer.put(posIndex + 2, (int)(z * (1 << 16))); 199cfd74d65d832137e20e193c960802afba73b5d38sm 200cfd74d65d832137e20e193c960802afba73b5d38sm mFixedTexCoordBuffer.put(texIndex, (int)(u * (1 << 16))); 201cfd74d65d832137e20e193c960802afba73b5d38sm mFixedTexCoordBuffer.put(texIndex + 1, (int)(v * (1 << 16))); 202cfd74d65d832137e20e193c960802afba73b5d38sm } 203cfd74d65d832137e20e193c960802afba73b5d38sm } 204cfd74d65d832137e20e193c960802afba73b5d38sm 205cfd74d65d832137e20e193c960802afba73b5d38sm public static void beginDrawing(GL10 gl, boolean useTexture) { 206cfd74d65d832137e20e193c960802afba73b5d38sm gl.glEnableClientState(GL10.GL_VERTEX_ARRAY); 207cfd74d65d832137e20e193c960802afba73b5d38sm 208cfd74d65d832137e20e193c960802afba73b5d38sm if (useTexture) { 209cfd74d65d832137e20e193c960802afba73b5d38sm gl.glEnableClientState(GL10.GL_TEXTURE_COORD_ARRAY); 210cfd74d65d832137e20e193c960802afba73b5d38sm gl.glEnable(GL10.GL_TEXTURE_2D); 211cfd74d65d832137e20e193c960802afba73b5d38sm } else { 212cfd74d65d832137e20e193c960802afba73b5d38sm gl.glDisableClientState(GL10.GL_TEXTURE_COORD_ARRAY); 213cfd74d65d832137e20e193c960802afba73b5d38sm gl.glDisable(GL10.GL_TEXTURE_2D); 214cfd74d65d832137e20e193c960802afba73b5d38sm } 215cfd74d65d832137e20e193c960802afba73b5d38sm } 216cfd74d65d832137e20e193c960802afba73b5d38sm 217cfd74d65d832137e20e193c960802afba73b5d38sm public void beginDrawingStrips(GL10 gl, boolean useTexture) { 218cfd74d65d832137e20e193c960802afba73b5d38sm beginDrawing(gl, useTexture); 219cfd74d65d832137e20e193c960802afba73b5d38sm if (!mUseHardwareBuffers) { 220cfd74d65d832137e20e193c960802afba73b5d38sm gl.glVertexPointer(3, mCoordinateType, 0, mVertexBuffer); 221cfd74d65d832137e20e193c960802afba73b5d38sm 222cfd74d65d832137e20e193c960802afba73b5d38sm if (useTexture) { 223cfd74d65d832137e20e193c960802afba73b5d38sm gl.glTexCoordPointer(2, mCoordinateType, 0, mTexCoordBuffer); 224cfd74d65d832137e20e193c960802afba73b5d38sm } 225cfd74d65d832137e20e193c960802afba73b5d38sm 226cfd74d65d832137e20e193c960802afba73b5d38sm } else { 227cfd74d65d832137e20e193c960802afba73b5d38sm GL11 gl11 = (GL11)gl; 228cfd74d65d832137e20e193c960802afba73b5d38sm // draw using hardware buffers 229cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glBindBuffer(GL11.GL_ARRAY_BUFFER, mVertBufferIndex); 230cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glVertexPointer(3, mCoordinateType, 0, 0); 231cfd74d65d832137e20e193c960802afba73b5d38sm 232cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glBindBuffer(GL11.GL_ARRAY_BUFFER, mTextureCoordBufferIndex); 233cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glTexCoordPointer(2, mCoordinateType, 0, 0); 234cfd74d65d832137e20e193c960802afba73b5d38sm 235cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glBindBuffer(GL11.GL_ELEMENT_ARRAY_BUFFER, mIndexBufferIndex); 236cfd74d65d832137e20e193c960802afba73b5d38sm } 237cfd74d65d832137e20e193c960802afba73b5d38sm } 238cfd74d65d832137e20e193c960802afba73b5d38sm 239cfd74d65d832137e20e193c960802afba73b5d38sm // Assumes beginDrawingStrips() has been called before this. 240cfd74d65d832137e20e193c960802afba73b5d38sm public void drawStrip(GL10 gl, boolean useTexture, int startIndex, int indexCount) { 241cfd74d65d832137e20e193c960802afba73b5d38sm int count = indexCount; 242cfd74d65d832137e20e193c960802afba73b5d38sm if (startIndex + indexCount >= mIndexCount) { 243cfd74d65d832137e20e193c960802afba73b5d38sm count = mIndexCount - startIndex; 244cfd74d65d832137e20e193c960802afba73b5d38sm } 245cfd74d65d832137e20e193c960802afba73b5d38sm if (!mUseHardwareBuffers) { 246cfd74d65d832137e20e193c960802afba73b5d38sm gl.glDrawElements(GL10.GL_TRIANGLES, count, 247cfd74d65d832137e20e193c960802afba73b5d38sm GL10.GL_UNSIGNED_SHORT, mIndexBuffer.position(startIndex)); 248cfd74d65d832137e20e193c960802afba73b5d38sm } else { 249cfd74d65d832137e20e193c960802afba73b5d38sm GL11 gl11 = (GL11)gl; 250cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glDrawElements(GL11.GL_TRIANGLES, count, 251cfd74d65d832137e20e193c960802afba73b5d38sm GL11.GL_UNSIGNED_SHORT, startIndex * CHAR_SIZE); 252cfd74d65d832137e20e193c960802afba73b5d38sm 253cfd74d65d832137e20e193c960802afba73b5d38sm } 254cfd74d65d832137e20e193c960802afba73b5d38sm } 255cfd74d65d832137e20e193c960802afba73b5d38sm 256cfd74d65d832137e20e193c960802afba73b5d38sm public void draw(GL10 gl, boolean useTexture) { 257cfd74d65d832137e20e193c960802afba73b5d38sm if (!mUseHardwareBuffers) { 258cfd74d65d832137e20e193c960802afba73b5d38sm gl.glVertexPointer(3, mCoordinateType, 0, mVertexBuffer); 259cfd74d65d832137e20e193c960802afba73b5d38sm 260cfd74d65d832137e20e193c960802afba73b5d38sm if (useTexture) { 261cfd74d65d832137e20e193c960802afba73b5d38sm gl.glTexCoordPointer(2, mCoordinateType, 0, mTexCoordBuffer); 262cfd74d65d832137e20e193c960802afba73b5d38sm } 263cfd74d65d832137e20e193c960802afba73b5d38sm 264cfd74d65d832137e20e193c960802afba73b5d38sm gl.glDrawElements(GL10.GL_TRIANGLES, mIndexCount, 265cfd74d65d832137e20e193c960802afba73b5d38sm GL10.GL_UNSIGNED_SHORT, mIndexBuffer); 266cfd74d65d832137e20e193c960802afba73b5d38sm } else { 267cfd74d65d832137e20e193c960802afba73b5d38sm GL11 gl11 = (GL11)gl; 268cfd74d65d832137e20e193c960802afba73b5d38sm // draw using hardware buffers 269cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glBindBuffer(GL11.GL_ARRAY_BUFFER, mVertBufferIndex); 270cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glVertexPointer(3, mCoordinateType, 0, 0); 271cfd74d65d832137e20e193c960802afba73b5d38sm 272cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glBindBuffer(GL11.GL_ARRAY_BUFFER, mTextureCoordBufferIndex); 273cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glTexCoordPointer(2, mCoordinateType, 0, 0); 274cfd74d65d832137e20e193c960802afba73b5d38sm 275cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glBindBuffer(GL11.GL_ELEMENT_ARRAY_BUFFER, mIndexBufferIndex); 276cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glDrawElements(GL11.GL_TRIANGLES, mIndexCount, 277cfd74d65d832137e20e193c960802afba73b5d38sm GL11.GL_UNSIGNED_SHORT, 0); 278cfd74d65d832137e20e193c960802afba73b5d38sm 279cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glBindBuffer(GL11.GL_ARRAY_BUFFER, 0); 280cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glBindBuffer(GL11.GL_ELEMENT_ARRAY_BUFFER, 0); 281cfd74d65d832137e20e193c960802afba73b5d38sm 282cfd74d65d832137e20e193c960802afba73b5d38sm 283cfd74d65d832137e20e193c960802afba73b5d38sm } 284cfd74d65d832137e20e193c960802afba73b5d38sm } 285cfd74d65d832137e20e193c960802afba73b5d38sm 286cfd74d65d832137e20e193c960802afba73b5d38sm public static void endDrawing(GL10 gl) { 287cfd74d65d832137e20e193c960802afba73b5d38sm gl.glDisableClientState(GL10.GL_VERTEX_ARRAY); 288cfd74d65d832137e20e193c960802afba73b5d38sm } 289cfd74d65d832137e20e193c960802afba73b5d38sm 290cfd74d65d832137e20e193c960802afba73b5d38sm public boolean usingHardwareBuffers() { 291cfd74d65d832137e20e193c960802afba73b5d38sm return mUseHardwareBuffers; 292cfd74d65d832137e20e193c960802afba73b5d38sm } 293cfd74d65d832137e20e193c960802afba73b5d38sm 294cfd74d65d832137e20e193c960802afba73b5d38sm /** 295cfd74d65d832137e20e193c960802afba73b5d38sm * When the OpenGL ES device is lost, GL handles become invalidated. 296cfd74d65d832137e20e193c960802afba73b5d38sm * In that case, we just want to "forget" the old handles (without 297cfd74d65d832137e20e193c960802afba73b5d38sm * explicitly deleting them) and make new ones. 298cfd74d65d832137e20e193c960802afba73b5d38sm */ 299cfd74d65d832137e20e193c960802afba73b5d38sm public void invalidateHardwareBuffers() { 300cfd74d65d832137e20e193c960802afba73b5d38sm mVertBufferIndex = 0; 301cfd74d65d832137e20e193c960802afba73b5d38sm mIndexBufferIndex = 0; 302cfd74d65d832137e20e193c960802afba73b5d38sm mTextureCoordBufferIndex = 0; 303cfd74d65d832137e20e193c960802afba73b5d38sm mUseHardwareBuffers = false; 304cfd74d65d832137e20e193c960802afba73b5d38sm } 305cfd74d65d832137e20e193c960802afba73b5d38sm 306cfd74d65d832137e20e193c960802afba73b5d38sm /** 307cfd74d65d832137e20e193c960802afba73b5d38sm * Deletes the hardware buffers allocated by this object (if any). 308cfd74d65d832137e20e193c960802afba73b5d38sm */ 309cfd74d65d832137e20e193c960802afba73b5d38sm public void releaseHardwareBuffers(GL10 gl) { 310cfd74d65d832137e20e193c960802afba73b5d38sm if (mUseHardwareBuffers) { 311cfd74d65d832137e20e193c960802afba73b5d38sm if (gl instanceof GL11) { 312cfd74d65d832137e20e193c960802afba73b5d38sm GL11 gl11 = (GL11)gl; 313cfd74d65d832137e20e193c960802afba73b5d38sm int[] buffer = new int[1]; 314cfd74d65d832137e20e193c960802afba73b5d38sm buffer[0] = mVertBufferIndex; 315cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glDeleteBuffers(1, buffer, 0); 316cfd74d65d832137e20e193c960802afba73b5d38sm 317cfd74d65d832137e20e193c960802afba73b5d38sm buffer[0] = mTextureCoordBufferIndex; 318cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glDeleteBuffers(1, buffer, 0); 319cfd74d65d832137e20e193c960802afba73b5d38sm 320cfd74d65d832137e20e193c960802afba73b5d38sm buffer[0] = mIndexBufferIndex; 321cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glDeleteBuffers(1, buffer, 0); 322cfd74d65d832137e20e193c960802afba73b5d38sm } 323cfd74d65d832137e20e193c960802afba73b5d38sm 324cfd74d65d832137e20e193c960802afba73b5d38sm invalidateHardwareBuffers(); 325cfd74d65d832137e20e193c960802afba73b5d38sm } 326cfd74d65d832137e20e193c960802afba73b5d38sm } 327cfd74d65d832137e20e193c960802afba73b5d38sm 328cfd74d65d832137e20e193c960802afba73b5d38sm /** 329cfd74d65d832137e20e193c960802afba73b5d38sm * Allocates hardware buffers on the graphics card and fills them with 330cfd74d65d832137e20e193c960802afba73b5d38sm * data if a buffer has not already been previously allocated. Note that 331cfd74d65d832137e20e193c960802afba73b5d38sm * this function uses the GL_OES_vertex_buffer_object extension, which is 332cfd74d65d832137e20e193c960802afba73b5d38sm * not guaranteed to be supported on every device. 333cfd74d65d832137e20e193c960802afba73b5d38sm * @param gl A pointer to the OpenGL ES context. 334cfd74d65d832137e20e193c960802afba73b5d38sm */ 335cfd74d65d832137e20e193c960802afba73b5d38sm public void generateHardwareBuffers(GL10 gl) { 336cfd74d65d832137e20e193c960802afba73b5d38sm if (!mUseHardwareBuffers) { 337cfd74d65d832137e20e193c960802afba73b5d38sm DebugLog.i("Grid", "Using Hardware Buffers"); 338cfd74d65d832137e20e193c960802afba73b5d38sm if (gl instanceof GL11) { 339cfd74d65d832137e20e193c960802afba73b5d38sm GL11 gl11 = (GL11)gl; 340cfd74d65d832137e20e193c960802afba73b5d38sm int[] buffer = new int[1]; 341cfd74d65d832137e20e193c960802afba73b5d38sm 342cfd74d65d832137e20e193c960802afba73b5d38sm // Allocate and fill the vertex buffer. 343cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glGenBuffers(1, buffer, 0); 344cfd74d65d832137e20e193c960802afba73b5d38sm mVertBufferIndex = buffer[0]; 345cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glBindBuffer(GL11.GL_ARRAY_BUFFER, mVertBufferIndex); 3466cb78e547641bcab6f18ec34badca0840e000992Keun young Park final int vertexSize = mVertexBuffer.capacity() * mCoordinateSize; 3476cb78e547641bcab6f18ec34badca0840e000992Keun young Park // too fast task switching leaves buffers in the middle pos which 3486cb78e547641bcab6f18ec34badca0840e000992Keun young Park // crashes app 3496cb78e547641bcab6f18ec34badca0840e000992Keun young Park mVertexBuffer.position(0); 350cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glBufferData(GL11.GL_ARRAY_BUFFER, vertexSize, 351cfd74d65d832137e20e193c960802afba73b5d38sm mVertexBuffer, GL11.GL_STATIC_DRAW); 352cfd74d65d832137e20e193c960802afba73b5d38sm 353cfd74d65d832137e20e193c960802afba73b5d38sm // Allocate and fill the texture coordinate buffer. 354cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glGenBuffers(1, buffer, 0); 355cfd74d65d832137e20e193c960802afba73b5d38sm mTextureCoordBufferIndex = buffer[0]; 356cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glBindBuffer(GL11.GL_ARRAY_BUFFER, 357cfd74d65d832137e20e193c960802afba73b5d38sm mTextureCoordBufferIndex); 358cfd74d65d832137e20e193c960802afba73b5d38sm final int texCoordSize = 359cfd74d65d832137e20e193c960802afba73b5d38sm mTexCoordBuffer.capacity() * mCoordinateSize; 3606cb78e547641bcab6f18ec34badca0840e000992Keun young Park mTexCoordBuffer.position(0); 361cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glBufferData(GL11.GL_ARRAY_BUFFER, texCoordSize, 362cfd74d65d832137e20e193c960802afba73b5d38sm mTexCoordBuffer, GL11.GL_STATIC_DRAW); 363cfd74d65d832137e20e193c960802afba73b5d38sm 364cfd74d65d832137e20e193c960802afba73b5d38sm // Unbind the array buffer. 365cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glBindBuffer(GL11.GL_ARRAY_BUFFER, 0); 366cfd74d65d832137e20e193c960802afba73b5d38sm 367cfd74d65d832137e20e193c960802afba73b5d38sm // Allocate and fill the index buffer. 368cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glGenBuffers(1, buffer, 0); 369cfd74d65d832137e20e193c960802afba73b5d38sm mIndexBufferIndex = buffer[0]; 370cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glBindBuffer(GL11.GL_ELEMENT_ARRAY_BUFFER, 371cfd74d65d832137e20e193c960802afba73b5d38sm mIndexBufferIndex); 372cfd74d65d832137e20e193c960802afba73b5d38sm // A char is 2 bytes. 373cfd74d65d832137e20e193c960802afba73b5d38sm final int indexSize = mIndexBuffer.capacity() * 2; 3746cb78e547641bcab6f18ec34badca0840e000992Keun young Park 3756cb78e547641bcab6f18ec34badca0840e000992Keun young Park mIndexBuffer.position(0); 376cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glBufferData(GL11.GL_ELEMENT_ARRAY_BUFFER, indexSize, mIndexBuffer, 377cfd74d65d832137e20e193c960802afba73b5d38sm GL11.GL_STATIC_DRAW); 378cfd74d65d832137e20e193c960802afba73b5d38sm 379cfd74d65d832137e20e193c960802afba73b5d38sm // Unbind the element array buffer. 380cfd74d65d832137e20e193c960802afba73b5d38sm gl11.glBindBuffer(GL11.GL_ELEMENT_ARRAY_BUFFER, 0); 381cfd74d65d832137e20e193c960802afba73b5d38sm 382cfd74d65d832137e20e193c960802afba73b5d38sm mUseHardwareBuffers = true; 383cfd74d65d832137e20e193c960802afba73b5d38sm 384cfd74d65d832137e20e193c960802afba73b5d38sm assert mVertBufferIndex != 0; 385cfd74d65d832137e20e193c960802afba73b5d38sm assert mTextureCoordBufferIndex != 0; 386cfd74d65d832137e20e193c960802afba73b5d38sm assert mIndexBufferIndex != 0; 387cfd74d65d832137e20e193c960802afba73b5d38sm assert gl11.glGetError() == 0; 388cfd74d65d832137e20e193c960802afba73b5d38sm 389cfd74d65d832137e20e193c960802afba73b5d38sm 390cfd74d65d832137e20e193c960802afba73b5d38sm } 391cfd74d65d832137e20e193c960802afba73b5d38sm } 392cfd74d65d832137e20e193c960802afba73b5d38sm } 393cfd74d65d832137e20e193c960802afba73b5d38sm 394cfd74d65d832137e20e193c960802afba73b5d38sm} 395