]> mj.ucw.cz Git - leo.git/blob - osm.h
osm.h: osm_ref_(head|tail)
[leo.git] / osm.h
1 /*
2  *      Hic Est Leo -- Representation of OSM Data
3  *
4  *      (c) 2014 Martin Mares <mj@ucw.cz>
5  */
6
7 #ifndef _LEO_OSM_H
8 #define _LEO_OSM_H
9
10 #include "dict.h"
11
12 typedef u64 osm_id_t;
13 #define OSM_INVALID_ID ~(osm_id_t)0
14
15 typedef u32 osm_key_t, osm_val_t;
16
17 struct osm_object {
18   cnode n;                      // In the per-type list
19   byte type;                    // OSM_TYPE_xxx
20   byte pad[3];
21   osm_id_t id;
22   clist tags;
23   clist backrefs;               // Objects pointing to this one
24 };
25
26 enum osm_object_type {
27   OSM_TYPE_INVALID,
28   OSM_TYPE_NODE,
29   OSM_TYPE_WAY,
30   OSM_TYPE_RELATION,
31   OSM_TYPE_MULTIPOLYGON,
32   // Remember to update osm_obj_type_names[], too
33   OSM_TYPE_MAX,
34 };
35
36 struct osm_tag {
37   cnode n;                      // In object->tags
38   osm_key_t key;
39   osm_val_t val;
40 };
41
42 struct osm_ref {
43   cnode n;
44   struct osm_object *o;
45   osm_val_t role;
46 };
47
48 struct osm_node {
49   struct osm_object o;
50   double x, y;
51   /*
52    * For WGS84 coordinates, x is longitude and y latitude.
53    * For UTM, x is easting and y northing.
54    * After map scaling, x is horizontal (left-to-right) and y vertical (top-to-bottom) on the paper.
55    */
56   struct graph_vertex *vertex;
57 };
58
59 struct osm_way {
60   struct osm_object o;
61   clist nodes;                  // List of osm_ref's
62 };
63
64 struct osm_relation {
65   struct osm_object o;
66   clist members;                // List of osm_ref's
67 };
68
69 struct osm_multipolygon {       // Virtual object constructed from multipolygon relations
70   struct osm_object o;
71   struct osm_relation *rel;     // Original relation
72   clist boundaries;             // List of osm_mpg_boundary's
73 };
74
75 struct osm_mpg_boundary {
76   cnode n;
77   bool inner;
78   clist nodes;                  // List of osm_ref's (without back-references, since the boundary is not a regular object)
79 };
80
81 struct osm {
82   struct mempool *pool;
83   clist obj_list[OSM_TYPE_MAX];
84   struct osm_id_hash_table *id_hash[OSM_TYPE_MAX];
85   uint obj_cnt[OSM_TYPE_MAX];
86 };
87
88 extern struct osm *osm_this;
89
90 struct osm *osm_init(void);
91 void osm_dump(void);
92 void osm_stats(void);
93
94 osm_id_t osm_parse_id(const char *str);
95 struct osm_object *osm_obj_find_by_id(enum osm_object_type type, osm_id_t id);
96 void osm_obj_add_tag(struct osm_object *o, const char *key, const char *val);
97 void osm_obj_add_tag_raw(struct osm_object *o, osm_key_t key, osm_val_t val);
98 void osm_obj_set_tag(struct osm_object *o, const char *key, const char *val);
99 void osm_obj_set_tag_raw(struct osm_object *o, osm_key_t key, osm_val_t val);
100 osm_val_t osm_obj_find_tag(struct osm_object *o, osm_val_t key);
101 void osm_obj_dump(struct osm_object *o);
102 void osm_obj_warn(struct osm_object *o, const char *msg, ...);
103 extern const char * const osm_obj_type_names[OSM_TYPE_MAX];
104 #define STK_OSM_NAME(o) stk_printf("%s:%ju", osm_obj_type_names[(o)->type], (uintmax_t) (o)->id)
105
106 void osm_ref_add(struct osm_object *parent, clist *list, struct osm_object *son, osm_val_t role);
107 #define OSM_FOR_EACH_BEGIN(_type, _var, _list) CLIST_FOR_EACH(struct osm_ref *, _ref, _list) { _type _var = (_type) _ref->o;
108 #define OSM_FOR_EACH_END }
109
110 static inline struct osm_object *osm_ref_head(clist *list)
111 {
112   struct osm_ref *r = clist_head(list);
113   return r ? r->o : NULL;
114 }
115
116 static inline struct osm_object *osm_ref_tail(clist *list)
117 {
118   struct osm_ref *r = clist_tail(list);
119   return r ? r->o : NULL;
120 }
121
122 struct osm_node *osm_node_new(osm_id_t id);
123 void osm_node_dump(struct osm_node *n);
124 void osm_node_dump_all(void);
125
126 struct osm_way *osm_way_new(osm_id_t id);
127 void osm_way_add_node(struct osm_way *w, struct osm_node *n);
128 void osm_way_dump(struct osm_way *w);
129 void osm_way_dump_all(void);
130 bool osm_way_cyclic_p(struct osm_way *w);
131
132 struct osm_relation *osm_relation_new(osm_id_t id);
133 void osm_relation_add_member(struct osm_relation *r, struct osm_object *o, const char *role);
134 void osm_relation_dump(struct osm_relation *w);
135 void osm_relation_dump_all(void);
136
137 void osm_multipolygon_dump(struct osm_multipolygon *w);
138 void osm_multipolygon_dump_all(void);
139 void osm_make_multipolygons(void);
140
141 void osm_project(const char *spec);
142
143 bool osm_obj_center(struct osm_object *o, double *xp, double *yp);
144
145 /* Tags */
146
147 extern struct dict osm_key_dict, osm_value_dict;
148
149 static inline osm_key_t osm_key_encode(const char *key)
150 {
151   return dict_encode(&osm_key_dict, key);
152 }
153
154 static inline const char *osm_key_decode(osm_key_t key)
155 {
156   return dict_decode(&osm_key_dict, key);
157 }
158
159 static inline osm_val_t osm_val_encode(const char *val)
160 {
161   return dict_encode(&osm_value_dict, val);
162 }
163
164 static inline const char *osm_val_decode(osm_val_t key)
165 {
166   return dict_decode(&osm_value_dict, key);
167 }
168
169 void osm_tag_dump(struct osm_tag *t);
170
171 /* Well-known tags and values */
172
173 enum tag_keys {
174     KEY_NULL,
175 #define P(x,y) KEY_##x,
176 #include "dict-keys.h"
177 #undef P
178 };
179
180 enum value_names {
181     VALUE_NULL,
182 #define P(x,y) VALUE_##x,
183 #include "dict-values.h"
184 #undef P
185 };
186
187 /* xml.c */
188
189 void osm_xml_parse(const char *name);
190
191 #endif