source: josm/trunk/src/org/openstreetmap/josm/gui/mappaint/xml/XmlStyleSource.java@ 3827

Last change on this file since 3827 was 3827, checked in by bastiK, 13 years ago

IconElemStyle: delay the loading of imagage icon until it is actually displayed on screen

  • Property svn:eol-style set to native
File size: 8.4 KB
Line 
1// License: GPL. For details, see LICENSE file.
2package org.openstreetmap.josm.gui.mappaint.xml;
3
4import java.io.File;
5import java.util.Collection;
6import java.util.Collections;
7import java.util.HashMap;
8import java.util.Iterator;
9import java.util.LinkedList;
10import java.util.List;
11
12import org.openstreetmap.josm.data.osm.Node;
13import org.openstreetmap.josm.data.osm.OsmPrimitive;
14import org.openstreetmap.josm.data.osm.OsmUtils;
15import org.openstreetmap.josm.data.osm.Way;
16import org.openstreetmap.josm.gui.mappaint.ElemStyles.WayPrototypesRecord;
17import org.openstreetmap.josm.gui.preferences.SourceEntry;
18
19public class XmlStyleSource extends SourceEntry {
20
21 public final HashMap<String, IconPrototype> icons = new HashMap<String, IconPrototype>();
22 public final HashMap<String, LinePrototype> lines = new HashMap<String, LinePrototype>();
23 public final HashMap<String, LinemodPrototype> modifiers = new HashMap<String, LinemodPrototype>();
24 public final HashMap<String, AreaPrototype> areas = new HashMap<String, AreaPrototype>();
25 public final LinkedList<IconPrototype> iconsList = new LinkedList<IconPrototype>();
26 public final LinkedList<LinePrototype> linesList = new LinkedList<LinePrototype>();
27 public final LinkedList<LinemodPrototype> modifiersList = new LinkedList<LinemodPrototype>();
28 public final LinkedList<AreaPrototype> areasList = new LinkedList<AreaPrototype>();
29
30 public boolean hasError = false;
31 public File zipIcons;
32
33 public XmlStyleSource(String url, String name, String shortdescription) {
34 super(url, name, shortdescription, true);
35 }
36
37 public XmlStyleSource(SourceEntry entry) {
38 super(entry.url, entry.name, entry.shortdescription, entry.active);
39 }
40
41 public IconPrototype getNode(OsmPrimitive primitive, IconPrototype icon) {
42 for (String key : primitive.keySet()) {
43 String val = primitive.get(key);
44 IconPrototype style;
45 if ((style = icons.get("n" + key + "=" + val)) != null) {
46 if (icon == null || style.priority >= icon.priority) {
47 icon = style;
48 }
49 }
50 if ((style = icons.get("b" + key + "=" + OsmUtils.getNamedOsmBoolean(val))) != null) {
51 if (icon == null || style.priority >= icon.priority) {
52 icon = style;
53 }
54 }
55 if ((style = icons.get("x" + key)) != null) {
56 if (icon == null || style.priority >= icon.priority) {
57 icon = style;
58 }
59 }
60 }
61 for (IconPrototype s : iconsList) {
62 if ((icon == null || s.priority >= icon.priority) && s.check(primitive)) {
63 icon = s;
64 }
65 }
66 return icon;
67 }
68
69 /**
70 * @param closed The primitive is a closed way or we pretend it is closed.
71 * This is useful for multipolygon relations and outer ways of untagged
72 * multipolygon relations.
73 */
74 public void get(OsmPrimitive primitive, boolean closed, WayPrototypesRecord p) {
75 String lineIdx = null;
76 HashMap<String, LinemodPrototype> overlayMap = new HashMap<String, LinemodPrototype>();
77 for (String key : primitive.keySet()) {
78 String val = primitive.get(key);
79 AreaPrototype styleArea;
80 LinePrototype styleLine;
81 LinemodPrototype styleLinemod;
82 String idx = "n" + key + "=" + val;
83 if ((styleArea = areas.get(idx)) != null && (p.area == null || styleArea.priority >= p.area.priority) && (closed || !styleArea.closed)) {
84 p.area = styleArea;
85 }
86 if ((styleLine = lines.get(idx)) != null && (p.line == null || styleLine.priority >= p.line.priority)) {
87 p.line = styleLine;
88 lineIdx = idx;
89 }
90 if ((styleLinemod = modifiers.get(idx)) != null) {
91 overlayMap.put(idx, styleLinemod);
92 }
93 idx = "b" + key + "=" + OsmUtils.getNamedOsmBoolean(val);
94 if ((styleArea = areas.get(idx)) != null && (p.area == null || styleArea.priority >= p.area.priority) && (closed || !styleArea.closed)) {
95 p.area = styleArea;
96 }
97 if ((styleLine = lines.get(idx)) != null && (p.line == null || styleLine.priority >= p.line.priority)) {
98 p.line = styleLine;
99 lineIdx = idx;
100 }
101 if ((styleLinemod = modifiers.get(idx)) != null) {
102 overlayMap.put(idx, styleLinemod);
103 }
104 idx = "x" + key;
105 if ((styleArea = areas.get(idx)) != null && (p.area == null || styleArea.priority >= p.area.priority) && (closed || !styleArea.closed)) {
106 p.area = styleArea;
107 }
108 if ((styleLine = lines.get(idx)) != null && (p.line == null || styleLine.priority >= p.line.priority)) {
109 p.line = styleLine;
110 lineIdx = idx;
111 }
112 if ((styleLinemod = modifiers.get(idx)) != null) {
113 overlayMap.put(idx, styleLinemod);
114 }
115 }
116 for (AreaPrototype s : areasList) {
117 if ((p.area == null || s.priority >= p.area.priority) && (closed || !s.closed) && s.check(primitive)) {
118 p.area = s;
119 }
120 }
121 for (LinePrototype s : linesList) {
122 if ((p.line == null || s.priority >= p.line.priority) && s.check(primitive)) {
123 p.line = s;
124 }
125 }
126 for (LinemodPrototype s : modifiersList) {
127 if (s.check(primitive)) {
128 overlayMap.put(s.getCode(), s);
129 }
130 }
131 overlayMap.remove(lineIdx); // do not use overlay if linestyle is from the same rule (example: railway=tram)
132 if (!overlayMap.isEmpty() && p.line != null) {
133 List<LinemodPrototype> tmp = new LinkedList<LinemodPrototype>();
134 if (p.linemods != null) {
135 tmp.addAll(p.linemods);
136 }
137 tmp.addAll(overlayMap.values());
138 Collections.sort(tmp);
139 p.linemods = tmp;
140 }
141 }
142
143 public boolean isArea(OsmPrimitive o) {
144 if (o.hasKeys() && !(o instanceof Node)) {
145 boolean noclosed = o instanceof Way && !((Way) o).isClosed();
146 Iterator<String> iterator = o.keySet().iterator();
147 while (iterator.hasNext()) {
148 String key = iterator.next();
149 String val = o.get(key);
150 AreaPrototype s = areas.get("n" + key + "=" + val);
151 if (s == null || (s.closed && noclosed)) {
152 s = areas.get("b" + key + "=" + OsmUtils.getNamedOsmBoolean(val));
153 }
154 if (s == null || (s.closed && noclosed)) {
155 s = areas.get("x" + key);
156 }
157 if (s != null && !(s.closed && noclosed)) {
158 return true;
159 }
160 }
161 for (AreaPrototype s : areasList) {
162 if (!(s.closed && noclosed) && s.check(o)) {
163 return true;
164 }
165 }
166 }
167 return false;
168 }
169
170 public boolean hasAreas() {
171 return areas.size() > 0;
172 }
173
174 public void add(XmlCondition c, Collection<XmlCondition> conditions, Prototype prot) {
175 if(conditions != null)
176 {
177 prot.conditions = conditions;
178 if (prot instanceof IconPrototype) {
179 iconsList.add((IconPrototype) prot);
180 } else if (prot instanceof LinemodPrototype) {
181 modifiersList.add((LinemodPrototype) prot);
182 } else if (prot instanceof LinePrototype) {
183 linesList.add((LinePrototype) prot);
184 } else if (prot instanceof AreaPrototype) {
185 areasList.add((AreaPrototype) prot);
186 } else
187 throw new RuntimeException();
188 }
189 else {
190 String key = c.getKey();
191 prot.code = key;
192 if (prot instanceof IconPrototype) {
193 icons.put(key, (IconPrototype) prot);
194 } else if (prot instanceof LinemodPrototype) {
195 modifiers.put(key, (LinemodPrototype) prot);
196 } else if (prot instanceof LinePrototype) {
197 lines.put(key, (LinePrototype) prot);
198 } else if (prot instanceof AreaPrototype) {
199 areas.put(key, (AreaPrototype) prot);
200 } else
201 throw new RuntimeException();
202 }
203 }
204}
Note: See TracBrowser for help on using the repository browser.