RenderBuckets: unify baseBuckets and textureBuckets

... finally
This commit is contained in:
Hannes Janetzek 2014-09-04 23:54:30 +02:00
parent f6d85ce8bd
commit 3f8b028d60
11 changed files with 131 additions and 184 deletions

View File

@ -80,7 +80,7 @@ public class LineTest extends GdxMap {
} }
buckets.clear(); buckets.clear();
buckets.setBaseBuckets(ll); buckets.set(ll);
g.clear(); g.clear();
for (int i = 0; i < 60; i++) { for (int i = 0; i < 60; i++) {
g.startLine(); g.startLine();

View File

@ -221,7 +221,7 @@ public class PathLayer extends Layer {
mMapPosition.copy(t.pos); mMapPosition.copy(t.pos);
// compile new layers // compile new layers
buckets.setBaseBuckets(t.bucket.getBaseBuckets()); buckets.set(t.bucket.get());
compile(); compile();
} }
} }
@ -294,7 +294,7 @@ public class PathLayer extends Layer {
} }
if (size == 0) { if (size == 0) {
if (task.bucket.getBaseBuckets() != null) { if (task.bucket.get() != null) {
task.bucket.clear(); task.bucket.clear();
mMap.render(); mMap.render();
} }

View File

@ -86,7 +86,7 @@ public class MarkerRenderer extends BucketRenderer {
long flip = (long) (Tile.SIZE * v.pos.scale) >> 1; long flip = (long) (Tile.SIZE * v.pos.scale) >> 1;
if (mItems == null) { if (mItems == null) {
if (buckets.getTextureBuckets() != null) { if (buckets.get() != null) {
buckets.clear(); buckets.clear();
compile(); compile();
} }
@ -162,7 +162,7 @@ public class MarkerRenderer extends BucketRenderer {
mSymbolLayer.pushSymbol(s); mSymbolLayer.pushSymbol(s);
} }
buckets.setTextureBuckets(mSymbolLayer); buckets.set(mSymbolLayer);
buckets.prepare(); buckets.prepare();
compile(); compile();

View File

@ -178,50 +178,40 @@ public class VectorTileRenderer extends TileRenderer {
PolygonBucket.Renderer.clip(mClipMVP, mClipMode); PolygonBucket.Renderer.clip(mClipMVP, mClipMode);
RenderBucket b = buckets.getBaseBuckets();
boolean first = true; boolean first = true;
while (b != null) {
if (b.type == POLYGON) { for (RenderBucket b = buckets.get(); b != null;) {
switch (b.type) {
case POLYGON:
b = PolygonBucket.Renderer.draw(b, v, div, first); b = PolygonBucket.Renderer.draw(b, v, div, first);
first = false; first = false;
/* set test for clip to tile region */ /* set test for clip to tile region */
GL.glStencilFunc(GL_EQUAL, 0x80, 0x80); GL.glStencilFunc(GL_EQUAL, 0x80, 0x80);
continue; break;
} case LINE:
if (b.type == LINE) {
b = LineBucket.Renderer.draw(b, v, scale, buckets); b = LineBucket.Renderer.draw(b, v, scale, buckets);
continue; break;
} case TEXLINE:
if (b.type == TEXLINE) {
b = LineTexBucket.Renderer.draw(b, v, div, buckets); b = LineTexBucket.Renderer.draw(b, v, div, buckets);
if (buckets.ibo != null) if (buckets.ibo != null)
buckets.ibo.bind(); buckets.ibo.bind();
continue; break;
} case MESH:
if (b.type == MESH) {
b = MeshBucket.Renderer.draw(b, v); b = MeshBucket.Renderer.draw(b, v);
continue; break;
} case HAIRLINE:
if (b.type == HAIRLINE) {
b = HairLineBucket.Renderer.draw(b, v); b = HairLineBucket.Renderer.draw(b, v);
continue; break;
} case BITMAP:
b = BitmapBucket.Renderer.draw(b, v, 1, mLayerAlpha);
break;
default:
/* just in case */ /* just in case */
log.error("unknown layer {}", b.type); log.error("unknown layer {}", b.type);
b = b.next; b = b.next;
break;
} }
buckets.bind();
b = buckets.getTextureBuckets();
while (b != null) {
if (b.type == BITMAP) {
b = BitmapBucket.Renderer.draw(b, v, 1, mLayerAlpha);
continue;
}
log.error("unknown layer {}", b.type);
b = b.next;
} }
if (debugOverdraw) { if (debugOverdraw) {

View File

@ -61,9 +61,9 @@ public class BitmapTileLoader extends TileLoader {
BitmapBucket l = new BitmapBucket(false); BitmapBucket l = new BitmapBucket(false);
l.setBitmap(bitmap, Tile.SIZE, Tile.SIZE, mLayer.pool); l.setBitmap(bitmap, Tile.SIZE, Tile.SIZE, mLayer.pool);
RenderBuckets layers = new RenderBuckets(); RenderBuckets b = new RenderBuckets();
layers.setTextureBuckets(l); b.set(l);
mTile.data = layers; mTile.data = b;
} }
@Override @Override

View File

@ -67,7 +67,7 @@ class TextRenderer extends BucketRenderer {
} }
// set new TextLayer to be uploaded and rendered // set new TextLayer to be uploaded and rendered
buckets.setTextureBuckets(t.layers); buckets.set(t.layers);
mMapPosition = t.pos; mMapPosition = t.pos;
compile(); compile();
} }
@ -83,7 +83,7 @@ class TextRenderer extends BucketRenderer {
setMatrix(v, false); setMatrix(v, false);
for (RenderBucket l = buckets.getTextureBuckets(); l != null;) for (RenderBucket l = buckets.get(); l != null;)
l = TextureBucket.Renderer.draw(buckets, l, v, scale); l = TextureBucket.Renderer.draw(buckets, l, v, scale);
} }

View File

@ -60,7 +60,7 @@ public class BitmapRenderer extends BucketRenderer {
BitmapBucket l = new BitmapBucket(true); BitmapBucket l = new BitmapBucket(true);
l.setBitmap(mBitmap, mWidth, mHeight); l.setBitmap(mBitmap, mWidth, mHeight);
buckets.setTextureBuckets(l); buckets.set(l);
mUpdateBitmap = true; mUpdateBitmap = true;
} }
@ -84,6 +84,6 @@ public class BitmapRenderer extends BucketRenderer {
@Override @Override
protected synchronized void render(GLViewport v) { protected synchronized void render(GLViewport v) {
v.useScreenCoordinates(false, 8); v.useScreenCoordinates(false, 8);
BitmapBucket.Renderer.draw(buckets.getTextureBuckets(), v, 1, 1); BitmapBucket.Renderer.draw(buckets.get(), v, 1, 1);
} }
} }

