我对android和OGLES2.0
有一点了解,但是当我画一张照片大概需要0.4毫秒。因此,我可以在16ms内仅绘制40张图片,以便为我的游戏获得60fps。
这是我的GLRenderer
代码:
重要的部分是Render-method和Sprite Class。
public class GLRenderer implements Renderer {
// Our matrices
private final float[] mtrxProjection = new float[16];
private final float[] mtrxView = new float[16];
private final float[] mtrxProjectionAndView = new float[16];
// Geometric variables
public static int[] vertices;
public static short[] indices;
public static int[] uvs;
public IntBuffer vertexBuffer;
public ShortBuffer drawListBuffer;
public IntBuffer uvBuffer;
public List<Sprite> sprites;
public int[] texturenames;
public MainActivity mainActivity;
// Our screenresolution
float mScreenWidth = 1280;
float mScreenHeight = 720;
float ssu = 1.0f;
float ssx = 1.0f;
float ssy = 1.0f;
float swp = 1280.0f;
float shp = 720.0f;
Update update;
Images images;
// Misc
Context mContext;
long mLastTime;
int mProgram;
public GLRenderer (MainActivity mainActivity) {
this.mContext = mainActivity;
this.mainActivity = mainActivity;
this.mLastTime = System.currentTimeMillis() + 100;
this.sprites = new ArrayList<Sprite>();
}
public void onPause () {
/* Do stuff to pause the renderer */
}
public void onResume () {
/* Do stuff to resume the renderer */
this.mLastTime = System.currentTimeMillis();
}
@Override
public void onDrawFrame (GL10 unused) {
// Get the current time
long now = System.currentTimeMillis();
// We should make sure we are valid and sane
if (this.mLastTime > now) return;
// Get the amount of time the last frame took.
long elapsed = now - this.mLastTime;
System.out.println(elapsed);
// clear Screen and Depth Buffer, we have set the clear color as black.
GLES20.glClear(GLES20.GL_COLOR_BUFFER_BIT | GLES20.GL_DEPTH_BUFFER_BIT);
// Drawing all static things like the background
drawStatics();
for (Opponent opponent: this.update.opponents) {
int position = this.sprites.indexOf(opponent.getSprite());
// Rotate the sprite
this.sprites.get(position).rotate((float) Math.toRadians(opponent.getAngle()));
// Create the image information
SetupImage(opponent.getPicture(), 0);
// Update our example
UpdateSprite(position);
// Render our example
Render(this.mtrxProjectionAndView, 0);
}
for (Tower tower: this.update.towers) {
long a = System.nanoTime();
int position = this.sprites.indexOf(tower.getSprite());
// Rotate the sprite
this.sprites.get(position).rotate((float) Math.toRadians(tower.getAngle()));
// Create the image information
SetupImage(tower.getPicture(), 0);
// Update our example
UpdateSprite(position);
// Render our example
Render(this.mtrxProjectionAndView, 0);
System.out.println("time: " + (System.nanoTime() - a));
}
for (Bullet bullet: this.update.bullets) {
int position = this.sprites.indexOf(bullet.getSprite());
// Rotate the sprite
this.sprites.get(position).rotate((float) Math.toRadians(bullet.getAngle()));
// Create the image information
SetupImage(bullet.getPicture(), 0);
// Update our example
UpdateSprite(position);
// Render our example
Render(this.mtrxProjectionAndView, 0);
}
for (SuperExplosion explosion: this.update.explosions) {
int position = this.sprites.indexOf(explosion.getSprite());
// Rotate the sprite
// sprites.get(position).rotate((float)Math.toRadians(explosion.getAngle()));
// Create the image information
SetupImage(explosion.getPicture(), 0);
// Update our example
UpdateSprite(position);
// Render our example
Render(this.mtrxProjectionAndView, 0);
}
drawStatics2();
// Save the current time to see how long it took :).
this.mLastTime = now;
// System.out.println("höhe "+mScreenHeight+" breite "+ mScreenWidth);
}
private void drawStatics () {
// Ground
// Update our example
long h = System.nanoTime();
UpdateSprite(0);
// for (int i = 0; i < vertices.length; i++) {
// System.out.println("vertices [" + i + "]: " + vertices[i]);
// }
// Render our example
Render(this.mtrxProjectionAndView, 1);
System.out.println("time: " + (System.nanoTime() - h));
// Bar
// Update our example
UpdateSprite(1);
// Render our example
Render(this.mtrxProjectionAndView, 2);
if (!this.update.upgrade) {
if (this.update.normalSpeed) {
// Update our example
UpdateSprite(2);
// Render our example
Render(this.mtrxProjectionAndView, 3);
} else {
// Update our example
UpdateSprite(3);
// Render our example
Render(this.mtrxProjectionAndView, 4);
}
if (!this.update.start) {
// Update our example
UpdateSprite(4);
// Render our example
Render(this.mtrxProjectionAndView, 5);
}
}
// UpgradeBar
if (this.update.upgrade) {
// Update our example
UpdateSprite(6);
// Render our example
Render(this.mtrxProjectionAndView, 7);
}
h = System.nanoTime();
// Bunny1
// Update our example
UpdateSprite(7);
// Render our example
Render(this.mtrxProjectionAndView, 8);
System.out.println("time bunny1 " + (System.nanoTime() - h));
// CarrotTower
// Update our example
UpdateSprite(8);
// Render our example
Render(this.mtrxProjectionAndView, 9);
// MineThrower
// Update our example
UpdateSprite(9);
// Render our example
Render(this.mtrxProjectionAndView, 10);
// BunnyKing
// Update our example
UpdateSprite(10);
// Render our example
Render(this.mtrxProjectionAndView, 11);
}
private void drawStatics2 () {
// Life
// Update our example
UpdateSprite(5);
// Render our example
Render(this.mtrxProjectionAndView, 6);
}
private void Render (float[] m, int index) {
// get handle to vertex shader's vPosition member
int mPositionHandle = GLES20.glGetAttribLocation(riGraphicTools.sp_Image, "vPosition");
// Enable generic vertex attribute array
GLES20.glEnableVertexAttribArray(mPositionHandle);
// Prepare the triangle coordinate data
GLES20.glVertexAttribPointer(mPositionHandle, 3, GLES20.GL_INT, false, 0, this.vertexBuffer);
// Get handle to texture coordinates location
int mTexCoordLoc = GLES20.glGetAttribLocation(riGraphicTools.sp_Image, "a_texCoord");
// Enable generic vertex attribute array
GLES20.glEnableVertexAttribArray(mTexCoordLoc);
// Prepare the texturecoordinates
GLES20.glVertexAttribPointer(mTexCoordLoc, 2, GLES20.GL_INT, false, 0, this.uvBuffer);
// Get handle to shape's transformation matrix
int mtrxhandle = GLES20.glGetUniformLocation(riGraphicTools.sp_Image, "uMVPMatrix");
// Apply the projection and view transformation
GLES20.glUniformMatrix4fv(mtrxhandle, 1, false, m, 0);
// Get handle to textures locations
int mSamplerLoc = GLES20.glGetUniformLocation(riGraphicTools.sp_Image, "s_texture");
// Set the sampler texture unit to 0, where we have saved the texture.
GLES20.glUniform1i(mSamplerLoc, index);
GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, this.texturenames[index]);
// Set filtering
GLES20.glTexParameteri(GLES20.GL_TEXTURE_2D, GLES20.GL_TEXTURE_MIN_FILTER, GLES20.GL_LINEAR);
GLES20.glTexParameteri(GLES20.GL_TEXTURE_2D, GLES20.GL_TEXTURE_MAG_FILTER, GLES20.GL_LINEAR);
// Draw the triangle
GLES20.glDrawElements(GLES20.GL_TRIANGLES, indices.length, GLES20.GL_UNSIGNED_SHORT, this.drawListBuffer);
// Disable vertex array
GLES20.glDisableVertexAttribArray(mPositionHandle);
GLES20.glDisableVertexAttribArray(mTexCoordLoc);
}
@Override
public void onSurfaceChanged (GL10 gl, int width, int height) {
// We need to know the current width and height.
this.mScreenWidth = width;
this.mScreenHeight = height;
// Redo the Viewport, making it fullscreen.
GLES20.glViewport(0, 0, (int) this.mScreenWidth, (int) this.mScreenHeight);
// Clear our matrices
for (int i = 0; i < 16; i++) {
this.mtrxProjection[i] = 0.0f;
this.mtrxView[i] = 0.0f;
this.mtrxProjectionAndView[i] = 0.0f;
}
// Setup our screen width and height for normal sprite translation.
Matrix.orthoM(this.mtrxProjection, 0, 0f, this.mScreenWidth, 0.0f, this.mScreenHeight, 0, 50);
// Set the camera position (View matrix)
Matrix.setLookAtM(this.mtrxView, 0, 0f, 0f, 1f, 0f, 0f, 0f, 0f, 1.0f, 0.0f);
// Calculate the projection and view transformation
Matrix.multiplyMM(this.mtrxProjectionAndView, 0, this.mtrxProjection, 0, this.mtrxView, 0);
// Setup our scaling system
SetupScaling();
// Create the GroundSprite
SetupTriangle(this.images.ground_1.getWidth(), this.images.ground_1.getHeight(), 0, 0);
SetupTriangle(this.images.bar1.getWidth(), this.images.bar1.getHeight(), 0, 0);
SetupTriangle(this.images.speed1.getWidth(), this.images.speed1.getHeight(), 0, 0);
SetupTriangle(this.images.speed2.getWidth(), this.images.speed2.getHeight(), 0, 0);
SetupTriangle(this.images.start.getWidth(), this.images.start.getHeight(), 0, 0);
SetupTriangle(this.images.life.getWidth(), this.images.life.getHeight(), 0, 0);
SetupTriangle(this.images.upgradeBar.getWidth(), this.images.upgradeBar.getHeight(), 0, 0);
SetupTriangle(this.images.bunny1.getWidth(), this.images.bunny1.getHeight(), 0, 0);
SetupTriangle(this.images.carrotTower.getWidth(), this.images.carrotTower.getHeight(), 0, 0);
SetupTriangle(this.images.mineThrower.getWidth(), this.images.mineThrower.getHeight(), 0, 0);
SetupTriangle(this.images.bunnyKing1.getWidth(), this.images.bunnyKing1.getHeight(), 0, 0);
this.sprites.get(0).translate(this.ssx * this.images.ground_1.getWidth() / 2, this.ssy * this.images.ground_1.getHeight() / 2);
this.sprites.get(1).translate(this.ssx * (this.images.bar1.getWidth() / 2) + this.ssx * 1084.0f, this.ssy * this.images.bar1.getHeight() / 2.0f);
this.sprites.get(2).translate(this.ssx * this.images.speed1.getWidth() / 2 + this.ssx * 20, this.mScreenHeight - (this.ssy * this.images.speed1.getHeight() / 2) - this.ssy * 5);
this.sprites.get(3).translate(this.ssx * this.images.speed2.getWidth() / 2 + this.ssx * 20, this.mScreenHeight - (this.ssy * this.images.speed2.getHeight() / 2) - this.ssy * 5);
this.sprites.get(4).translate(this.ssx * this.images.start.getWidth() / 2 + this.ssx * 120, this.mScreenHeight - (this.ssy * this.images.start.getHeight() / 2) - this.ssy * 5);
this.sprites.get(5).translate(this.ssx * this.images.life.getWidth() / 2 + this.ssx * 5, this.ssy * this.images.life.getHeight() / 2 + this.ssy * (20));
this.sprites.get(6).translate(this.ssx * this.images.upgradeBar.getWidth() / 2, this.ssy * this.images.upgradeBar.getHeight() / 2);
this.sprites.get(7).translate(this.ssx * (this.images.bunny1.getWidth()) + this.ssx * (1280 - 143 - (this.images.bunny1.getWidth() / 2)), this.mScreenHeight - (this.ssy * this.images.bunny1.getHeight() / 2) - (this.ssy * (235 + (this.images.bunny1.getHeight() / 2))));
this.sprites.get(8).translate(this.ssx * (this.images.carrotTower.getWidth()) + this.ssx * (1280 - 53 - (this.images.carrotTower.getWidth() / 2)), this.mScreenHeight - (this.ssy * this.images.carrotTower.getHeight() / 2) - (this.ssy * (235 + (this.images.carrotTower.getHeight() / 2))));
this.sprites.get(9).translate(this.ssx * (this.images.mineThrower.getWidth()) + this.ssx * (1280 - 143 - (this.images.mineThrower.getWidth() / 2)), this.mScreenHeight - (this.ssy * this.images.mineThrower.getHeight() / 2) - (this.ssy * (325 + (this.images.mineThrower.getHeight() / 2))));
this.sprites.get(10).translate(this.ssx * (this.images.bunnyKing1.getWidth()) + this.ssx * (1280 - 53 - (this.images.bunnyKing1.getWidth() / 2)), this.mScreenHeight - (this.ssy * this.images.bunnyKing1.getHeight() / 2) - (this.ssy * (325 + (this.images.bunnyKing1.getHeight() / 2))));
}
@Override
public void onSurfaceCreated (GL10 gl, EGLConfig config) {
// Setup our scaling system
SetupScaling();
// Set the clear color to black
GLES20.glClearColor(0.0f, 0.0f, 0.0f, 1);
// Blending
GLES20.glEnable(GLES20.GL_BLEND);
// How should opengl blend it
GLES20.glBlendFunc(GLES20.GL_ONE, GLES20.GL_ONE_MINUS_SRC_ALPHA);
// Create the shaders, solid color
int vertexShader = riGraphicTools.loadShader(GLES20.GL_VERTEX_SHADER, riGraphicTools.vs_SolidColor);
int fragmentShader = riGraphicTools.loadShader(GLES20.GL_FRAGMENT_SHADER, riGraphicTools.fs_SolidColor);
riGraphicTools.sp_SolidColor = GLES20.glCreateProgram(); // create empty
// OpenGL ES
// Program
GLES20.glAttachShader(riGraphicTools.sp_SolidColor, vertexShader); // add
// the
// vertex
// shader
// to
// program
GLES20.glAttachShader(riGraphicTools.sp_SolidColor, fragmentShader); // add
// the
// fragment
// shader
// to
// program
GLES20.glLinkProgram(riGraphicTools.sp_SolidColor); // creates OpenGL ES
// program
// executables
// Create the shaders, images
vertexShader = riGraphicTools.loadShader(GLES20.GL_VERTEX_SHADER, riGraphicTools.vs_Image);
fragmentShader = riGraphicTools.loadShader(GLES20.GL_FRAGMENT_SHADER, riGraphicTools.fs_Image);
riGraphicTools.sp_Image = GLES20.glCreateProgram(); // create empty
// OpenGL ES Program
GLES20.glAttachShader(riGraphicTools.sp_Image, vertexShader); // add the
// vertex
// shader
// to
// program
GLES20.glAttachShader(riGraphicTools.sp_Image, fragmentShader); // add
// the
// fragment
// shader
// to
// program
GLES20.glLinkProgram(riGraphicTools.sp_Image); // creates OpenGL ES
// program executables
// Set our shader programm
GLES20.glUseProgram(riGraphicTools.sp_Image);
// Creating a Images Object
this.images = new Images(this.mainActivity.getResources());
// Loading the Bitmaps
this.images.load();
Timer t = new Timer();
t.schedule(this.update = new Update(this.mainActivity, this, this.images), 16);
// Generate Textures, if more needed, alter these numbers.
this.texturenames = new int[24];
GLES20.glGenTextures(24, this.texturenames, 0);
SetupImageStatics();
}
private void SetupImageStatics () {
SetupImage(this.images.ground_1, 1);
SetupImage(this.images.bar1, 2);
SetupImage(this.images.speed1, 3);
SetupImage(this.images.speed2, 4);
SetupImage(this.images.start, 5);
SetupImage(this.images.life, 6);
SetupImage(this.images.upgradeBar, 7);
SetupImage(this.images.bunny1, 8);
SetupImage(this.images.carrotTower, 9);
SetupImage(this.images.mineThrower, 10);
SetupImage(this.images.bunnyKing1, 11);
}
public void SetupScaling () {
// The screen resolutions
this.swp = (this.mContext.getResources().getDisplayMetrics().widthPixels);
this.shp = (this.mContext.getResources().getDisplayMetrics().heightPixels);
// Orientation is assumed portrait
this.ssx = this.swp / 1280.0f;
this.ssy = this.shp / 720.0f;
// Get our uniform scaler
if (this.ssx > this.ssy) this.ssu = this.ssy;
else this.ssu = this.ssx;
}
public void processTouchEvent (MotionEvent me) {
switch (me.getAction()) {
case MotionEvent.ACTION_DOWN:
this.update.x = (int) me.getX();
this.update.y = (int) me.getY();
this.update.getItemOrUpgrade(this.update.x, this.update.y);
this.update.fastForward(this.update.x, this.update.y);
this.update.start(this.update.x, this.update.y);
this.update.nextUpgrade(this.update.x, this.update.y);
break;
case MotionEvent.ACTION_MOVE:
if (this.update.tower != 0) {
this.update.x = (int) me.getX();
this.update.y = (int) me.getY();
this.update.pathPlace(this.update.x, this.update.y);
}
break;
case MotionEvent.ACTION_UP:
this.update.x = (int) me.getX();
this.update.y = (int) me.getY();
this.update.placeOrReleaseItem = true;
break;
}
}
public void UpdateSprite (int location) {
// Get new transformed vertices
vertices = this.sprites.get(location).getTransformedVertices();
// The vertex buffer.
ByteBuffer bb = ByteBuffer.allocateDirect(vertices.length * 4);
bb.order(ByteOrder.nativeOrder());
this.vertexBuffer = bb.asIntBuffer();
this.vertexBuffer.put(vertices);
this.vertexBuffer.position(0);
}
public void SetupImage (Bitmap bmp, int index) {
// Create our UV coordinates.
uvs = new int[] { 0, 0, 0, 1, 1, 1, 1, 0 };
// The texture buffer
ByteBuffer bb = ByteBuffer.allocateDirect(uvs.length * 4);
bb.order(ByteOrder.nativeOrder());
this.uvBuffer = bb.asIntBuffer();
this.uvBuffer.put(uvs);
this.uvBuffer.position(0);
// // Retrieve our image from resources.
// int id =
// mContext.getResources().getIdentifier("drawable/ic_launcher", null,
// mContext.getPackageName());
//
// // Temporary create a bitmap
// Bitmap bmp = BitmapFactory.decodeResource(mContext.getResources(),
// id);
// Bind texture to texturename
GLES20.glActiveTexture(GLES20.GL_TEXTURE0 + index);
GLES20.glBindTexture(GLES20.GL_TEXTURE_2D, this.texturenames[index]);
// Set filtering
GLES20.glTexParameteri(GLES20.GL_TEXTURE_2D, GLES20.GL_TEXTURE_MIN_FILTER, GLES20.GL_LINEAR);
GLES20.glTexParameteri(GLES20.GL_TEXTURE_2D, GLES20.GL_TEXTURE_MAG_FILTER, GLES20.GL_LINEAR);
// Load the bitmap into the bound texture.
GLUtils.texImage2D(GLES20.GL_TEXTURE_2D, 0, bmp, 0);
// // We are done using the bitmap so we should recycle it.
// bmp.recycle();
}
public void SetupTriangle (float width, float height, float x, float y) {
// Get information of sprite.
this.sprites.add(new Sprite(width, height, x, y));
vertices = this.sprites.get(this.sprites.size() - 1).getTransformedVertices();
// The order of vertexrendering for a quad
indices = new short[] { 0, 1, 2, 0, 2, 3 };
// The vertex buffer.
ByteBuffer bb = ByteBuffer.allocateDirect(vertices.length * 4);
bb.order(ByteOrder.nativeOrder());
this.vertexBuffer = bb.asIntBuffer();
this.vertexBuffer.put(vertices);
this.vertexBuffer.position(0);
// initialize byte buffer for the draw list
ByteBuffer dlb = ByteBuffer.allocateDirect(indices.length * 2);
dlb.order(ByteOrder.nativeOrder());
this.drawListBuffer = dlb.asShortBuffer();
this.drawListBuffer.put(indices);
this.drawListBuffer.position(0);
}
class Sprite {
float angle;
float scale;
RectF base;
Point translation;
public Sprite (float width, float height, float x, float y) {
// Initialise our intital size around the 0,0 point
this.base = new RectF(-(width / 2f) * GLRenderer.this.ssu, (height / 2f) * GLRenderer.this.ssu, (width / 2f) * GLRenderer.this.ssu, -(height / 2f) * GLRenderer.this.ssu);
// Initial translation
this.translation = new Point(Math.round(x * GLRenderer.this.ssu), Math.round(y * GLRenderer.this.ssu));
// We start with our inital size
this.scale = 1f;
// We start in our inital angle
this.angle = 0.0f;
}
public void translate (float deltax, float deltay) {
// Update our location.
this.translation.x += Math.round(deltax);
this.translation.y += Math.round(deltay);
}
public void scale (float deltas) {
this.scale += deltas;
}
public void rotate (float deltaa) {
this.angle += deltaa;
}
public int[] getTransformedVertices () {
// Start with scaling
int x1 = Math.round(this.base.left * this.scale);
int x2 = Math.round(this.base.right * this.scale);
int y1 = Math.round(this.base.bottom * this.scale);
int y2 = Math.round(this.base.top * this.scale);
// We now detach from our Rect because when rotating,
// we need the seperate points, so we do so in opengl order
Point one = new Point(x1, y2);
Point two = new Point(x1, y1);
Point three = new Point(x2, y1);
Point four = new Point(x2, y2);
// We create the sin and cos function once,
// so we do not have calculate them each time.
float s = (float) Math.sin(this.angle);
float c = (float) Math.cos(this.angle);
// Then we rotate each point
one.x = Math.round(x1 * c - y2 * s);
one.y = Math.round(x1 * s + y2 * c);
two.x = Math.round(x1 * c - y1 * s);
two.y = Math.round(x1 * s + y1 * c);
three.x = Math.round(x2 * c - y1 * s);
three.y = Math.round(x2 * s + y1 * c);
four.x = Math.round(x2 * c - y2 * s);
four.y = Math.round(x2 * s + y2 * c);
// Finally we translate the sprite to its correct position.
one.x += this.translation.x;
one.y += this.translation.y;
two.x += this.translation.x;
two.y += this.translation.y;
three.x += this.translation.x;
three.y += this.translation.y;
four.x += this.translation.x;
four.y += this.translation.y;
// We now return our float array of vertices.
return new int[] { Math.round(one.x), Math.round(one.y), 0, Math.round(two.x), Math.round(two.y), 0, Math.round(three.x), Math.round(three.y), 0, Math.round(four.x), Math.round(four.y), 0, };
}
}
public class Update extends TimerTask {
Bitmap ball;
int x, y;
int mapStage = StaticVariables.getMap();
int towerCost = 200;
boolean start = false;
int x2 = 0;
int y2 = 0;
public int points = 50000;
public boolean stageClear = false;
boolean everythingSpawned = false;
public int life = 200;
private int space = 40;
public boolean stageLose = false;
public boolean upgrade = false;
List<Opponent> opponents = new ArrayList<Opponent>();
List<Tower> towers = new ArrayList<Tower>();
List<Bullet> bullets = new ArrayList<Bullet>();
List<SuperExplosion> explosions = new ArrayList<SuperExplosion>();
List<Path> paths = new ArrayList<Path>();
List<int[]> stages = new ArrayList<int[]>();
private List<Integer> minesPassive = new ArrayList<Integer>();
private List<Integer> removeBulletsIndex = new ArrayList<Integer>();
List<Integer> removeMinesPassive = new ArrayList<Integer>();
public int time = 16;
public int speed = 1;
public int stageLevel = 1;
public boolean placePossible = true;
private int timeTimes = 0;
private int bubble = 0;
public boolean wait = false;
public int mapLength;
boolean change = false, change1 = false, change2 = false, change3 = false;
double maxX, maxY, minX, minY, abstandX2, abstandX, abstandY2, abstandY, shortestSpacing, shortest, angleMaxX, angleMaxY, angleMinX, angleMinY, angleAbstandX, angleAbstandY;
int shortestIndex, index, spawnCounter = 0;
private MediaPlayer bubblePopSound;
private int tower = 0;
int nextImage = 0;
private boolean normalSpeed = true;
float invisability = 1;
private int upgradeBarDiff = 0;
private boolean hideUpgradeBar = false;
public int iceBallRotation;
private int explosionTime;
private List<MinePlace> minesPlaced = new ArrayList<MinePlace>();
private int gameLocation = 0;
Localizer localizer;
int testCounter;
boolean load = true;
private boolean placeOrReleaseItem = false;
double viewWidth, viewHeight;
MergeSort mergeSort = new MergeSort();
GLRenderer glRenderer2;
public List<Integer> getMinesPassive () {
return this.minesPassive;
}
public void setMinesPassive (int index2, int minesPassive) {
this.minesPassive.set(index2, minesPassive);
}
public void addMinesPassive (int minesPassive) {
this.minesPassive.add(minesPassive);
}
public void addMinesPassive (int i, Integer minesPassive) {
this.minesPassive.add(i, minesPassive);
}
}
我希望你知道一种提高绘图速度的方法。 提前谢谢!
答案 0 :(得分:0)
在您的案例中,如何提高性能有点难。从我的角度来看,代码中的噪音太大了。但一般来说,有一些关于如何在渲染过程中提高性能的基本技巧: - 避免不必要的OpenGl状态机更改 - 避免不必要的OpenGl状态查询(例如GLES20.glGetAttribLocation()) - 在渲染过程中避免内存分配 - 使用最简单的着色器 - 使用纹理图集以避免必要的纹理绑定 - 尽可能使用VBO
有关主题的更多信息,请尝试阅读https://www.opengl.org/wiki/Performance。或者看一下这个话题https://www.youtube.com/watch?v=YLVbLVtjDDw。
您也可以考虑使用libGDX http://libgdx.badlogicgames.com/,它将为您提供有效的绘图精灵。