diff options
author | Sven Gothel <[email protected]> | 2014-02-27 09:43:25 +0100 |
---|---|---|
committer | Sven Gothel <[email protected]> | 2014-02-27 09:43:25 +0100 |
commit | 073ac5ab63af792d8468d8bf074b982f7c44ef33 (patch) | |
tree | fb1fc78c8b4e5ba22936ef7d71a3fc993b8b8041 /src/jogl/classes/jogamp/graph/font | |
parent | 80a0ddd084e674fbfff007e6a83eec6162aaa32d (diff) |
Bug 801: Graph TextRenderer Cleanup Part-2: Remove Path2D from Glyph/Typecast* ; Misc Cleanup
Commit c3621221b9a563495b4f54fe60e18e8db8cc57fb introduced
create an OutlineShape per Glyph from it's data w/o going through Path2D.
Misc Cleanup: Remove unused code/fields, use private/final where possible.
Diffstat (limited to 'src/jogl/classes/jogamp/graph/font')
5 files changed, 49 insertions, 349 deletions
diff --git a/src/jogl/classes/jogamp/graph/font/FontInt.java b/src/jogl/classes/jogamp/graph/font/FontInt.java deleted file mode 100644 index f87a00251..000000000 --- a/src/jogl/classes/jogamp/graph/font/FontInt.java +++ /dev/null @@ -1,44 +0,0 @@ -/** - * Copyright 2011 JogAmp Community. All rights reserved. - * - * Redistribution and use in source and binary forms, with or without modification, are - * permitted provided that the following conditions are met: - * - * 1. Redistributions of source code must retain the above copyright notice, this list of - * conditions and the following disclaimer. - * - * 2. Redistributions in binary form must reproduce the above copyright notice, this list - * of conditions and the following disclaimer in the documentation and/or other materials - * provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY JogAmp Community ``AS IS'' AND ANY EXPRESS OR IMPLIED - * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND - * FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JogAmp Community OR - * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR - * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR - * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON - * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING - * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF - * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - * - * The views and conclusions contained in the software and documentation are those of the - * authors and should not be interpreted as representing official policies, either expressed - * or implied, of JogAmp Community. - */ -package jogamp.graph.font; - -import jogamp.graph.geom.plane.Path2D; - -import com.jogamp.graph.font.Font; - -/** - * @deprecated - */ -public interface FontInt extends Font { - - public interface GlyphInt extends Font.Glyph { - public Path2D getPath(); // unscaled path - public Path2D getPath(float pixelSize); - } - -} diff --git a/src/jogl/classes/jogamp/graph/font/typecast/TypecastFont.java b/src/jogl/classes/jogamp/graph/font/typecast/TypecastFont.java index 41fa6c223..81c06cd83 100644 --- a/src/jogl/classes/jogamp/graph/font/typecast/TypecastFont.java +++ b/src/jogl/classes/jogamp/graph/font/typecast/TypecastFont.java @@ -27,9 +27,6 @@ */ package jogamp.graph.font.typecast; -import java.util.List; - -import jogamp.graph.font.FontInt; import jogamp.graph.font.typecast.ot.OTFont; import jogamp.graph.font.typecast.ot.OTFontCollection; import jogamp.graph.font.typecast.ot.table.CmapFormat; @@ -37,8 +34,6 @@ import jogamp.graph.font.typecast.ot.table.CmapIndexEntry; import jogamp.graph.font.typecast.ot.table.CmapTable; import jogamp.graph.font.typecast.ot.table.HdmxTable; import jogamp.graph.font.typecast.ot.table.ID; -import jogamp.graph.geom.plane.AffineTransform; -import jogamp.graph.geom.plane.Path2D; import com.jogamp.common.util.IntObjectHashMap; import com.jogamp.graph.curve.OutlineShape; @@ -46,23 +41,22 @@ import com.jogamp.graph.font.Font; import com.jogamp.graph.font.FontFactory; import com.jogamp.graph.geom.SVertex; import com.jogamp.graph.geom.Vertex; -import com.jogamp.graph.geom.Vertex.Factory; import com.jogamp.opengl.math.geom.AABBox; -class TypecastFont implements FontInt { +class TypecastFont implements Font { static final boolean DEBUG = false; private static final Vertex.Factory<SVertex> vertexFactory = SVertex.factory(); - final OTFontCollection fontset; - final OTFont font; - TypecastHMetrics metrics; - final CmapFormat cmapFormat; - int cmapentries; + // private final OTFontCollection fontset; + /* pp */ final OTFont font; + private final CmapFormat cmapFormat; + private final int cmapentries; + private final IntObjectHashMap char2Glyph; + private final TypecastHMetrics metrics; // FIXME: Add cache size to limit memory usage ?? - IntObjectHashMap char2Glyph; - public TypecastFont(OTFontCollection fontset) { - this.fontset = fontset; + public TypecastFont(final OTFontCollection fontset) { + // this.fontset = fontset; this.font = fontset.getFont(0); // FIXME: Generic attempt to find the best CmapTable, @@ -124,10 +118,13 @@ class TypecastFont implements FontInt { } } - cmapentries = 0; - for (int i = 0; i < cmapFormat.getRangeCount(); ++i) { - CmapFormat.Range range = cmapFormat.getRange(i); - cmapentries += range.getEndCode() - range.getStartCode() + 1; // end included + { + int _cmapentries = 0; + for (int i = 0; i < cmapFormat.getRangeCount(); ++i) { + CmapFormat.Range range = cmapFormat.getRange(i); + _cmapentries += range.getEndCode() - range.getStartCode() + 1; // end included + } + cmapentries = _cmapentries; } if(DEBUG) { System.err.println("font direction hint: "+font.getHeadTable().getFontDirectionHint()); @@ -146,6 +143,7 @@ class TypecastFont implements FontInt { } } char2Glyph = new IntObjectHashMap(cmapentries + cmapentries/4); + metrics = new TypecastHMetrics(this); } @Override @@ -173,10 +171,7 @@ class TypecastFont implements FontInt { } @Override - public Metrics getMetrics() { - if (metrics == null) { - metrics = new TypecastHMetrics(this); - } + public final Metrics getMetrics() { return metrics; } @@ -203,11 +198,9 @@ class TypecastFont implements FontInt { throw new RuntimeException("Could not retrieve glyph for symbol: <"+symbol+"> "+(int)symbol+" -> glyph id "+code); } final OutlineShape shape = TypecastRenderer.buildShape(glyph, vertexFactory); - // FIXME: Remove Path2D - final Path2D path = TypecastRenderer.buildPath(glyph); - result = new TypecastGlyph(this, symbol, code, glyph.getBBox(), glyph.getAdvanceWidth(), path, shape); + result = new TypecastGlyph(this, symbol, code, glyph.getBBox(), glyph.getAdvanceWidth(), shape); if(DEBUG) { - System.err.println("New glyph: " + (int)symbol + " ( " + symbol +" ) -> " + code + ", contours " + glyph.getPointCount() + ": " + path); + System.err.println("New glyph: " + (int)symbol + " ( " + symbol +" ) -> " + code + ", contours " + glyph.getPointCount() + ": " + shape); } final HdmxTable hdmx = font.getHdmxTable(); if (null!= result && null != hdmx) { @@ -228,13 +221,6 @@ class TypecastFont implements FontInt { return result; } - // FIXME: Remove altogether - @Override - public List<OutlineShape> getOutlineShapes(List<OutlineShape> shapes, CharSequence string, float pixelSize, Factory<? extends Vertex> vertexFactory) { - AffineTransform transform = new AffineTransform(vertexFactory); - return TypecastRenderer.getOutlineShapes(shapes, this, string, pixelSize, transform, vertexFactory); - } - @Override public float getStringWidth(CharSequence string, float pixelSize) { float width = 0; diff --git a/src/jogl/classes/jogamp/graph/font/typecast/TypecastGlyph.java b/src/jogl/classes/jogamp/graph/font/typecast/TypecastGlyph.java index 40727826b..82971848e 100644 --- a/src/jogl/classes/jogamp/graph/font/typecast/TypecastGlyph.java +++ b/src/jogl/classes/jogamp/graph/font/typecast/TypecastGlyph.java @@ -29,19 +29,15 @@ package jogamp.graph.font.typecast; import java.util.HashMap; -import jogamp.graph.font.FontInt; -import jogamp.graph.geom.plane.AffineTransform; -import jogamp.graph.geom.plane.Path2D; - import com.jogamp.graph.curve.OutlineShape; import com.jogamp.graph.font.Font; import com.jogamp.opengl.math.geom.AABBox; -public class TypecastGlyph implements FontInt.GlyphInt { +public class TypecastGlyph implements Font.Glyph { public class Advance { - final Font font; - final float advance; + private final Font font; + private final float advance; HashMap<Float, Float> size2advance = new HashMap<Float, Float>(); public Advance(Font font, float advance) @@ -66,7 +62,7 @@ public class TypecastGlyph implements FontInt.GlyphInt { public float get(float size, boolean useFrationalMetrics) { - Float fo = size2advance.get(size); + final Float fo = size2advance.get(size); if(null == fo) { float value = (this.advance * getScale(size)); if (useFrationalMetrics == false) { @@ -91,8 +87,8 @@ public class TypecastGlyph implements FontInt.GlyphInt { public class Metrics { - AABBox bbox; - Advance advance; + private final AABBox bbox; + private final Advance advance; public Metrics(Font font, AABBox bbox, float advance) { @@ -137,41 +133,16 @@ public class TypecastGlyph implements FontInt.GlyphInt { public static final short MAX_ID = (short)((1 << 16) - 2); private final Font font; - protected final char symbol; - protected final OutlineShape shape; // in EM units - - protected final Path2D path; // in EM units FIXME remove! - - short id; - int advance; - Metrics metrics; - - protected Path2D pathSized; // FIXME remove! - protected float numberSized; // FIXME remove! + private final char symbol; + private final OutlineShape shape; // in EM units + private final short id; + private final int advance; + private final Metrics metrics; - protected TypecastGlyph(Font font, char symbol) { - this.font = font; - this.symbol = symbol; - this.shape = null; - this.path = null; - } - - protected TypecastGlyph(Font font, - char symbol, short id, AABBox bbox, int advance, Path2D path, OutlineShape shape) { + protected TypecastGlyph(Font font, char symbol, short id, AABBox bbox, int advance, OutlineShape shape) { this.font = font; this.symbol = symbol; this.shape = shape; - this.path = path; - - this.advance = advance; - - init(id, bbox, advance); - - this.pathSized = null; - this.numberSized = 0.0f; - } - - void init(short id, AABBox bbox, int advance) { this.id = id; this.advance = advance; this.metrics = new Metrics(this.font, bbox, this.advance); @@ -184,74 +155,62 @@ public class TypecastGlyph implements FontInt.GlyphInt { } */ @Override - public Font getFont() { + public final Font getFont() { return this.font; } @Override - public char getSymbol() { + public final char getSymbol() { return this.symbol; } - AABBox getBBoxUnsized() { + final AABBox getBBoxUnsized() { return this.metrics.getBBox(); } - public AABBox getBBox() { + @Override + public final AABBox getBBox() { return this.metrics.getBBox(); } - public Metrics getMetrics() { + public final Metrics getMetrics() { return this.metrics; } - public short getID() { + @Override + public final short getID() { return this.id; } - public float getScale(float pixelSize) { + @Override + public final float getScale(float pixelSize) { return this.metrics.getScale(pixelSize); } @Override - public AABBox getBBox(float pixelSize) { + public final AABBox getBBox(float pixelSize) { final float size = getScale(pixelSize); AABBox newBox = getBBox().clone(); newBox.scale(size); return newBox; } - protected void addAdvance(float advance, float size) { + protected final void addAdvance(float advance, float size) { this.metrics.addAdvance(advance, size); } @Override - public float getAdvance(float pixelSize, boolean useFrationalMetrics) { + public final float getAdvance(float pixelSize, boolean useFrationalMetrics) { return this.metrics.getAdvance(pixelSize, useFrationalMetrics); } @Override - public OutlineShape getShape() { + public final OutlineShape getShape() { return this.shape; } @Override - public Path2D getPath() { - return this.path; - } - - @Override - public Path2D getPath(float pixelSize) { - final float size = getScale(pixelSize); - - if (this.numberSized != size) { - this.numberSized = size; - this.pathSized = AffineTransform.getScaleInstance(null, size, size).createTransformedShape(getPath()); - } - return this.pathSized; - } - - public int hashCode() { + public final int hashCode() { // 31 * x == (x << 5) - x int hash = 31 + font.getName(Font.NAME_UNIQUNAME).hashCode(); return ((hash << 5) - hash) + id; diff --git a/src/jogl/classes/jogamp/graph/font/typecast/TypecastHMetrics.java b/src/jogl/classes/jogamp/graph/font/typecast/TypecastHMetrics.java index ecc41e438..7efad5fb0 100644 --- a/src/jogl/classes/jogamp/graph/font/typecast/TypecastHMetrics.java +++ b/src/jogl/classes/jogamp/graph/font/typecast/TypecastHMetrics.java @@ -50,7 +50,7 @@ class TypecastHMetrics implements Metrics { headTable = this.fontImpl.font.getHeadTable(); hheaTable = this.fontImpl.font.getHheaTable(); // vheaTable = this.fontImpl.font.getVheaTable(); - unitsPerEM_Inv = 1.0f / ( (float) headTable.getUnitsPerEm() ); + unitsPerEM_Inv = 1.0f / ( headTable.getUnitsPerEm() ); int maxWidth = headTable.getXMax() - headTable.getXMin(); int maxHeight = headTable.getYMax() - headTable.getYMin(); diff --git a/src/jogl/classes/jogamp/graph/font/typecast/TypecastRenderer.java b/src/jogl/classes/jogamp/graph/font/typecast/TypecastRenderer.java index 83ccadab3..c8feb26d3 100644 --- a/src/jogl/classes/jogamp/graph/font/typecast/TypecastRenderer.java +++ b/src/jogl/classes/jogamp/graph/font/typecast/TypecastRenderer.java @@ -27,145 +27,19 @@ */ package jogamp.graph.font.typecast; -import java.util.ArrayList; -import java.util.List; - -import jogamp.graph.font.FontInt.GlyphInt; import jogamp.graph.font.typecast.ot.OTGlyph; import jogamp.graph.font.typecast.ot.Point; -import jogamp.graph.geom.plane.AffineTransform; -import jogamp.graph.geom.plane.Path2D; -import jogamp.graph.geom.plane.PathIterator; import com.jogamp.graph.curve.OutlineShape; -import com.jogamp.graph.font.Font; -import com.jogamp.graph.font.Font.Glyph; import com.jogamp.graph.geom.Vertex; import com.jogamp.graph.geom.Vertex.Factory; /** - * Factory to build a {@link com.jogamp.graph.geom.Path2D Path2D} from + * Factory to build an {@link OutlineShape} from * {@link jogamp.graph.font.typecast.ot.OTGlyph Glyph}s. */ public class TypecastRenderer { - private static void getPaths(TypecastFont font, - CharSequence string, float pixelSize, AffineTransform transform, Path2D[] p) - { - if (string == null) { - return; - } - final Font.Metrics metrics = font.getMetrics(); - final float lineGap = metrics.getLineGap(pixelSize) ; - final float ascent = metrics.getAscent(pixelSize) ; - final float descent = metrics.getDescent(pixelSize) ; - final float advanceY = lineGap - descent + ascent; - final float scale = metrics.getScale(pixelSize); - if (transform == null) { - transform = new AffineTransform(); - } - final AffineTransform t = new AffineTransform(transform.getFactory()); - - final int len = string.length(); - - float advanceTotal = 0; - float y = 0; - - for (int i=0; i<len; i++) - { - p[i] = new Path2D(); - p[i].reset(); - final char character = string.charAt(i); - if (character == '\n') { - y += advanceY; - advanceTotal = 0; - } else if (character == ' ') { - advanceTotal += font.getAdvanceWidth(Glyph.ID_SPACE, pixelSize); - } else { - final Glyph glyph = font.getGlyph(character); - final Path2D gp = ((GlyphInt)glyph).getPath(); - t.setTransform(transform); // reset transform - t.translate(advanceTotal, y); - t.scale(scale, scale); - p[i].append(gp.iterator(t), false); - advanceTotal += glyph.getAdvance(pixelSize, true); - } - } - } - - public static OutlineShape getOutlineShape(TypecastFont font, Glyph glyph, Factory<? extends Vertex> vertexFactory) { - // FIXME: Remove Path2D - Path2D path = ((GlyphInt)glyph).getPath(); - AffineTransform transform = new AffineTransform(vertexFactory); - OutlineShape shape = new OutlineShape(vertexFactory); - - PathIterator iterator = path.iterator(transform); - if(null != iterator){ - while(!iterator.isDone()){ - float[] coords = new float[6]; - int segmentType = iterator.currentSegment(coords); - addPathVertexToOutline(shape, vertexFactory, coords, segmentType); - iterator.next(); - } - } - return shape; - } - - public static List<OutlineShape> getOutlineShapes(List<OutlineShape> shapes, TypecastFont font, CharSequence string, float pixelSize, AffineTransform transform, Factory<? extends Vertex> vertexFactory) { - // FIXME: Remove Path2D - // FIXME: Remove altogether - Path2D[] paths = new Path2D[string.length()]; - getPaths(font, string, pixelSize, transform, paths); - - if(null == shapes) { - shapes = new ArrayList<OutlineShape>(); - } - final int numGlyps = paths.length; - for (int index=0;index<numGlyps;index++) { - if(paths[index] == null){ - continue; - } - OutlineShape shape = new OutlineShape(vertexFactory); - shapes.add(shape); - PathIterator iterator = paths[index].iterator(transform); - if(null != iterator){ - while(!iterator.isDone()){ - float[] coords = new float[6]; - int segmentType = iterator.currentSegment(coords); - addPathVertexToOutline(shape, vertexFactory, coords, segmentType); - iterator.next(); - } - } - } - return shapes; - } - private static void addPathVertexToOutline(OutlineShape shape, Factory<? extends Vertex> vertexFactory, float[] coords, int segmentType){ - switch(segmentType) { - case PathIterator.SEG_MOVETO: - shape.closeLastOutline(); - shape.addEmptyOutline(); - shape.addVertex(0, vertexFactory.create(coords, 0, 2, true)); - break; - case PathIterator.SEG_LINETO: - shape.addVertex(0, vertexFactory.create(coords, 0, 2, true)); - break; - case PathIterator.SEG_QUADTO: - shape.addVertex(0, vertexFactory.create(coords, 0, 2, false)); - shape.addVertex(0, vertexFactory.create(coords, 2, 2, true)); - break; - case PathIterator.SEG_CUBICTO: - shape.addVertex(0, vertexFactory.create(coords, 0, 2, false)); - shape.addVertex(0, vertexFactory.create(coords, 2, 2, false)); - shape.addVertex(0, vertexFactory.create(coords, 4, 2, true)); - break; - case PathIterator.SEG_CLOSE: - shape.closeLastOutline(); - break; - default: - throw new IllegalArgumentException("Unhandled Segment Type: "+segmentType); - } - } - private static void addShapeMoveTo(final OutlineShape shape, Factory<? extends Vertex> vertexFactory, Point p1) { shape.closeLastOutline(); shape.addEmptyOutline(); @@ -278,81 +152,6 @@ public class TypecastRenderer { return shape; } - /** - * Build a {@link com.jogamp.graph.geom.Path2D Path2D} from a - * {@link jogamp.graph.font.typecast.ot.OTGlyph Glyph}. This glyph path can then - * be transformed and rendered. - */ - public static Path2D buildPath(OTGlyph glyph) { - - if (glyph == null) { - return null; - } - - Path2D glyphPath = new Path2D(); - - // Iterate through all of the points in the glyph. Each time we find a - // contour end point, add the point range to the path. - int firstIndex = 0; - int count = 0; - for (int i = 0; i < glyph.getPointCount(); i++) { - count++; - if (glyph.getPoint(i).endOfContour) { - addContourToPath(glyphPath, glyph, firstIndex, count); - firstIndex = i + 1; - count = 0; - } - } - return glyphPath; - } - - private static void addContourToPath(Path2D gp, OTGlyph glyph, int startIndex, int count) { - int offset = 0; - while (offset < count) { - Point point = glyph.getPoint(startIndex + offset%count); - Point point_plus1 = glyph.getPoint(startIndex + (offset+1)%count); - Point point_plus2 = glyph.getPoint(startIndex + (offset+2)%count); - if(offset == 0) - { - gp.moveTo(point.x, point.y); - } - - if (point.onCurve) { - if (point_plus1.onCurve) { - // s = new Line2D.Float(point.x, point.y, point_plus1.x, point_plus1.y); - gp.lineTo( point_plus1.x, point_plus1.y ); - offset++; - } else { - if (point_plus2.onCurve) { - // s = new QuadCurve2D.Float( point.x, point.y, point_plus1.x, point_plus1.y, point_plus2.x, point_plus2.y); - gp.quadTo(point_plus1.x, point_plus1.y, point_plus2.x, point_plus2.y); - offset+=2; - } else { - // s = new QuadCurve2D.Float(point.x,point.y,point_plus1.x,point_plus1.y, - // midValue(point_plus1.x, point_plus2.x), midValue(point_plus1.y, point_plus2.y)); - gp.quadTo(point_plus1.x, point_plus1.y, midValue(point_plus1.x, point_plus2.x), midValue(point_plus1.y, point_plus2.y)); - offset+=2; - } - } - } else { - if (point_plus1.onCurve) { - // s = new QuadCurve2D.Float(midValue(point_minus1.x, point.x), midValue(point_minus1.y, point.y), - // point.x, point.y, point_plus1.x, point_plus1.y); - //gp.curve3(point_plus1.x, point_plus1.y, point.x, point.y); - gp.quadTo(point.x, point.y, point_plus1.x, point_plus1.y); - offset++; - - } else { - // s = new QuadCurve2D.Float(midValue(point_minus1.x, point.x), midValue(point_minus1.y, point.y), point.x, point.y, - // midValue(point.x, point_plus1.x), midValue(point.y, point_plus1.y)); - //gp.curve3(midValue(point.x, point_plus1.x), midValue(point.y, point_plus1.y), point.x, point.y); - gp.quadTo(point.x, point.y, midValue(point.x, point_plus1.x), midValue(point.y, point_plus1.y)); - offset++; - } - } - } - } - private static int midValue(int a, int b) { return a + (b - a)/2; } |