View File

@ -17,6 +17,7 @@
package org.oscim.renderer; package org.oscim.renderer;
import static org.oscim.renderer.bucket.RenderBucket.BITMAP; import static org.oscim.renderer.bucket.RenderBucket.BITMAP;
import static org.oscim.renderer.bucket.RenderBucket.HAIRLINE;
import static org.oscim.renderer.bucket.RenderBucket.LINE; import static org.oscim.renderer.bucket.RenderBucket.LINE;
import static org.oscim.renderer.bucket.RenderBucket.MESH; import static org.oscim.renderer.bucket.RenderBucket.MESH;
import static org.oscim.renderer.bucket.RenderBucket.POLYGON; import static org.oscim.renderer.bucket.RenderBucket.POLYGON;
@ -78,53 +79,42 @@ public abstract class BucketRenderer extends LayerRenderer {
float div = (float) (v.pos.scale / layerPos.scale); float div = (float) (v.pos.scale / layerPos.scale);
RenderBucket b = buckets.getBaseBuckets();
if (b != null)
setMatrix(v, true); setMatrix(v, true);
while (b != null) { for (RenderBucket b = buckets.get(); b != null;) {
if (b.type == POLYGON) { switch (b.type) {
case POLYGON:
b = PolygonBucket.Renderer.draw(b, v, 1, true); b = PolygonBucket.Renderer.draw(b, v, 1, true);
continue; break;
} case LINE:
if (b.type == LINE) {
b = LineBucket.Renderer.draw(b, v, div, buckets); b = LineBucket.Renderer.draw(b, v, div, buckets);
continue; break;
} case TEXLINE:
if (b.type == TEXLINE) {
b = LineTexBucket.Renderer.draw(b, v, div, buckets); b = LineTexBucket.Renderer.draw(b, v, div, buckets);
// rebind // rebind
buckets.ibo.bind(); buckets.ibo.bind();
continue; break;
} case MESH:
if (b.type == MESH) {
b = MeshBucket.Renderer.draw(b, v); b = MeshBucket.Renderer.draw(b, v);
continue; break;
} case HAIRLINE:
if (b.type == RenderBucket.HAIRLINE) {
b = HairLineBucket.Renderer.draw(b, v); b = HairLineBucket.Renderer.draw(b, v);
continue;
}
log.error("invalid bucket {}", b.type);
break; break;
} case BITMAP:
b = buckets.getTextureBuckets();
if (b != null)
setMatrix(v, false);
while (b != null) {
if (b.type == BITMAP) {
b = BitmapBucket.Renderer.draw(b, v, 1, 1); b = BitmapBucket.Renderer.draw(b, v, 1, 1);
continue; // rebind
} buckets.ibo.bind();
if (b.type == SYMBOL) {
b = TextureBucket.Renderer.draw(buckets, b, v, div);
continue;
}
log.error("invalid bucket {}", b.type);
break; break;
case SYMBOL:
b = TextureBucket.Renderer.draw(buckets, b, v, div);
// rebind
buckets.ibo.bind();
break;
default:
log.error("invalid bucket {}", b.type);
b = b.next;
break;
}
} }
} }

