mirror of
https://github.com/enzet/map-machine.git
synced 2025-05-23 05:56:28 +02:00
Issue #63: support ways, areas, and relations.
This commit is contained in:
parent
6635a5de4a
commit
0748bab9a5
9 changed files with 73 additions and 37 deletions
|
@ -107,10 +107,6 @@ def main(options) -> None:
|
||||||
Path(ICONS_FILE_NAME), Path("icons/config.json")
|
Path(ICONS_FILE_NAME), Path("icons/config.json")
|
||||||
)
|
)
|
||||||
|
|
||||||
def check_level(x) -> bool:
|
|
||||||
"""Draw objects on all levels."""
|
|
||||||
return True
|
|
||||||
|
|
||||||
if options.level:
|
if options.level:
|
||||||
if options.level == "overground":
|
if options.level == "overground":
|
||||||
check_level = check_level_overground
|
check_level = check_level_overground
|
||||||
|
|
|
@ -1,7 +1,6 @@
|
||||||
"""
|
"""
|
||||||
Construct Röntgen nodes and ways.
|
Construct Röntgen nodes and ways.
|
||||||
"""
|
"""
|
||||||
from collections import Counter
|
|
||||||
from datetime import datetime
|
from datetime import datetime
|
||||||
from hashlib import sha256
|
from hashlib import sha256
|
||||||
from typing import Any, Dict, Iterator, List, Optional, Set
|
from typing import Any, Dict, Iterator, List, Optional, Set
|
||||||
|
|
|
@ -1,9 +1,9 @@
|
||||||
"""
|
"""
|
||||||
Icon grid drawing.
|
Icon grid drawing.
|
||||||
"""
|
"""
|
||||||
from dataclasses import dataclass, field
|
from dataclasses import dataclass
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from typing import Dict, List, Optional, Set
|
from typing import List, Optional, Set
|
||||||
|
|
||||||
import logging
|
import logging
|
||||||
import numpy as np
|
import numpy as np
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
MapCSS scheme creation.
|
MapCSS scheme creation.
|
||||||
"""
|
"""
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from typing import Dict, List, Optional
|
from typing import List, Optional, Dict
|
||||||
|
|
||||||
import logging
|
import logging
|
||||||
from colour import Color
|
from colour import Color
|
||||||
|
@ -23,13 +23,8 @@ class MapCSSWriter:
|
||||||
self.add_icons_for_lifecycle = add_icons_for_lifecycle
|
self.add_icons_for_lifecycle = add_icons_for_lifecycle
|
||||||
self.icon_directory_name = icon_directory_name
|
self.icon_directory_name = icon_directory_name
|
||||||
|
|
||||||
self.matchers: Dict[Matcher, List[str]] = {}
|
self.point_matchers: List[Matcher] = scheme.node_matchers
|
||||||
for matcher in scheme.node_matchers:
|
self.line_matchers: List[Matcher] = scheme.way_matchers
|
||||||
if matcher.shapes and not matcher.location_restrictions:
|
|
||||||
self.matchers[matcher] = [
|
|
||||||
(x if isinstance(x, str) else x["shape"])
|
|
||||||
for x in matcher.shapes
|
|
||||||
]
|
|
||||||
|
|
||||||
def add_selector(
|
def add_selector(
|
||||||
self,
|
self,
|
||||||
|
@ -38,15 +33,40 @@ class MapCSSWriter:
|
||||||
prefix: str = "",
|
prefix: str = "",
|
||||||
opacity: Optional[float] = None,
|
opacity: Optional[float] = None,
|
||||||
) -> str:
|
) -> str:
|
||||||
selector = (
|
elements: Dict[str, str] = {}
|
||||||
target + matcher.get_mapcss_selector(prefix) + " {\n"
|
|
||||||
f' icon-image: "{self.icon_directory_name}/'
|
clean_shapes = matcher.get_clean_shapes()
|
||||||
+ "___".join(self.matchers[matcher])
|
if clean_shapes:
|
||||||
+ '.svg";\n'
|
elements["icon-image"] = (
|
||||||
|
f'"{self.icon_directory_name}/'
|
||||||
|
+ "___".join(clean_shapes) + '.svg"'
|
||||||
)
|
)
|
||||||
|
|
||||||
if opacity is not None:
|
if opacity is not None:
|
||||||
selector += f" icon-opacity: {opacity:.2f};\n"
|
elements["icon-opacity"] = f"{opacity:.2f}"
|
||||||
|
|
||||||
|
style = matcher.get_style()
|
||||||
|
if style:
|
||||||
|
if "fill" in style:
|
||||||
|
elements["fill-color"] = style["fill"]
|
||||||
|
if "stroke" in style:
|
||||||
|
elements["color"] = style["stroke"]
|
||||||
|
if "stroke-width" in style:
|
||||||
|
elements["width"] = style["stroke-width"]
|
||||||
|
if "stroke-dasharray" in style:
|
||||||
|
elements["dashes"] = style["stroke-dasharray"]
|
||||||
|
if "opacity" in style:
|
||||||
|
elements["fill-opacity"] = style["opacity"]
|
||||||
|
elements["opacity"] = style["opacity"]
|
||||||
|
|
||||||
|
if not elements:
|
||||||
|
return ""
|
||||||
|
|
||||||
|
selector: str = target + matcher.get_mapcss_selector(prefix) + " {\n"
|
||||||
|
for element in elements:
|
||||||
|
selector += f" {element}: {elements[element]};\n"
|
||||||
selector += "}\n"
|
selector += "}\n"
|
||||||
|
|
||||||
return selector
|
return selector
|
||||||
|
|
||||||
def write(self, output_file) -> None:
|
def write(self, output_file) -> None:
|
||||||
|
@ -58,7 +78,11 @@ class MapCSSWriter:
|
||||||
|
|
||||||
output_file.write("\n")
|
output_file.write("\n")
|
||||||
|
|
||||||
for matcher in self.matchers:
|
for line_matcher in self.line_matchers:
|
||||||
|
for target in ["way", "relation"]:
|
||||||
|
output_file.write(self.add_selector(target, line_matcher))
|
||||||
|
|
||||||
|
for matcher in self.point_matchers:
|
||||||
for target in ["node", "area"]:
|
for target in ["node", "area"]:
|
||||||
output_file.write(self.add_selector(target, matcher))
|
output_file.write(self.add_selector(target, matcher))
|
||||||
|
|
||||||
|
@ -67,7 +91,7 @@ class MapCSSWriter:
|
||||||
|
|
||||||
for index, stage_of_decay in enumerate(STAGES_OF_DECAY):
|
for index, stage_of_decay in enumerate(STAGES_OF_DECAY):
|
||||||
opacity: float = 0.6 - 0.4 * index / (len(STAGES_OF_DECAY) - 1)
|
opacity: float = 0.6 - 0.4 * index / (len(STAGES_OF_DECAY) - 1)
|
||||||
for matcher in self.matchers:
|
for matcher in self.point_matchers:
|
||||||
if len(matcher.tags) > 1:
|
if len(matcher.tags) > 1:
|
||||||
continue
|
continue
|
||||||
for target in ["node", "area"]:
|
for target in ["node", "area"]:
|
||||||
|
|
|
@ -51,9 +51,13 @@ class ArgumentParser(argparse.ArgumentParser):
|
||||||
|
|
||||||
if "help" in option:
|
if "help" in option:
|
||||||
help_value: List = [option["help"]]
|
help_value: List = [option["help"]]
|
||||||
if "default" in option and option["default"] and option["default"] != "==SUPPRESS==":
|
if (
|
||||||
|
"default" in option
|
||||||
|
and option["default"]
|
||||||
|
and option["default"] != "==SUPPRESS=="
|
||||||
|
):
|
||||||
help_value += [
|
help_value += [
|
||||||
f", default value: ", Tag("tt", [str(option['default'])])
|
", default value: ", Tag("tt", [str(option['default'])])
|
||||||
]
|
]
|
||||||
row.append(help_value)
|
row.append(help_value)
|
||||||
else:
|
else:
|
||||||
|
|
|
@ -137,7 +137,15 @@ class Matcher:
|
||||||
|
|
||||||
See https://wiki.openstreetmap.org/wiki/MapCSS/0.2
|
See https://wiki.openstreetmap.org/wiki/MapCSS/0.2
|
||||||
"""
|
"""
|
||||||
return "".join([get_selector(x, y, prefix) for (x, y) in self.tags.items()])
|
return "".join(
|
||||||
|
[get_selector(x, y, prefix) for (x, y) in self.tags.items()]
|
||||||
|
)
|
||||||
|
|
||||||
|
def get_clean_shapes(self):
|
||||||
|
return None
|
||||||
|
|
||||||
|
def get_style(self):
|
||||||
|
return None
|
||||||
|
|
||||||
|
|
||||||
class NodeMatcher(Matcher):
|
class NodeMatcher(Matcher):
|
||||||
|
@ -177,6 +185,11 @@ class NodeMatcher(Matcher):
|
||||||
if "with_icon" in structure:
|
if "with_icon" in structure:
|
||||||
self.with_icon = structure["with_icon"]
|
self.with_icon = structure["with_icon"]
|
||||||
|
|
||||||
|
def get_clean_shapes(self):
|
||||||
|
if not self.shapes:
|
||||||
|
return
|
||||||
|
return [(x if isinstance(x, str) else x["shape"]) for x in self.shapes]
|
||||||
|
|
||||||
|
|
||||||
class WayMatcher(Matcher):
|
class WayMatcher(Matcher):
|
||||||
"""
|
"""
|
||||||
|
@ -197,6 +210,9 @@ class WayMatcher(Matcher):
|
||||||
if "priority" in structure:
|
if "priority" in structure:
|
||||||
self.priority = structure["priority"]
|
self.priority = structure["priority"]
|
||||||
|
|
||||||
|
def get_style(self):
|
||||||
|
return self.style
|
||||||
|
|
||||||
|
|
||||||
class RoadMatcher(Matcher):
|
class RoadMatcher(Matcher):
|
||||||
"""
|
"""
|
||||||
|
@ -391,11 +407,11 @@ class Scheme:
|
||||||
if main_icon and color:
|
if main_icon and color:
|
||||||
main_icon.recolor(color)
|
main_icon.recolor(color)
|
||||||
|
|
||||||
keys_left = [
|
# keys_left = [
|
||||||
x
|
# x
|
||||||
for x in tags.keys()
|
# for x in tags.keys()
|
||||||
if x not in processed and not self.is_no_drawable(x)
|
# if x not in processed and not self.is_no_drawable(x)
|
||||||
]
|
# ]
|
||||||
|
|
||||||
default_shape = icon_extractor.get_shape(DEFAULT_SHAPE_ID)
|
default_shape = icon_extractor.get_shape(DEFAULT_SHAPE_ID)
|
||||||
if not main_icon:
|
if not main_icon:
|
||||||
|
|
|
@ -6,7 +6,7 @@ See https://wiki.openstreetmap.org/wiki/Taginfo/Projects
|
||||||
import json
|
import json
|
||||||
from datetime import datetime
|
from datetime import datetime
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from typing import Dict, List
|
from typing import List
|
||||||
|
|
||||||
import logging
|
import logging
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,6 @@ Tile generation.
|
||||||
|
|
||||||
See https://wiki.openstreetmap.org/wiki/Tiles
|
See https://wiki.openstreetmap.org/wiki/Tiles
|
||||||
"""
|
"""
|
||||||
import argparse
|
|
||||||
import sys
|
import sys
|
||||||
from dataclasses import dataclass
|
from dataclasses import dataclass
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
|
|
|
@ -13,5 +13,3 @@ SCHEME: Scheme = Scheme(Path("scheme/default.yml"))
|
||||||
SHAPE_EXTRACTOR: ShapeExtractor = ShapeExtractor(
|
SHAPE_EXTRACTOR: ShapeExtractor = ShapeExtractor(
|
||||||
Path("icons/icons.svg"), Path("icons/config.json")
|
Path("icons/icons.svg"), Path("icons/config.json")
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue