Mark Burton wrote:
Hi Johann,

Hi Mark,

I've not tested the patch, but looked at the diff. Could not see the sense in it at a glance. For me it makes no difference to the previous state.
What do you intend with this patch?

Regards,
Johann

If I understand the problem correctly, if someone (Felix, for example)
generates multiple lines from the same OSM way and one of the lines is
routable and the other(s) are not, then the original DP code would
generate different shaped lines for the routable and non-routable ways
because only the routable version of the line had CoordNodes in it. So,
my patch just marks those points that are going to be nodes but that's
done before the way is duplicated so those marked points will be seen
in the DP code for both the routable and non-routable lines that are
based on the same set of points. That's the theory, hopefully someone
(Felix, for example) will test the patch and let us know if it works as
expected.

Cheers,

Mark
okay back...

Well running ant-clean it now doesn't even compile using the patch (of course I know that not ant-clean is the problem here, more that I did not use it before cause I though just another patch on top...)

[javac] Compiling 315 source files to d:\Garmin\mkgmap_svn_trunk\build\classes [javac] d:\Garmin\mkgmap_svn_trunk\src\uk\me\parabola\mkgmap\filters\RoundCoordsFilter.java:56: cannot find symbol
[javac] symbol  : method isBoundary()
[javac] location: class uk.me.parabola.imgfmt.app.CoordNode
[javac] newP = new CoordNode(lat, lon, ((CoordNode)p).getId(), ((CoordNode)p).isBoundary()); [javac] ^ [javac] d:\Garmin\mkgmap_svn_trunk\src\uk\me\parabola\mkgmap\filters\RoundCoordsFilter.java:56: internal error; cannot instantiate Co [javac] newP = new CoordNode(lat, lon, ((CoordNode)p).getId(), ((CoordNode)p).isBoundary());
[javac]                                            ^

I attach the patches that I am using. - I think the mb-round-coords-v2 is causing some problems in combination.


-- I'll remove that patch and try again the DP-avoid filter without round cords. More soon.
_______________________________________________
mkgmap-dev mailing list
[email protected]
http://www.mkgmap.org.uk/mailman/listinfo/mkgmap-dev
Index: src/uk/me/parabola/mkgmap/build/MapBuilder.java
===================================================================
--- src/uk/me/parabola/mkgmap/build/MapBuilder.java
+++ src/uk/me/parabola/mkgmap/build/MapBuilder.java
@@ -61,6 +61,7 @@ import uk.me.parabola.mkgmap.filters.MapFilter;
 import uk.me.parabola.mkgmap.filters.MapFilterChain;
 import uk.me.parabola.mkgmap.filters.PolygonSplitterFilter;
 import uk.me.parabola.mkgmap.filters.RemoveEmpty;
+import uk.me.parabola.mkgmap.filters.RoundCoordsFilter;
 import uk.me.parabola.mkgmap.filters.SizeFilter;
 import uk.me.parabola.mkgmap.general.LevelInfo;
 import uk.me.parabola.mkgmap.general.LoadableMapDataSource;