View File

@ -28,6 +28,7 @@ import org.oscim.theme.styles.TextStyle;
import org.oscim.theme.styles.TextStyle.TextBuilder; import org.oscim.theme.styles.TextStyle.TextBuilder;
public class GridRenderer extends BucketRenderer { public class GridRenderer extends BucketRenderer {
private final TextBucket mTextBucket; private final TextBucket mTextBucket;
private final TextStyle mText; private final TextStyle mText;
private final LineBucket mLineBucket; private final LineBucket mLineBucket;
@ -67,13 +68,18 @@ public class GridRenderer extends BucketRenderer {
mText = textStyle; mText = textStyle;
if (mText != null) mLineBucket = new LineBucket(0);
mTextBucket = buckets.addTextBucket(new TextBucket()); mLineBucket.line = lineStyle;
else
mTextBucket = null;
mLineBucket = buckets.addLineBucket(0, lineStyle); if (mText != null) {
mLineBucket.addLine(mLines); mTextBucket = new TextBucket();
buckets.set(mTextBucket);
mTextBucket.next = mLineBucket;
buckets.set(mTextBucket);
} else {
mTextBucket = null;
buckets.set(mLineBucket);
}
mStringBuffer = new StringBuilder(32); mStringBuffer = new StringBuilder(32);
} }
@ -101,12 +107,6 @@ public class GridRenderer extends BucketRenderer {
tl.addText(ti); tl.addText(ti);
} }
} }
/* render TextItems to a bitmap and prepare vertex buffer data. */
tl.prepare();
/* release TextItems */
tl.clearLabels();
} }
@Override @Override
@ -131,13 +131,14 @@ public class GridRenderer extends BucketRenderer {
mMapPosition.scale = z; mMapPosition.scale = z;
if (mText != null) { if (mText != null) {
buckets.set(mTextBucket);
addLabels(x, y, v.pos.zoomLevel); addLabels(x, y, v.pos.zoomLevel);
buckets.setBaseBuckets(mLineBucket);
mLineBucket.addLine(mLines); mLineBucket.addLine(mLines);
compile(); buckets.prepare();
setReady(false);
}
} else if (buckets.vbo == null) { if (!isReady())
compile(); compile();
} }
} }
}

View File

