wip: use HairLine for PolygonLayer outlines
This commit is contained in:
parent
7bf2544a83
commit
e830252c85
@ -81,15 +81,7 @@ public class ThemeStylerActivity extends BaseMapActivity implements OnSeekBarCha
|
|||||||
s.set(areaBuilder.set(s)
|
s.set(areaBuilder.set(s)
|
||||||
.color(modColor(s.color, areaColor))
|
.color(modColor(s.color, areaColor))
|
||||||
.blendColor(modColor(s.blendColor, areaColor))
|
.blendColor(modColor(s.blendColor, areaColor))
|
||||||
.build());
|
.strokeColor(modColor(s.strokeColor, areaColor))
|
||||||
|
|
||||||
if (s.outline == null)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
s.outline.set(lineBuilder.set(s.outline)
|
|
||||||
.color(modColor(s.outline.color, areaColor))
|
|
||||||
.stippleColor(modColor(s.outline.stippleColor,
|
|
||||||
areaColor))
|
|
||||||
.build());
|
.build());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -17,16 +17,21 @@
|
|||||||
package org.oscim.renderer.elements;
|
package org.oscim.renderer.elements;
|
||||||
|
|
||||||
import static org.oscim.backend.GL20.GL_ALWAYS;
|
import static org.oscim.backend.GL20.GL_ALWAYS;
|
||||||
|
import static org.oscim.backend.GL20.GL_ELEMENT_ARRAY_BUFFER;
|
||||||
import static org.oscim.backend.GL20.GL_EQUAL;
|
import static org.oscim.backend.GL20.GL_EQUAL;
|
||||||
import static org.oscim.backend.GL20.GL_INVERT;
|
import static org.oscim.backend.GL20.GL_INVERT;
|
||||||
import static org.oscim.backend.GL20.GL_KEEP;
|
import static org.oscim.backend.GL20.GL_KEEP;
|
||||||
|
import static org.oscim.backend.GL20.GL_LINES;
|
||||||
import static org.oscim.backend.GL20.GL_REPLACE;
|
import static org.oscim.backend.GL20.GL_REPLACE;
|
||||||
import static org.oscim.backend.GL20.GL_SHORT;
|
import static org.oscim.backend.GL20.GL_SHORT;
|
||||||
import static org.oscim.backend.GL20.GL_TRIANGLE_FAN;
|
import static org.oscim.backend.GL20.GL_TRIANGLE_FAN;
|
||||||
import static org.oscim.backend.GL20.GL_TRIANGLE_STRIP;
|
import static org.oscim.backend.GL20.GL_TRIANGLE_STRIP;
|
||||||
|
import static org.oscim.backend.GL20.GL_UNSIGNED_SHORT;
|
||||||
import static org.oscim.backend.GL20.GL_ZERO;
|
import static org.oscim.backend.GL20.GL_ZERO;
|
||||||
import static org.oscim.utils.FastMath.clamp;
|
import static org.oscim.utils.FastMath.clamp;
|
||||||
|
|
||||||
|
import java.nio.ShortBuffer;
|
||||||
|
|
||||||
import org.oscim.core.GeometryBuffer;
|
import org.oscim.core.GeometryBuffer;
|
||||||
import org.oscim.core.Tile;
|
import org.oscim.core.Tile;
|
||||||
import org.oscim.renderer.GLMatrix;
|
import org.oscim.renderer.GLMatrix;
|
||||||
@ -43,7 +48,8 @@ import org.slf4j.LoggerFactory;
|
|||||||
/**
|
/**
|
||||||
* Special Renderer for drawing tile polygons using the stencil buffer method
|
* Special Renderer for drawing tile polygons using the stencil buffer method
|
||||||
*/
|
*/
|
||||||
public final class PolygonLayer extends RenderElement {
|
public final class PolygonLayer extends IndexedRenderElement {
|
||||||
|
|
||||||
static final Logger log = LoggerFactory.getLogger(PolygonLayer.class);
|
static final Logger log = LoggerFactory.getLogger(PolygonLayer.class);
|
||||||
|
|
||||||
public final static int CLIP_STENCIL = 1;
|
public final static int CLIP_STENCIL = 1;
|
||||||
@ -68,6 +74,10 @@ public final class PolygonLayer extends RenderElement {
|
|||||||
public void addPolygon(float[] points, short[] index) {
|
public void addPolygon(float[] points, short[] index) {
|
||||||
short center = (short) ((Tile.SIZE >> 1) * S);
|
short center = (short) ((Tile.SIZE >> 1) * S);
|
||||||
|
|
||||||
|
short id = (short) numVertices;
|
||||||
|
|
||||||
|
boolean outline = area.strokeWidth > 0;
|
||||||
|
|
||||||
for (int i = 0, pos = 0, n = index.length; i < n; i++) {
|
for (int i = 0, pos = 0, n = index.length; i < n; i++) {
|
||||||
int length = index[i];
|
int length = index[i];
|
||||||
if (length < 0)
|
if (length < 0)
|
||||||
@ -79,21 +89,45 @@ public final class PolygonLayer extends RenderElement {
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
numVertices += length / 2 + 2;
|
//numVertices += length / 2 + 2;
|
||||||
vertexItems.add(center, center);
|
vertexItems.add(center, center);
|
||||||
|
id++;
|
||||||
|
|
||||||
int inPos = pos;
|
int inPos = pos;
|
||||||
|
|
||||||
for (int j = 0; j < length; j += 2) {
|
for (int j = 0; j < length; j += 2) {
|
||||||
vertexItems.add((short) (points[inPos++] * S),
|
vertexItems.add((short) (points[inPos++] * S),
|
||||||
(short) (points[inPos++] * S));
|
(short) (points[inPos++] * S));
|
||||||
|
|
||||||
|
if (outline) {
|
||||||
|
indiceItems.add(id++);
|
||||||
|
numIndices++;
|
||||||
|
|
||||||
|
indiceItems.add(id);
|
||||||
|
numIndices++;
|
||||||
|
} else {
|
||||||
|
id++;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
vertexItems.add((short) (points[pos + 0] * S),
|
vertexItems.add((short) (points[pos + 0] * S),
|
||||||
(short) (points[pos + 1] * S));
|
(short) (points[pos + 1] * S));
|
||||||
|
id++;
|
||||||
|
|
||||||
pos += length;
|
pos += length;
|
||||||
}
|
}
|
||||||
|
numVertices = id;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected void compile(ShortBuffer sbuf) {
|
||||||
|
if (area.strokeWidth == 0) {
|
||||||
|
/* add vertices to shared VBO */
|
||||||
|
compileVertexItems(sbuf);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
/* compile with indexed outline */
|
||||||
|
super.compile(sbuf);
|
||||||
}
|
}
|
||||||
|
|
||||||
static class Shader extends GLShader {
|
static class Shader extends GLShader {
|
||||||
@ -121,7 +155,7 @@ public final class PolygonLayer extends RenderElement {
|
|||||||
|
|
||||||
private static final float FADE_START = 1.3f;
|
private static final float FADE_START = 1.3f;
|
||||||
|
|
||||||
private static AreaStyle[] mAreaFills;
|
private static PolygonLayer[] mAreaFills;
|
||||||
|
|
||||||
private static Shader polyShader;
|
private static Shader polyShader;
|
||||||
private static Shader texShader;
|
private static Shader texShader;
|
||||||
@ -130,7 +164,7 @@ public final class PolygonLayer extends RenderElement {
|
|||||||
polyShader = new Shader("base_shader");
|
polyShader = new Shader("base_shader");
|
||||||
texShader = new Shader("polygon_layer_tex");
|
texShader = new Shader("polygon_layer_tex");
|
||||||
|
|
||||||
mAreaFills = new AreaStyle[STENCIL_BITS];
|
mAreaFills = new PolygonLayer[STENCIL_BITS];
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -143,15 +177,19 @@ public final class PolygonLayer extends RenderElement {
|
|||||||
|
|
||||||
/* do not modify stencil buffer */
|
/* do not modify stencil buffer */
|
||||||
GL.glStencilMask(0x00);
|
GL.glStencilMask(0x00);
|
||||||
//int shader = polyShader;
|
Shader s;
|
||||||
|
|
||||||
Shader s = setShader(polyShader, v.mvp, false);
|
for (int i = start; i < end; i++) {
|
||||||
|
PolygonLayer l = mAreaFills[i];
|
||||||
|
AreaStyle a = l.area.current();
|
||||||
|
|
||||||
for (int c = start; c < end; c++) {
|
boolean useTexture = enableTexture && a.texture != null;
|
||||||
AreaStyle a = mAreaFills[c].current();
|
if (useTexture)
|
||||||
|
|
||||||
if (enableTexture && a.texture != null) {
|
|
||||||
s = setShader(texShader, v.mvp, false);
|
s = setShader(texShader, v.mvp, false);
|
||||||
|
else
|
||||||
|
s = setShader(polyShader, v.mvp, false);
|
||||||
|
|
||||||
|
if (useTexture) {
|
||||||
float num = clamp((Tile.SIZE / a.texture.width) >> 1, 1, Tile.SIZE);
|
float num = clamp((Tile.SIZE / a.texture.width) >> 1, 1, Tile.SIZE);
|
||||||
float transition = Interpolation.exp5.apply(clamp(scale - 1, 0, 1));
|
float transition = Interpolation.exp5.apply(clamp(scale - 1, 0, 1));
|
||||||
GL.glUniform2f(s.uScale, transition, div / num);
|
GL.glUniform2f(s.uScale, transition, div / num);
|
||||||
@ -184,10 +222,8 @@ public final class PolygonLayer extends RenderElement {
|
|||||||
GLUtils.setColor(s.uColor, a.blendColor, 1);
|
GLUtils.setColor(s.uColor, a.blendColor, 1);
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
if (a.color < 0xff000000)
|
/* test if color contains alpha */
|
||||||
GLState.blend(true);
|
GLState.blend((a.color & OPAQUE) != OPAQUE);
|
||||||
else
|
|
||||||
GLState.blend(false);
|
|
||||||
|
|
||||||
GLUtils.setColor(s.uColor, a.color, 1);
|
GLUtils.setColor(s.uColor, a.color, 1);
|
||||||
}
|
}
|
||||||
@ -195,14 +231,37 @@ public final class PolygonLayer extends RenderElement {
|
|||||||
/* set stencil buffer mask used to draw this layer
|
/* set stencil buffer mask used to draw this layer
|
||||||
* also check that clip bit is set to avoid overdraw
|
* also check that clip bit is set to avoid overdraw
|
||||||
* of other tiles */
|
* of other tiles */
|
||||||
GL.glStencilFunc(GL_EQUAL, 0xff, CLIP_BIT | 1 << c);
|
GL.glStencilFunc(GL_EQUAL, 0xff, CLIP_BIT | 1 << i);
|
||||||
|
|
||||||
/* draw tile fill coordinates */
|
/* draw tile fill coordinates */
|
||||||
GL.glDrawArrays(GL_TRIANGLE_STRIP, 0, 4);
|
GL.glDrawArrays(GL_TRIANGLE_STRIP, 0, 4);
|
||||||
|
|
||||||
/* disable texture shader */
|
if (l.indicesVbo == null)
|
||||||
if (s != polyShader)
|
continue;
|
||||||
s = setShader(polyShader, v.mvp, false);
|
|
||||||
|
GL.glStencilFunc(GL_EQUAL, CLIP_BIT, CLIP_BIT);
|
||||||
|
|
||||||
|
GLState.blend(true);
|
||||||
|
//GLState.testDepth(false);
|
||||||
|
|
||||||
|
HairLineLayer.Renderer.shader.set(v);
|
||||||
|
|
||||||
|
l.indicesVbo.bind();
|
||||||
|
|
||||||
|
GLUtils.setColor(HairLineLayer.Renderer.shader.uColor, l.area.strokeColor, 1);
|
||||||
|
|
||||||
|
GL.glVertexAttribPointer(HairLineLayer.Renderer.shader.aPos, 2, GL_SHORT,
|
||||||
|
false, 0, l.offset << 2);
|
||||||
|
|
||||||
|
GL.glDrawElements(GL_LINES, l.numIndices,
|
||||||
|
GL_UNSIGNED_SHORT, 0);
|
||||||
|
GL.glLineWidth(1);
|
||||||
|
|
||||||
|
GL.glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, 0);
|
||||||
|
|
||||||
|
///* disable texture shader */
|
||||||
|
//if (s != polyShader)
|
||||||
|
//s = setShader(polyShader, v, false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -280,7 +339,7 @@ public final class PolygonLayer extends RenderElement {
|
|||||||
start = cur = 0;
|
start = cur = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
mAreaFills[cur] = pl.area.current();
|
mAreaFills[cur] = pl;
|
||||||
|
|
||||||
/* set stencil mask to draw to */
|
/* set stencil mask to draw to */
|
||||||
GL.glStencilMask(1 << cur++);
|
GL.glStencilMask(1 << cur++);
|
||||||
|
@ -472,8 +472,7 @@ public class XmlThemeBuilder extends DefaultHandler {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
AreaStyle area = createArea(style, localName, attributes, mLevels);
|
AreaStyle area = createArea(style, localName, attributes, mLevels++);
|
||||||
mLevels += 2;
|
|
||||||
|
|
||||||
if (isStyle) {
|
if (isStyle) {
|
||||||
mStyles.put(AREA_STYLE + area.style, area);
|
mStyles.put(AREA_STYLE + area.style, area);
|
||||||
@ -509,12 +508,12 @@ public class XmlThemeBuilder extends DefaultHandler {
|
|||||||
b.color(value);
|
b.color(value);
|
||||||
|
|
||||||
else if ("stroke".equals(name))
|
else if ("stroke".equals(name))
|
||||||
b.outlineColor(value);
|
b.strokeColor(value);
|
||||||
|
|
||||||
else if ("stroke-width".equals(name)) {
|
else if ("stroke-width".equals(name)) {
|
||||||
float strokeWidth = Float.parseFloat(value);
|
float strokeWidth = Float.parseFloat(value);
|
||||||
validateNonNegative("stroke-width", strokeWidth);
|
validateNonNegative("stroke-width", strokeWidth);
|
||||||
b.outlineWidth = strokeWidth;
|
b.strokeWidth = strokeWidth;
|
||||||
|
|
||||||
} else if ("fade".equals(name))
|
} else if ("fade".equals(name))
|
||||||
b.fadeScale = Integer.parseInt(value);
|
b.fadeScale = Integer.parseInt(value);
|
||||||
|
@ -46,7 +46,8 @@ public class AreaStyle extends RenderStyle {
|
|||||||
public final TextureItem texture;
|
public final TextureItem texture;
|
||||||
|
|
||||||
/** Outline */
|
/** Outline */
|
||||||
public final LineStyle outline;
|
public final int strokeColor;
|
||||||
|
public final float strokeWidth;
|
||||||
|
|
||||||
public AreaStyle(int color) {
|
public AreaStyle(int color) {
|
||||||
this(0, color);
|
this(0, color);
|
||||||
@ -60,7 +61,8 @@ public class AreaStyle extends RenderStyle {
|
|||||||
this.blendScale = -1;
|
this.blendScale = -1;
|
||||||
this.color = color;
|
this.color = color;
|
||||||
this.texture = null;
|
this.texture = null;
|
||||||
this.outline = null;
|
this.strokeColor = color;
|
||||||
|
this.strokeWidth = 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
public AreaStyle(AreaBuilder b) {
|
public AreaStyle(AreaBuilder b) {
|
||||||
@ -72,23 +74,8 @@ public class AreaStyle extends RenderStyle {
|
|||||||
this.color = b.color;
|
this.color = b.color;
|
||||||
this.texture = b.texture;
|
this.texture = b.texture;
|
||||||
|
|
||||||
if (b.outline != null &&
|
this.strokeColor = b.strokeColor;
|
||||||
b.outlineColor == b.outline.color &&
|
this.strokeWidth = b.strokeWidth;
|
||||||
b.outlineWidth == b.outline.width) {
|
|
||||||
this.outline = b.outline;
|
|
||||||
} else if (b.outlineColor != Color.TRANSPARENT) {
|
|
||||||
this.outline = new LineStyle(-1, b.outlineColor, b.outlineWidth);
|
|
||||||
} else {
|
|
||||||
this.outline = null;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void update() {
|
|
||||||
super.update();
|
|
||||||
|
|
||||||
if (outline != null)
|
|
||||||
outline.update();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@ -99,22 +86,18 @@ public class AreaStyle extends RenderStyle {
|
|||||||
@Override
|
@Override
|
||||||
public void renderWay(Callback renderCallback) {
|
public void renderWay(Callback renderCallback) {
|
||||||
renderCallback.renderArea(this, level);
|
renderCallback.renderArea(this, level);
|
||||||
|
|
||||||
if (outline != null)
|
|
||||||
renderCallback.renderWay(outline, level + 1);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class AreaBuilder implements StyleBuilder {
|
public static class AreaBuilder implements StyleBuilder {
|
||||||
public int level;
|
public int level;
|
||||||
public String style;
|
public String style;
|
||||||
public LineStyle outline;
|
|
||||||
public int color;
|
public int color;
|
||||||
public int fadeScale;
|
public int fadeScale;
|
||||||
public int blendColor;
|
public int blendColor;
|
||||||
public int blendScale;
|
public int blendScale;
|
||||||
|
|
||||||
public int outlineColor;
|
public int strokeColor;
|
||||||
public float outlineWidth;
|
public float strokeWidth;
|
||||||
|
|
||||||
public TextureItem texture;
|
public TextureItem texture;
|
||||||
|
|
||||||
@ -129,14 +112,8 @@ public class AreaStyle extends RenderStyle {
|
|||||||
this.blendScale = area.blendScale;
|
this.blendScale = area.blendScale;
|
||||||
this.color = area.color;
|
this.color = area.color;
|
||||||
this.texture = area.texture;
|
this.texture = area.texture;
|
||||||
this.outline = area.outline;
|
this.strokeColor = area.strokeColor;
|
||||||
if (area.outline != null) {
|
this.strokeWidth = area.strokeWidth;
|
||||||
this.outlineColor = outline.color;
|
|
||||||
this.outlineWidth = outline.width;
|
|
||||||
} else {
|
|
||||||
outlineColor = Color.TRANSPARENT;
|
|
||||||
outlineWidth = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
@ -152,23 +129,23 @@ public class AreaStyle extends RenderStyle {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public AreaBuilder outline(int color, float width) {
|
public AreaBuilder outline(int color, float width) {
|
||||||
this.outlineColor = color;
|
this.strokeColor = color;
|
||||||
this.outlineWidth = width;
|
this.strokeWidth = width;
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
public AreaBuilder outlineColor(int color) {
|
public AreaBuilder strokeColor(int color) {
|
||||||
this.outlineColor = color;
|
this.strokeColor = color;
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
public AreaBuilder outlineColor(String color) {
|
public AreaBuilder strokeColor(String color) {
|
||||||
this.outlineColor = parseColor(color);
|
this.strokeColor = parseColor(color);
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
public AreaBuilder outlineWidth(float width) {
|
public AreaBuilder strokeWidth(float width) {
|
||||||
this.outlineWidth = width;
|
this.strokeWidth = width;
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -209,10 +186,8 @@ public class AreaStyle extends RenderStyle {
|
|||||||
|
|
||||||
public AreaBuilder reset() {
|
public AreaBuilder reset() {
|
||||||
color = Color.BLACK;
|
color = Color.BLACK;
|
||||||
|
strokeColor = Color.BLACK;
|
||||||
outlineColor = Color.TRANSPARENT;
|
strokeWidth = 0;
|
||||||
outlineWidth = 1;
|
|
||||||
|
|
||||||
fadeScale = -1;
|
fadeScale = -1;
|
||||||
blendScale = -1;
|
blendScale = -1;
|
||||||
blendColor = Color.TRANSPARENT;
|
blendColor = Color.TRANSPARENT;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user