@@ -867,6 +868,7 @@ public class MapBuilder implements Configurable {
 
 		LayerFilterChain filters = new LayerFilterChain(config);
 		if (enableLineCleanFilters && (res < 24)) {
+			filters.addFilter(new RoundCoordsFilter());
 			filters.addFilter(new SizeFilter());
 			filters.addFilter(new DouglasPeuckerFilter(FILTER_DISTANCE));
 		}
@@ -903,6 +905,7 @@ public class MapBuilder implements Configurable {
 		config.setResolution(res);
 		LayerFilterChain filters = new LayerFilterChain(config);
 		if (enableLineCleanFilters && (res < 24)) {
+			filters.addFilter(new RoundCoordsFilter());
 			filters.addFilter(new SizeFilter());
 			//DouglasPeucker behaves at the moment not really optimal at low zooms, but acceptable.
 			//Is there an similar algorithm for polygons?
Index: src/uk/me/parabola/mkgmap/filters/RoundCoordsFilter.java
===================================================================
--- /dev/null
+++ srcuk/me/parabola/mkgmap/filters/RoundCoordsFilter.java
@@ -0,0 +1,75 @@
+/*
+ * Copyright (C) 2007 Steve Ratcliffe
+ * 
+ *  This program is free software; you can redistribute it and/or modify
+ *  it under the terms of the GNU General Public License version 2 as
+ *  published by the Free Software Foundation.
+ * 
+ *  This program is distributed in the hope that it will be useful,
+ *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+ *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ *  GNU General Public License for more details.
+ * 
+ */
+package uk.me.parabola.mkgmap.filters;
+
+import uk.me.parabola.imgfmt.app.Coord;
+import uk.me.parabola.imgfmt.app.CoordNode;
+
+import uk.me.parabola.mkgmap.general.MapElement;
+import uk.me.parabola.mkgmap.general.MapLine;
+
+import java.util.ArrayList;
+import java.util.List;
+
+public class RoundCoordsFilter implements MapFilter {
+
+	int shift;
+
+	public void init(FilterConfig config) {
+		shift = config.getShift();
+	}
+
+	/**
+	 * @param element A map element that will be a line or a polygon.
+	 * @param next This is used to pass the possibly transformed element onward.
+	 */
+	public void doFilter(MapElement element, MapFilterChain next) {
+		MapLine line = (MapLine) element;
+		int half = 1 << (shift - 1);	// 0.5 shifted
+		int mask = ~((1 << shift) - 1); // to remove fraction bits
+
+		if(shift == 0) {
+			// do nothing
+			next.doFilter(line);
+		}
+		else {
+			// round lat/lon values to nearest for shift
+			List<Coord> newPoints = new ArrayList<Coord>(line.getPoints().size());
+			MapLine newLine = line.copy();
+			Coord lastP = null;
+			for(Coord p : line.getPoints()) {
+				int lat = (p.getLatitude() + half) & mask;
+				int lon = (p.getLongitude() + half) & mask;
+				Coord newP;
+				if(p instanceof CoordNode)
+					newP = new CoordNode(lat, lon, ((CoordNode)p).getId(), ((CoordNode)p).isBoundary());
+				else
+					newP = new Coord(lat, lon);
+				// only add the new point if it has different
+				// coordinates to the last point or if it's a
+				// CoordNode and the last point wasn't a CoordNode
+				if(lastP == null ||
+				   !lastP.equals(newP) ||
+				   (newP instanceof CoordNode && !(lastP instanceof CoordNode))) {
+					newPoints.add(newP);
+					lastP = newP;
+				}
+			}
+			if(newPoints.size() > 1) {
+				newLine.setPoints(newPoints);
+				next.doFilter(newLine);
+			}
+		}
+	}
+}
Index: src/uk/me/parabola/mkgmap/osmstyle/SequenceRule.java
===================================================================
--- src/uk/me/parabola/mkgmap/osmstyle/SequenceRule.java	(revision 1144)
+++ src/uk/me/parabola/mkgmap/osmstyle/SequenceRule.java	(working copy)
@@ -34,9 +34,9 @@
 public class SequenceRule implements Rule, Iterable<Rule> {
 	private final List<Rule> ruleList = new ArrayList<Rule>();
 
-	public GType resolveType(Element el) {
+	public GType resolveType(Element el, GType pre) {
 		for (Rule r : ruleList) {
-			GType type = r.resolveType(el);
+			GType type = r.resolveType(el, pre);
 			if (type != null)
 				return type;
 		}
Index: src/uk/me/parabola/mkgmap/osmstyle/TypeReader.java
===================================================================
--- src/uk/me/parabola/mkgmap/osmstyle/TypeReader.java	(revision 1144)
+++ src/uk/me/parabola/mkgmap/osmstyle/TypeReader.java	(working copy)
@@ -58,6 +58,10 @@
 				gt.setRoadSpeed(nextIntValue(ts));
 			} else if (w.equals("copy")) {
 				// reserved word.  not currently used
+			} else if (w.equals("continue")) {
+				gt.setContinue();
+			} else if (w.equals("stop")) {
+				gt.setFinal();
 			} else {
 				throw new SyntaxException(ts, "Unrecognised type command '" + w + '\'');
 			}
Index: src/uk/me/parabola/mkgmap/osmstyle/ActionRule.java
===================================================================
--- src/uk/me/parabola/mkgmap/osmstyle/ActionRule.java	(revision 1144)
+++ src/uk/me/parabola/mkgmap/osmstyle/ActionRule.java	(working copy)
@@ -52,7 +52,7 @@
 		this.type = null;
 	}
 
-	public GType resolveType(Element el) {
+	public GType resolveType(Element el, GType pre) {
 		if (expression == null || expression.eval(el)) {
 			for (Action a : actions)
 				a.perform(el);
Index: src/uk/me/parabola/mkgmap/osmstyle/RuleSet.java
===================================================================
--- src/uk/me/parabola/mkgmap/osmstyle/RuleSet.java	(revision 1144)
+++ src/uk/me/parabola/mkgmap/osmstyle/RuleSet.java	(working copy)
@@ -63,14 +63,14 @@
 		return rules.entrySet();
 	}
 
-	public GType resolveType(Element el) {
+	public GType resolveType(Element el, GType pre) {
 		GType foundType = null;
 		for (String tagKey : el) {
 			Rule rule = rules.get(tagKey);
 			if (rule != null) {
-				GType type = rule.resolveType(el);
+				GType type = rule.resolveType(el, pre);
 				if (type != null) {
-					if (foundType == null || type.isBetterPriority(foundType)) {
+					if ((foundType == null || type.isBetterPriority(foundType)) && (pre == null || pre.isBetterPriority(type))) {
 						foundType = type;
 					}
 				}
Index: src/uk/me/parabola/mkgmap/osmstyle/FixedRule.java
===================================================================
--- src/uk/me/parabola/mkgmap/osmstyle/FixedRule.java	(revision 1144)
+++ src/uk/me/parabola/mkgmap/osmstyle/FixedRule.java	(working copy)
@@ -32,7 +32,7 @@
 		this.gtype = gtype;
 	}
 
-	public GType resolveType(Element el) {
+	public GType resolveType(Element el, GType pre) {
 		return gtype;
 	}
 
Index: src/uk/me/parabola/mkgmap/osmstyle/ExpressionRule.java
===================================================================
--- src/uk/me/parabola/mkgmap/osmstyle/ExpressionRule.java	(revision 1144)
+++ src/uk/me/parabola/mkgmap/osmstyle/ExpressionRule.java	(working copy)
@@ -28,22 +28,22 @@
  * @author Steve Ratcliffe
  */
 public class ExpressionRule implements Rule {
-	private final Op exression;
+	private final Op expression;
 	private final GType gtype;
 
-	public ExpressionRule(Op exression, GType gtype) {
-		this.exression = exression;
+	public ExpressionRule(Op expression, GType gtype) {
+		this.expression = expression;
 		this.gtype = gtype;
 	}
 
-	public GType resolveType(Element el) {
-		if (exression.eval(el))
+	public GType resolveType(Element el, GType pre) {
+		if (expression.eval(el))
 			return gtype;
 
 		return null;
 	}
 
 	public String toString() {
-		return exression.toString() + ' ' + gtype;
+		return expression.toString() + ' ' + gtype;
 	}
 }
Index: src/uk/me/parabola/mkgmap/osmstyle/StyledConverter.java
===================================================================
--- src/uk/me/parabola/mkgmap/osmstyle/StyledConverter.java	(revision 1144)
+++ src/uk/me/parabola/mkgmap/osmstyle/StyledConverter.java	(working copy)
@@ -247,26 +247,38 @@
 			foundType = makeGTypeFromTags(way);
 			if(foundType == null)
 				return;
+
+			if (foundType.getFeatureKind() == GType.POLYLINE) {
+				if(foundType.isRoad() &&
+				!MapElement.hasExtendedType(foundType.getType()))
+					addRoad(way, foundType);
+				else
+					addLine(way, foundType);
+			}
+			else
+				addShape(way, foundType);
+
 		}
 		else {
 			preConvertRules(way);
 
-			foundType = wayRules.resolveType(way);
-			if (foundType == null)
-				return;
+			do {
+				foundType = wayRules.resolveType(way, foundType);
+				if (foundType == null)
+					return;
 
-			postConvertRules(way, foundType);
-		}
+				postConvertRules(way, foundType);
 
-		if (foundType.getFeatureKind() == GType.POLYLINE) {
-		    if(foundType.isRoad() &&
-			   !MapElement.hasExtendedType(foundType.getType()))
-				addRoad(way, foundType);
-		    else
-				addLine(way, foundType);
+				if (foundType.getFeatureKind() == GType.POLYLINE) {
+					if(foundType.isRoad())
+						addRoad(way, foundType);
+					else
+						addLine(way, foundType);
+				}
+				else
+					addShape(way, foundType);
+			} while (!foundType.isFinal());
 		}
-		else
-			addShape(way, foundType);
 	}
 
 	/**
@@ -282,18 +294,21 @@
 			foundType = makeGTypeFromTags(node);
 			if(foundType == null)
 				return;
+			addPoint(node, foundType);
 		}
 		else {
 			preConvertRules(node);
 
-			foundType = nodeRules.resolveType(node);
-			if (foundType == null)
-				return;
+			do {
+				foundType = nodeRules.resolveType(node, foundType);
+				if (foundType == null)
+					return;
+  
+				postConvertRules(node, foundType);
 
-			postConvertRules(node, foundType);
+				addPoint(node, foundType);
+			} while (!foundType.isFinal());
 		}
-
-		addPoint(node, foundType);
 	}
 
 	/**
@@ -349,7 +364,7 @@
 	public void convertRelation(Relation relation) {
 		// Relations never resolve to a GType and so we ignore the return
 		// value.
-		relationRules.resolveType(relation);
+		relationRules.resolveType(relation, null);
 
 		if(relation instanceof RestrictionRelation) {
 			RestrictionRelation rr = (RestrictionRelation)relation;
@@ -382,7 +397,7 @@
 
 		clipper.clipShape(shape, collector);
 		
-		GType pointType = nodeRules.resolveType(way);
+		GType pointType = nodeRules.resolveType(way, null);
 		
 		if(pointType != null)
 			shape.setPoiType(pointType.getType());
Index: src/uk/me/parabola/mkgmap/reader/osm/Rule.java
===================================================================
--- src/uk/me/parabola/mkgmap/reader/osm/Rule.java	(revision 1144)
+++ src/uk/me/parabola/mkgmap/reader/osm/Rule.java	(working copy)
@@ -29,7 +29,8 @@
 	 * represent it.
 	 *
 	 * @param el The element as read from an OSM xml file in 'tag' format.
+	 * @param pre The previous garmin type generated from the element.
 	 * @return Enough information to represent this as a garmin type.
 	 */
-	public GType resolveType(Element el);
+	public GType resolveType(Element el, GType pre);
 }
Index: src/uk/me/parabola/mkgmap/reader/osm/GType.java
===================================================================
--- src/uk/me/parabola/mkgmap/reader/osm/GType.java	(revision 1144)
+++ src/uk/me/parabola/mkgmap/reader/osm/GType.java	(working copy)
@@ -58,6 +58,11 @@
 
 	private boolean road;
 
+	// control flag, whether this element defines
+	// the final conversion, or whether we shall search
+	// for further matching elements
+	private boolean FinalElement = true;
+	
 	public GType(int featureKind, String type) {
 		priority = nextPriority();
 		this.featureKind = featureKind;
@@ -190,6 +195,18 @@
 		return road;
 	}
 
+	public void setFinal() {
+		FinalElement = true;
+	}
+	
+	public void setContinue() {
+		FinalElement = false;
+	}
+	
+	public boolean isFinal() {
+		return FinalElement;
+	}
+	
 	public static void push() {
 		nextPriority += PRIORITY_PUSH;
 	}
Index: src/uk/me/parabola/imgfmt/app/trergn/TREHeader.java
===================================================================
--- src/uk/me/parabola/imgfmt/app/trergn/TREHeader.java	(revision 1379)
+++ src/uk/me/parabola/imgfmt/app/trergn/TREHeader.java	(working copy)
@@ -172,7 +172,7 @@
 		writer.put(getPoiDisplayFlags());
 
 		writer.put3(displayPriority);
-		writer.putInt(0x110301);
+		writer.putInt(0x170401);
 
 		writer.putChar((char) 1);
 		writer.put((byte) 0);
_______________________________________________
mkgmap-dev mailing list
[email protected]
http://www.mkgmap.org.uk/mailman/listinfo/mkgmap-dev

Reply via email to