@ -53,6 +53,7 @@ public abstract class RenderBucket extends Inlist<RenderBucket> {
/** Clear all resources. */ /** Clear all resources. */
protected void clear() { protected void clear() {
vertexItems.dispose(); vertexItems.dispose();
indiceItems.dispose();
numVertices = 0; numVertices = 0;
numIndices = 0; numIndices = 0;
} }
@ -80,6 +81,13 @@ public abstract class RenderBucket extends Inlist<RenderBucket> {
return vertexOffset; return vertexOffset;
} }
/**
* Start position in ibo for this bucket
*/
public int getIndiceOffset() {
return indiceOffset;
}
public void setVertexOffset(int offset) { public void setVertexOffset(int offset) {
this.vertexOffset = offset; this.vertexOffset = offset;
} }

View File

@ -50,16 +50,13 @@ public class RenderBuckets extends TileData {
2, // MESH_VERTEX 2, // MESH_VERTEX
4, // EXTRUSION_VERTEX 4, // EXTRUSION_VERTEX
2, // HAIRLINE_VERTEX 2, // HAIRLINE_VERTEX
6, // SYMBOL
6, // BITMAP
}; };
private final static int TEXTURE_VERTEX_SHORTS = 6;
private final static int SHORT_BYTES = 2; private final static int SHORT_BYTES = 2;
/** mixed Polygon- and LineBuckets */ private RenderBucket buckets;
private RenderBucket baseBuckets;
/** Text- and SymbolBuckets */
private RenderBucket textureBuckets;
/** /**
* VBO holds all vertex data to draw lines and polygons after compilation. * VBO holds all vertex data to draw lines and polygons after compilation.
@ -161,38 +158,21 @@ public class RenderBuckets extends TileData {
return (HairLineBucket) getBucket(level, HAIRLINE); return (HairLineBucket) getBucket(level, HAIRLINE);
} }
public TextBucket addTextBucket(TextBucket textBucket) { /**
textBucket.next = textureBuckets; * Set new bucket items and clear previous.
textureBuckets = textBucket; */
return textBucket; public void set(RenderBucket buckets) {
for (RenderBucket l = this.buckets; l != null; l = l.next)
l.clear();
this.buckets = buckets;
} }
/** /**
* Set new Base-Buckets and clear previous. * @return internal linked list of RenderBucket items
*/ */
public void setBaseBuckets(RenderBucket buckets) { public RenderBucket get() {
for (RenderBucket l = baseBuckets; l != null; l = l.next) return buckets;
l.clear();
baseBuckets = buckets;
}
public RenderBucket getBaseBuckets() {
return baseBuckets;
}
/**
* Set new TextureBuckets and clear previous.
*/
public void setTextureBuckets(TextureBucket tl) {
for (RenderBucket l = textureBuckets; l != null; l = l.next)
l.clear();
textureBuckets = tl;
}
public RenderBucket getTextureBuckets() {
return textureBuckets;
} }
private RenderBucket getBucket(int level, int type) { private RenderBucket getBucket(int level, int type) {
@ -211,7 +191,7 @@ public class RenderBuckets extends TileData {
return bucket; return bucket;
} }
RenderBucket b = baseBuckets; RenderBucket b = buckets;
if (b == null || b.level > level) { if (b == null || b.level > level) {
/* insert new bucket at start */ /* insert new bucket at start */
b = null; b = null;
@ -248,8 +228,8 @@ public class RenderBuckets extends TileData {
if (b == null) { if (b == null) {
/** insert at start */ /** insert at start */
bucket.next = baseBuckets; bucket.next = buckets;
baseBuckets = bucket; buckets = bucket;
} else { } else {
bucket.next = b.next; bucket.next = b.next;
b.next = bucket; b.next = bucket;
@ -274,42 +254,33 @@ public class RenderBuckets extends TileData {
private int countVboSize() { private int countVboSize() {
int vboShorts = 0; int vboShorts = 0;
for (RenderBucket l = baseBuckets; l != null; l = l.next) for (RenderBucket l = buckets; l != null; l = l.next)
vboShorts += l.numVertices * VERTEX_SHORT_CNT[l.type]; vboShorts += l.numVertices * VERTEX_SHORT_CNT[l.type];
for (RenderBucket l = textureBuckets; l != null; l = l.next)
vboShorts += l.numVertices * TEXTURE_VERTEX_SHORTS;
return vboShorts; return vboShorts;
} }
private int countIboSize() { private int countIboSize() {
int numIndices = 0; int numIndices = 0;
for (RenderBucket l = baseBuckets; l != null; l = l.next) for (RenderBucket l = buckets; l != null; l = l.next)
numIndices += l.numIndices;
for (RenderBucket l = textureBuckets; l != null; l = l.next)
numIndices += l.numIndices; numIndices += l.numIndices;
return numIndices; return numIndices;
} }
public void setFrom(RenderBuckets buckets) { public void setFrom(RenderBuckets buckets) {
setBaseBuckets(buckets.baseBuckets); set(buckets.buckets);
setTextureBuckets((TextureBucket) buckets.textureBuckets);
mCurBucket = null; mCurBucket = null;
buckets.baseBuckets = null; buckets.buckets = null;
buckets.textureBuckets = null;
buckets.mCurBucket = null; buckets.mCurBucket = null;
} }
/** cleanup only when buckets are not used by tile or bucket anymore! */ /** cleanup only when buckets are not used by tile or bucket anymore! */
public void clear() { public void clear() {
/* NB: set null calls clear() on each bucket! */ /* NB: set null calls clear() on each bucket! */
setBaseBuckets(null); set(null);
setTextureBuckets(null);
mCurBucket = null; mCurBucket = null;
vbo = BufferObject.release(vbo); vbo = BufferObject.release(vbo);
@ -322,10 +293,7 @@ public class RenderBuckets extends TileData {
} }
public void prepare() { public void prepare() {
for (RenderBucket l = baseBuckets; l != null; l = l.next) for (RenderBucket l = buckets; l != null; l = l.next)
l.prepare();
for (RenderBucket l = textureBuckets; l != null; l = l.next)
l.prepare(); l.prepare();
} }
@ -343,7 +311,6 @@ public class RenderBuckets extends TileData {
int vboSize = countVboSize(); int vboSize = countVboSize();
if (vboSize <= 0) { if (vboSize <= 0) {
// FIXME just clear?
vbo = BufferObject.release(vbo); vbo = BufferObject.release(vbo);
ibo = BufferObject.release(ibo); ibo = BufferObject.release(ibo);
return false; return false;
@ -364,14 +331,11 @@ public class RenderBuckets extends TileData {
iboData = MapRenderer.getShortBuffer(iboSize); iboData = MapRenderer.getShortBuffer(iboSize);
} }
//>>compile(vboData, iboData, addFill);
int pos = addFill ? 4 : 0; int pos = addFill ? 4 : 0;
for (RenderBucket l = baseBuckets; l != null; l = l.next) { for (RenderBucket l = buckets; l != null; l = l.next) {
if (l.type == POLYGON) { if (l.type == POLYGON) {
l.compile(vboData, iboData); l.compile(vboData, iboData);
//log.debug("offset {} {}", l.offset, pos);
l.vertexOffset = pos; l.vertexOffset = pos;
pos += l.numVertices; pos += l.numVertices;
} }
@ -379,7 +343,7 @@ public class RenderBuckets extends TileData {
offset[LINE] = vboData.position() * SHORT_BYTES; offset[LINE] = vboData.position() * SHORT_BYTES;
pos = 0; pos = 0;
for (RenderBucket l = baseBuckets; l != null; l = l.next) { for (RenderBucket l = buckets; l != null; l = l.next) {
if (l.type == LINE) { if (l.type == LINE) {
l.compile(vboData, iboData); l.compile(vboData, iboData);
@ -388,18 +352,12 @@ public class RenderBuckets extends TileData {
} }
} }
//offset[TEXLINE] = size * SHORT_BYTES; for (RenderBucket l = buckets; l != null; l = l.next) {
if (l.type != LINE && l.type != POLYGON) {
for (RenderBucket l = baseBuckets; l != null; l = l.next) {
if (l.type == TEXLINE || l.type == MESH || l.type == HAIRLINE) {
l.compile(vboData, iboData); l.compile(vboData, iboData);
} }
} }
for (RenderBucket l = textureBuckets; l != null; l = l.next) {
l.compile(vboData, iboData);
}
//<<
if (vboSize != vboData.position()) { if (vboSize != vboData.position()) {
log.debug("wrong vertex buffer size: " log.debug("wrong vertex buffer size: "
+ " new size: " + vboSize + " new size: " + vboSize