Routino SVN Repository Browser

Check out the latest version of Routino: svn co http://routino.org/svn/trunk routino

ViewVC logotype

Contents of /trunk/src/visualiser.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1573 - (show annotations) (download) (as text)
Tue May 20 17:31:20 2014 UTC (10 years, 9 months ago) by amb
File MIME type: text/x-csrc
File size: 31638 byte(s)
When visualising segments include all of the ones that overlap the selected
region (not missing a few that cross the edges).

1 /***************************************
2 Extract data from Routino.
3
4 Part of the Routino routing software.
5 ******************/ /******************
6 This file Copyright 2008-2014 Andrew M. Bishop
7
8 This program is free software: you can redistribute it and/or modify
9 it under the terms of the GNU Affero General Public License as published by
10 the Free Software Foundation, either version 3 of the License, or
11 (at your option) any later version.
12
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU Affero General Public License for more details.
17
18 You should have received a copy of the GNU Affero General Public License
19 along with this program. If not, see <http://www.gnu.org/licenses/>.
20 ***************************************/
21
22
23 #include <stdio.h>
24 #include <stdlib.h>
25 #include <string.h>
26
27 #include "types.h"
28 #include "nodes.h"
29 #include "segments.h"
30 #include "ways.h"
31 #include "relations.h"
32 #include "errorlog.h"
33
34 #include "visualiser.h"
35
36
37 /*+ The maximum number of segments per node (used to size temporary storage). +*/
38 #define MAX_SEG_PER_NODE 32
39
40 /* Limit types */
41
42 #define SPEED_LIMIT 1
43 #define WEIGHT_LIMIT 2
44 #define HEIGHT_LIMIT 3
45 #define WIDTH_LIMIT 4
46 #define LENGTH_LIMIT 5
47
48 /* Local types */
49
50 typedef void (*callback_t)(index_t node,double latitude,double longitude);
51
52 /* Local variables */
53
54 static Nodes *OSMNodes;
55 static Segments *OSMSegments;
56 static Ways *OSMWays;
57 static Relations *OSMRelations;
58
59 static double LatMin;
60 static double LatMax;
61 static double LonMin;
62 static double LonMax;
63
64 static int limit_type=0;
65 static Highway highways=Highway_None;
66 static Transports transports=Transports_None;
67 static Properties properties=Properties_None;
68 static highway_t waytype=0;
69
70 /* Local functions */
71
72 static void find_all_nodes(Nodes *nodes,callback_t callback);
73
74 static void output_junctions(index_t node,double latitude,double longitude);
75 static void output_super(index_t node,double latitude,double longitude);
76 static void output_waytype(index_t node,double latitude,double longitude);
77 static void output_highway(index_t node,double latitude,double longitude);
78 static void output_transport(index_t node,double latitude,double longitude);
79 static void output_barrier(index_t node,double latitude,double longitude);
80 static void output_turnrestriction(index_t node,double latitude,double longitude);
81 static void output_limits(index_t node,double latitude,double longitude);
82 static void output_property(index_t node,double latitude,double longitude);
83
84
85 /*++++++++++++++++++++++++++++++++++++++
86 Output the data for junctions.
87
88 Nodes *nodes The set of nodes to use.
89
90 Segments *segments The set of segments to use.
91
92 Ways *ways The set of ways to use.
93
94 Relations *relations The set of relations to use.
95
96 double latmin The minimum latitude.
97
98 double latmax The maximum latitude.
99
100 double lonmin The minimum longitude.
101
102 double lonmax The maximum longitude.
103 ++++++++++++++++++++++++++++++++++++++*/
104
105 void OutputJunctions(Nodes *nodes,Segments *segments,Ways *ways,Relations *relations,double latmin,double latmax,double lonmin,double lonmax)
106 {
107 /* Use local variables so that the callback doesn't need to pass them backwards and forwards */
108
109 OSMNodes=nodes;
110 OSMSegments=segments;
111 OSMWays=ways;
112 OSMRelations=relations;
113
114 LatMin=latmin;
115 LatMax=latmax;
116 LonMin=lonmin;
117 LonMax=lonmax;
118
119 /* Iterate through the nodes and process them */
120
121 find_all_nodes(nodes,(callback_t)output_junctions);
122 }
123
124
125 /*++++++++++++++++++++++++++++++++++++++
126 Process a single node as a junction (called as a callback).
127
128 index_t node The node to output.
129
130 double latitude The latitude of the node.
131
132 double longitude The longitude of the node.
133 ++++++++++++++++++++++++++++++++++++++*/
134
135 static void output_junctions(index_t node,double latitude,double longitude)
136 {
137 Node *nodep=LookupNode(OSMNodes,node,1);
138 Segment *segmentp;
139 Way *firstwayp;
140 int count=0,difference=0;
141
142 segmentp=FirstSegment(OSMSegments,nodep,1);
143 firstwayp=LookupWay(OSMWays,segmentp->way,1);
144
145 do
146 {
147 Way *wayp=LookupWay(OSMWays,segmentp->way,2);
148
149 if(IsNormalSegment(segmentp))
150 count++;
151
152 if(WaysCompare(firstwayp,wayp))
153 difference=1;
154
155 segmentp=NextSegment(OSMSegments,segmentp,node);
156 }
157 while(segmentp);
158
159 if(count!=2 || difference)
160 printf("node%"Pindex_t" %.6f %.6f %d\n",node,radians_to_degrees(latitude),radians_to_degrees(longitude),count);
161 }
162
163
164 /*++++++++++++++++++++++++++++++++++++++
165 Output the data for super-nodes and super-segments.
166
167 Nodes *nodes The set of nodes to use.
168
169 Segments *segments The set of segments to use.
170
171 Ways *ways The set of ways to use.
172
173 Relations *relations The set of relations to use.
174
175 double latmin The minimum latitude.
176
177 double latmax The maximum latitude.
178
179 double lonmin The minimum longitude.
180
181 double lonmax The maximum longitude.
182 ++++++++++++++++++++++++++++++++++++++*/
183
184 void OutputSuper(Nodes *nodes,Segments *segments,Ways *ways,Relations *relations,double latmin,double latmax,double lonmin,double lonmax)
185 {
186 /* Use local variables so that the callback doesn't need to pass them backwards and forwards */
187
188 OSMNodes=nodes;
189 OSMSegments=segments;
190 OSMWays=ways;
191 OSMRelations=relations;
192
193 LatMin=latmin;
194 LatMax=latmax;
195 LonMin=lonmin;
196 LonMax=lonmax;
197
198 /* Iterate through the nodes and process them */
199
200 find_all_nodes(nodes,(callback_t)output_super);
201 }
202
203
204 /*++++++++++++++++++++++++++++++++++++++
205 Process a single node as a super-node (called as a callback).
206
207 index_t node The node to output.
208
209 double latitude The latitude of the node.
210
211 double longitude The longitude of the node.
212 ++++++++++++++++++++++++++++++++++++++*/
213
214 static void output_super(index_t node,double latitude,double longitude)
215 {
216 Node *nodep=LookupNode(OSMNodes,node,1);
217 Segment *segmentp;
218
219 if(!IsSuperNode(nodep))
220 return;
221
222 printf("node%"Pindex_t" %.6f %.6f\n",node,radians_to_degrees(latitude),radians_to_degrees(longitude));
223
224 segmentp=FirstSegment(OSMSegments,nodep,1);
225
226 do
227 {
228 if(IsSuperSegment(segmentp))
229 {
230 index_t othernode=OtherNode(segmentp,node);
231 double lat,lon;
232
233 GetLatLong(OSMNodes,othernode,NULL,&lat,&lon);
234
235 if(node>othernode || (lat<LatMin || lat>LatMax || lon<LonMin || lon>LonMax))
236 printf("segment%"Pindex_t" %.6f %.6f\n",IndexSegment(OSMSegments,segmentp),radians_to_degrees(lat),radians_to_degrees(lon));
237 }
238
239 segmentp=NextSegment(OSMSegments,segmentp,node);
240 }
241 while(segmentp);
242 }
243
244
245 /*++++++++++++++++++++++++++++++++++++++
246 Output the data for one-way segments.
247
248 Nodes *nodes The set of nodes to use.
249
250 Segments *segments The set of segments to use.
251
252 Ways *ways The set of ways to use.
253
254 Relations *relations The set of relations to use.
255
256 double latmin The minimum latitude.
257
258 double latmax The maximum latitude.
259
260 double lonmin The minimum longitude.
261
262 double lonmax The maximum longitude.
263
264 highway_t mask A bit mask that must match the highway type.
265 ++++++++++++++++++++++++++++++++++++++*/
266
267 void OutputWaytype(Nodes *nodes,Segments *segments,Ways *ways,Relations *relations,double latmin,double latmax,double lonmin,double lonmax,highway_t mask)
268 {
269 /* Use local variables so that the callback doesn't need to pass them backwards and forwards */
270
271 OSMNodes=nodes;
272 OSMSegments=segments;
273 OSMWays=ways;
274 OSMRelations=relations;
275
276 LatMin=latmin;
277 LatMax=latmax;
278 LonMin=lonmin;
279 LonMax=lonmax;
280
281 /* Iterate through the nodes and process them */
282
283 waytype=mask;
284
285 find_all_nodes(nodes,(callback_t)output_waytype);
286 }
287
288
289 /*++++++++++++++++++++++++++++++++++++++
290 Process a single node and all connected way-type segments (called as a callback).
291
292 index_t node The node to output.
293
294 double latitude The latitude of the node.
295
296 double longitude The longitude of the node.
297 ++++++++++++++++++++++++++++++++++++++*/
298
299 static void output_waytype(index_t node,double latitude,double longitude)
300 {
301 Node *nodep=LookupNode(OSMNodes,node,1);
302 Segment *segmentp;
303
304 segmentp=FirstSegment(OSMSegments,nodep,1);
305
306 do
307 {
308 if(IsNormalSegment(segmentp))
309 {
310 Way *wayp=LookupWay(OSMWays,segmentp->way,1);
311
312 if(wayp->type&waytype)
313 {
314 index_t othernode=OtherNode(segmentp,node);
315 double lat,lon;
316
317 GetLatLong(OSMNodes,othernode,NULL,&lat,&lon);
318
319 if(node>othernode || (lat<LatMin || lat>LatMax || lon<LonMin || lon>LonMax))
320 {
321 if(IsOnewayFrom(segmentp,node))
322 printf("segment%"Pindex_t" %.6f %.6f %.6f %.6f\n",IndexSegment(OSMSegments,segmentp),radians_to_degrees(latitude),radians_to_degrees(longitude),radians_to_degrees(lat),radians_to_degrees(lon));
323 else if(IsOnewayFrom(segmentp,othernode))
324 printf("segment%"Pindex_t" %.6f %.6f %.6f %.6f\n",IndexSegment(OSMSegments,segmentp),radians_to_degrees(lat),radians_to_degrees(lon),radians_to_degrees(latitude),radians_to_degrees(longitude));
325 }
326 }
327 }
328
329 segmentp=NextSegment(OSMSegments,segmentp,node);
330 }
331 while(segmentp);
332 }
333
334
335 /*++++++++++++++++++++++++++++++++++++++
336 Output the data for segments of a particular highway type.
337
338 Nodes *nodes The set of nodes to use.
339
340 Segments *segments The set of segments to use.
341
342 Ways *ways The set of ways to use.
343
344 Relations *relations The set of relations to use.
345
346 double latmin The minimum latitude.
347
348 double latmax The maximum latitude.
349
350 double lonmin The minimum longitude.
351
352 double lonmax The maximum longitude.
353
354 Highway highway The type of highway.
355 ++++++++++++++++++++++++++++++++++++++*/
356
357 void OutputHighway(Nodes *nodes,Segments *segments,Ways *ways,Relations *relations,double latmin,double latmax,double lonmin,double lonmax,Highway highway)
358 {
359 /* Use local variables so that the callback doesn't need to pass them backwards and forwards */
360
361 OSMNodes=nodes;
362 OSMSegments=segments;
363 OSMWays=ways;
364 OSMRelations=relations;
365
366 LatMin=latmin;
367 LatMax=latmax;
368 LonMin=lonmin;
369 LonMax=lonmax;
370
371 /* Iterate through the nodes and process them */
372
373 highways=highway;
374
375 find_all_nodes(nodes,(callback_t)output_highway);
376 }
377
378
379 /*++++++++++++++++++++++++++++++++++++++
380 Process a single node and all connected one-way segments (called as a callback).
381
382 index_t node The node to output.
383
384 double latitude The latitude of the node.
385
386 double longitude The longitude of the node.
387 ++++++++++++++++++++++++++++++++++++++*/
388
389 static void output_highway(index_t node,double latitude,double longitude)
390 {
391 Node *nodep=LookupNode(OSMNodes,node,1);
392 Segment *segmentp;
393
394 segmentp=FirstSegment(OSMSegments,nodep,1);
395
396 do
397 {
398 if(IsNormalSegment(segmentp))
399 {
400 Way *wayp=LookupWay(OSMWays,segmentp->way,1);
401
402 if(HIGHWAY(wayp->type)==highways)
403 {
404 index_t othernode=OtherNode(segmentp,node);
405 double lat,lon;
406
407 GetLatLong(OSMNodes,othernode,NULL,&lat,&lon);
408
409 if(node>othernode || (lat<LatMin || lat>LatMax || lon<LonMin || lon>LonMax))
410 printf("segment%"Pindex_t" %.6f %.6f %.6f %.6f\n",IndexSegment(OSMSegments,segmentp),radians_to_degrees(latitude),radians_to_degrees(longitude),radians_to_degrees(lat),radians_to_degrees(lon));
411 }
412 }
413
414 segmentp=NextSegment(OSMSegments,segmentp,node);
415 }
416 while(segmentp);
417 }
418
419
420 /*++++++++++++++++++++++++++++++++++++++
421 Output the data for segments allowed for a particular type of traffic.
422
423 Nodes *nodes The set of nodes to use.
424
425 Segments *segments The set of segments to use.
426
427 Ways *ways The set of ways to use.
428
429 Relations *relations The set of relations to use.
430
431 double latmin The minimum latitude.
432
433 double latmax The maximum latitude.
434
435 double lonmin The minimum longitude.
436
437 double lonmax The maximum longitude.
438
439 Transport transport The type of transport.
440 ++++++++++++++++++++++++++++++++++++++*/
441
442 void OutputTransport(Nodes *nodes,Segments *segments,Ways *ways,Relations *relations,double latmin,double latmax,double lonmin,double lonmax,Transport transport)
443 {
444 /* Use local variables so that the callback doesn't need to pass them backwards and forwards */
445
446 OSMNodes=nodes;
447 OSMSegments=segments;
448 OSMWays=ways;
449 OSMRelations=relations;
450
451 LatMin=latmin;
452 LatMax=latmax;
453 LonMin=lonmin;
454 LonMax=lonmax;
455
456 /* Iterate through the nodes and process them */
457
458 transports=TRANSPORTS(transport);
459
460 find_all_nodes(nodes,(callback_t)output_transport);
461 }
462
463
464 /*++++++++++++++++++++++++++++++++++++++
465 Process a single node and all connected one-way segments (called as a callback).
466
467 index_t node The node to output.
468
469 double latitude The latitude of the node.
470
471 double longitude The longitude of the node.
472 ++++++++++++++++++++++++++++++++++++++*/
473
474 static void output_transport(index_t node,double latitude,double longitude)
475 {
476 Node *nodep=LookupNode(OSMNodes,node,1);
477 Segment *segmentp;
478
479 segmentp=FirstSegment(OSMSegments,nodep,1);
480
481 do
482 {
483 if(IsNormalSegment(segmentp))
484 {
485 Way *wayp=LookupWay(OSMWays,segmentp->way,1);
486
487 if(wayp->allow&transports)
488 {
489 index_t othernode=OtherNode(segmentp,node);
490 double lat,lon;
491
492 GetLatLong(OSMNodes,othernode,NULL,&lat,&lon);
493
494 if(node>othernode || (lat<LatMin || lat>LatMax || lon<LonMin || lon>LonMax))
495 printf("segment%"Pindex_t" %.6f %.6f %.6f %.6f\n",IndexSegment(OSMSegments,segmentp),radians_to_degrees(latitude),radians_to_degrees(longitude),radians_to_degrees(lat),radians_to_degrees(lon));
496 }
497 }
498
499 segmentp=NextSegment(OSMSegments,segmentp,node);
500 }
501 while(segmentp);
502 }
503
504
505 /*++++++++++++++++++++++++++++++++++++++
506 Output the data for nodes disallowed for a particular type of traffic.
507
508 Nodes *nodes The set of nodes to use.
509
510 Segments *segments The set of segments to use.
511
512 Ways *ways The set of ways to use.
513
514 Relations *relations The set of relations to use.
515
516 double latmin The minimum latitude.
517
518 double latmax The maximum latitude.
519
520 double lonmin The minimum longitude.
521
522 double lonmax The maximum longitude.
523
524 Transport transport The type of transport.
525 ++++++++++++++++++++++++++++++++++++++*/
526
527 void OutputBarrier(Nodes *nodes,Segments *segments,Ways *ways,Relations *relations,double latmin,double latmax,double lonmin,double lonmax,Transport transport)
528 {
529 /* Use local variables so that the callback doesn't need to pass them backwards and forwards */
530
531 OSMNodes=nodes;
532 OSMSegments=segments;
533 OSMWays=ways;
534 OSMRelations=relations;
535
536 LatMin=latmin;
537 LatMax=latmax;
538 LonMin=lonmin;
539 LonMax=lonmax;
540
541 /* Iterate through the nodes and process them */
542
543 transports=TRANSPORTS(transport);
544
545 find_all_nodes(nodes,(callback_t)output_barrier);
546 }
547
548
549 /*++++++++++++++++++++++++++++++++++++++
550 Process a single node (called as a callback).
551
552 index_t node The node to output.
553
554 double latitude The latitude of the node.
555
556 double longitude The longitude of the node.
557 ++++++++++++++++++++++++++++++++++++++*/
558
559 static void output_barrier(index_t node,double latitude,double longitude)
560 {
561 Node *nodep=LookupNode(OSMNodes,node,1);
562
563 if(!(nodep->allow&transports))
564 printf("node%"Pindex_t" %.6f %.6f\n",node,radians_to_degrees(latitude),radians_to_degrees(longitude));
565 }
566
567
568 /*++++++++++++++++++++++++++++++++++++++
569 Output the data for turn restrictions.
570
571 Nodes *nodes The set of nodes to use.
572
573 Segments *segments The set of segments to use.
574
575 Ways *ways The set of ways to use.
576
577 Relations *relations The set of relations to use.
578
579 double latmin The minimum latitude.
580
581 double latmax The maximum latitude.
582
583 double lonmin The minimum longitude.
584
585 double lonmax The maximum longitude.
586 ++++++++++++++++++++++++++++++++++++++*/
587
588 void OutputTurnRestrictions(Nodes *nodes,Segments *segments,Ways *ways,Relations *relations,double latmin,double latmax,double lonmin,double lonmax)
589 {
590 /* Use local variables so that the callback doesn't need to pass them backwards and forwards */
591
592 OSMNodes=nodes;
593 OSMSegments=segments;
594 OSMWays=ways;
595 OSMRelations=relations;
596
597 LatMin=latmin;
598 LatMax=latmax;
599 LonMin=lonmin;
600 LonMax=lonmax;
601
602 /* Iterate through the nodes and process them */
603
604 find_all_nodes(nodes,(callback_t)output_turnrestriction);
605 }
606
607
608 /*++++++++++++++++++++++++++++++++++++++
609 Process a single node as the 'via' node for a turn restriction (called as a callback).
610
611 index_t node The node to output.
612
613 double latitude The latitude of the node.
614
615 double longitude The longitude of the node.
616 ++++++++++++++++++++++++++++++++++++++*/
617
618 static void output_turnrestriction(index_t node,double latitude,double longitude)
619 {
620 Node *nodep=LookupNode(OSMNodes,node,1);
621 index_t turnrelation=NO_RELATION;
622
623 if(!IsTurnRestrictedNode(nodep))
624 return;
625
626 turnrelation=FindFirstTurnRelation1(OSMRelations,node);
627
628 do
629 {
630 TurnRelation *relation;
631 Segment *from_segmentp,*to_segmentp;
632 index_t from_node,to_node;
633 double from_lat,from_lon,to_lat,to_lon;
634
635 relation=LookupTurnRelation(OSMRelations,turnrelation,1);
636
637 from_segmentp=LookupSegment(OSMSegments,relation->from,1);
638 to_segmentp =LookupSegment(OSMSegments,relation->to ,2);
639
640 from_node=OtherNode(from_segmentp,node);
641 to_node =OtherNode(to_segmentp ,node);
642
643 GetLatLong(OSMNodes,from_node,NULL,&from_lat,&from_lon);
644 GetLatLong(OSMNodes,to_node ,NULL,&to_lat ,&to_lon);
645
646 printf("turn-relation%"Pindex_t" %.6f %.6f %.6f %.6f %.6f %.6f\n",
647 turnrelation,
648 radians_to_degrees(from_lat),radians_to_degrees(from_lon),
649 radians_to_degrees(latitude),radians_to_degrees(longitude),
650 radians_to_degrees(to_lat),radians_to_degrees(to_lon));
651
652 turnrelation=FindNextTurnRelation1(OSMRelations,turnrelation);
653 }
654 while(turnrelation!=NO_RELATION);
655 }
656
657
658 /*++++++++++++++++++++++++++++++++++++++
659 Output the data for speed limits.
660
661 Nodes *nodes The set of nodes to use.
662
663 Segments *segments The set of segments to use.
664
665 Ways *ways The set of ways to use.
666
667 Relations *relations The set of relations to use.
668
669 double latmin The minimum latitude.
670
671 double latmax The maximum latitude.
672
673 double lonmin The minimum longitude.
674
675 double lonmax The maximum longitude.
676 ++++++++++++++++++++++++++++++++++++++*/
677
678 void OutputSpeedLimits(Nodes *nodes,Segments *segments,Ways *ways,Relations *relations,double latmin,double latmax,double lonmin,double lonmax)
679 {
680 /* Use local variables so that the callback doesn't need to pass them backwards and forwards */
681
682 OSMNodes=nodes;
683 OSMSegments=segments;
684 OSMWays=ways;
685 OSMRelations=relations;
686
687 LatMin=latmin;
688 LatMax=latmax;
689 LonMin=lonmin;
690 LonMax=lonmax;
691
692 /* Iterate through the nodes and process them */
693
694 limit_type=SPEED_LIMIT;
695
696 find_all_nodes(nodes,(callback_t)output_limits);
697 }
698
699
700 /*++++++++++++++++++++++++++++++++++++++
701 Output the data for weight limits.
702
703 Nodes *nodes The set of nodes to use.
704
705 Segments *segments The set of segments to use.
706
707 Ways *ways The set of ways to use.
708
709 Relations *relations The set of relations to use.
710
711 double latmin The minimum latitude.
712
713 double latmax The maximum latitude.
714
715 double lonmin The minimum longitude.
716
717 double lonmax The maximum longitude.
718 ++++++++++++++++++++++++++++++++++++++*/
719
720 void OutputWeightLimits(Nodes *nodes,Segments *segments,Ways *ways,Relations *relations,double latmin,double latmax,double lonmin,double lonmax)
721 {
722 /* Use local variables so that the callback doesn't need to pass them backwards and forwards */
723
724 OSMNodes=nodes;
725 OSMSegments=segments;
726 OSMWays=ways;
727 OSMRelations=relations;
728
729 LatMin=latmin;
730 LatMax=latmax;
731 LonMin=lonmin;
732 LonMax=lonmax;
733
734 /* Iterate through the nodes and process them */
735
736 limit_type=WEIGHT_LIMIT;
737
738 find_all_nodes(nodes,(callback_t)output_limits);
739 }
740
741
742 /*++++++++++++++++++++++++++++++++++++++
743 Output the data for height limits.
744
745 Nodes *nodes The set of nodes to use.
746
747 Segments *segments The set of segments to use.
748
749 Ways *ways The set of ways to use.
750
751 Relations *relations The set of relations to use.
752
753 double latmin The minimum latitude.
754
755 double latmax The maximum latitude.
756
757 double lonmin The minimum longitude.
758
759 double lonmax The maximum longitude.
760 ++++++++++++++++++++++++++++++++++++++*/
761
762 void OutputHeightLimits(Nodes *nodes,Segments *segments,Ways *ways,Relations *relations,double latmin,double latmax,double lonmin,double lonmax)
763 {
764 /* Use local variables so that the callback doesn't need to pass them backwards and forwards */
765
766 OSMNodes=nodes;
767 OSMSegments=segments;
768 OSMWays=ways;
769 OSMRelations=relations;
770
771 LatMin=latmin;
772 LatMax=latmax;
773 LonMin=lonmin;
774 LonMax=lonmax;
775
776 /* Iterate through the nodes and process them */
777
778 limit_type=HEIGHT_LIMIT;
779
780 find_all_nodes(nodes,(callback_t)output_limits);
781 }
782
783
784 /*++++++++++++++++++++++++++++++++++++++
785 Output the data for width limits.
786
787 Nodes *nodes The set of nodes to use.
788
789 Segments *segments The set of segments to use.
790
791 Ways *ways The set of ways to use.
792
793 Relations *relations The set of relations to use.
794
795 double latmin The minimum latitude.
796
797 double latmax The maximum latitude.
798
799 double lonmin The minimum longitude.
800
801 double lonmax The maximum longitude.
802 ++++++++++++++++++++++++++++++++++++++*/
803
804 void OutputWidthLimits(Nodes *nodes,Segments *segments,Ways *ways,Relations *relations,double latmin,double latmax,double lonmin,double lonmax)
805 {
806 /* Use local variables so that the callback doesn't need to pass them backwards and forwards */
807
808 OSMNodes=nodes;
809 OSMSegments=segments;
810 OSMWays=ways;
811 OSMRelations=relations;
812
813 LatMin=latmin;
814 LatMax=latmax;
815 LonMin=lonmin;
816 LonMax=lonmax;
817
818 /* Iterate through the nodes and process them */
819
820 limit_type=WIDTH_LIMIT;
821
822 find_all_nodes(nodes,(callback_t)output_limits);
823 }
824
825
826 /*++++++++++++++++++++++++++++++++++++++
827 Output the data for length limits.
828
829 Nodes *nodes The set of nodes to use.
830
831 Segments *segments The set of segments to use.
832
833 Ways *ways The set of ways to use.
834
835 Relations *relations The set of relations to use.
836
837 double latmin The minimum latitude.
838
839 double latmax The maximum latitude.
840
841 double lonmin The minimum longitude.
842
843 double lonmax The maximum longitude.
844 ++++++++++++++++++++++++++++++++++++++*/
845
846 void OutputLengthLimits(Nodes *nodes,Segments *segments,Ways *ways,Relations *relations,double latmin,double latmax,double lonmin,double lonmax)
847 {
848 /* Use local variables so that the callback doesn't need to pass them backwards and forwards */
849
850 OSMNodes=nodes;
851 OSMSegments=segments;
852 OSMWays=ways;
853 OSMRelations=relations;
854
855 LatMin=latmin;
856 LatMax=latmax;
857 LonMin=lonmin;
858 LonMax=lonmax;
859
860 /* Iterate through the nodes and process them */
861
862 limit_type=LENGTH_LIMIT;
863
864 find_all_nodes(nodes,(callback_t)output_limits);
865 }
866
867
868 /*++++++++++++++++++++++++++++++++++++++
869 Process a single node as a speed, weight, height, length, width limit (called as a callback).
870
871 index_t node The node to output.
872
873 double latitude The latitude of the node.
874
875 double longitude The longitude of the node.
876 ++++++++++++++++++++++++++++++++++++++*/
877
878 static void output_limits(index_t node,double latitude,double longitude)
879 {
880 Node *nodep=LookupNode(OSMNodes,node,1);
881 Segment *segmentp,segmentps[MAX_SEG_PER_NODE];
882 index_t segments[MAX_SEG_PER_NODE];
883 int limits[MAX_SEG_PER_NODE];
884 int count=0;
885 int i,j,same=0;
886
887 segmentp=FirstSegment(OSMSegments,nodep,1);
888
889 do
890 {
891 if(IsNormalSegment(segmentp) && count<MAX_SEG_PER_NODE)
892 {
893 Way *wayp=LookupWay(OSMWays,segmentp->way,1);
894
895 segmentps[count]=*segmentp;
896 segments [count]=IndexSegment(OSMSegments,segmentp);
897
898 switch(limit_type)
899 {
900 case SPEED_LIMIT: limits[count]=wayp->speed; break;
901 case WEIGHT_LIMIT: limits[count]=wayp->weight; break;
902 case HEIGHT_LIMIT: limits[count]=wayp->height; break;
903 case WIDTH_LIMIT: limits[count]=wayp->width; break;
904 case LENGTH_LIMIT: limits[count]=wayp->length; break;
905 }
906
907 if(limits[count] || HIGHWAY(wayp->type)<Highway_Track)
908 count++;
909 }
910
911 segmentp=NextSegment(OSMSegments,segmentp,node);
912 }
913 while(segmentp);
914
915 /* Nodes with only one limit are not interesting */
916
917 if(count==1)
918 return;
919
920 /* Nodes with all segments the same limit are not interesting */
921
922 same=0;
923 for(j=0;j<count;j++)
924 if(limits[0]==limits[j])
925 same++;
926
927 if(same==count)
928 return;
929
930 /* Display the interesting limits */
931
932 printf("node%"Pindex_t" %.6f %.6f\n",node,radians_to_degrees(latitude),radians_to_degrees(longitude));
933
934 for(i=0;i<count;i++)
935 {
936 same=0;
937 for(j=0;j<count;j++)
938 if(limits[i]==limits[j])
939 same++;
940
941 if(count==2 || same!=(count-1))
942 {
943 double lat,lon;
944
945 GetLatLong(OSMNodes,OtherNode(&segmentps[i],node),NULL,&lat,&lon);
946
947 switch(limit_type)
948 {
949 case SPEED_LIMIT:
950 printf("segment%"Pindex_t" %.6f %.6f %d\n",segments[i],radians_to_degrees(lat),radians_to_degrees(lon),speed_to_kph(limits[i]));
951 break;
952 case WEIGHT_LIMIT:
953 printf("segment%"Pindex_t" %.6f %.6f %.1f\n",segments[i],radians_to_degrees(lat),radians_to_degrees(lon),weight_to_tonnes(limits[i]));
954 break;
955 case HEIGHT_LIMIT:
956 printf("segment%"Pindex_t" %.6f %.6f %.1f\n",segments[i],radians_to_degrees(lat),radians_to_degrees(lon),height_to_metres(limits[i]));
957 break;
958 case WIDTH_LIMIT:
959 printf("segment%"Pindex_t" %.6f %.6f %.1f\n",segments[i],radians_to_degrees(lat),radians_to_degrees(lon),width_to_metres(limits[i]));
960 break;
961 case LENGTH_LIMIT:
962 printf("segment%"Pindex_t" %.6f %.6f %.1f\n",segments[i],radians_to_degrees(lat),radians_to_degrees(lon),length_to_metres(limits[i]));
963 break;
964 }
965 }
966 }
967 }
968
969
970 /*++++++++++++++++++++++++++++++++++++++
971 Output the data for segments that have a particular property.
972
973 Nodes *nodes The set of nodes to use.
974
975 Segments *segments The set of segments to use.
976
977 Ways *ways The set of ways to use.
978
979 Relations *relations The set of relations to use.
980
981 double latmin The minimum latitude.
982
983 double latmax The maximum latitude.
984
985 double lonmin The minimum longitude.
986
987 double lonmax The maximum longitude.
988
989 Property property The type of property.
990 ++++++++++++++++++++++++++++++++++++++*/
991
992 void OutputProperty(Nodes *nodes,Segments *segments,Ways *ways,Relations *relations,double latmin,double latmax,double lonmin,double lonmax,Property property)
993 {
994 /* Use local variables so that the callback doesn't need to pass them backwards and forwards */
995
996 OSMNodes=nodes;
997 OSMSegments=segments;
998 OSMWays=ways;
999 OSMRelations=relations;
1000
1001 LatMin=latmin;
1002 LatMax=latmax;
1003 LonMin=lonmin;
1004 LonMax=lonmax;
1005
1006 /* Iterate through the nodes and process them */
1007
1008 properties=PROPERTIES(property);
1009
1010 find_all_nodes(nodes,(callback_t)output_property);
1011 }
1012
1013
1014 /*++++++++++++++++++++++++++++++++++++++
1015 Process a single node and all connected one-way segments (called as a callback).
1016
1017 index_t node The node to output.
1018
1019 double latitude The latitude of the node.
1020
1021 double longitude The longitude of the node.
1022 ++++++++++++++++++++++++++++++++++++++*/
1023
1024 static void output_property(index_t node,double latitude,double longitude)
1025 {
1026 Node *nodep=LookupNode(OSMNodes,node,1);
1027 Segment *segmentp;
1028
1029 segmentp=FirstSegment(OSMSegments,nodep,1);
1030
1031 do
1032 {
1033 if(IsNormalSegment(segmentp))
1034 {
1035 Way *wayp=LookupWay(OSMWays,segmentp->way,1);
1036
1037 if(wayp->props&properties)
1038 {
1039 index_t othernode=OtherNode(segmentp,node);
1040 double lat,lon;
1041
1042 GetLatLong(OSMNodes,othernode,NULL,&lat,&lon);
1043
1044 if(node>othernode || (lat<LatMin || lat>LatMax || lon<LonMin || lon>LonMax))
1045 printf("segment%"Pindex_t" %.6f %.6f %.6f %.6f\n",IndexSegment(OSMSegments,segmentp),radians_to_degrees(latitude),radians_to_degrees(longitude),radians_to_degrees(lat),radians_to_degrees(lon));
1046 }
1047 }
1048
1049 segmentp=NextSegment(OSMSegments,segmentp,node);
1050 }
1051 while(segmentp);
1052 }
1053
1054
1055 /*++++++++++++++++++++++++++++++++++++++
1056 A function to iterate through all nodes and call a callback function for each one.
1057
1058 Nodes *nodes The set of nodes to use.
1059
1060 callback_t callback The callback function for each node.
1061 ++++++++++++++++++++++++++++++++++++++*/
1062
1063 static void find_all_nodes(Nodes *nodes,callback_t callback)
1064 {
1065 ll_bin_t latminbin=latlong_to_bin(radians_to_latlong(LatMin))-nodes->file.latzero;
1066 ll_bin_t latmaxbin=latlong_to_bin(radians_to_latlong(LatMax))-nodes->file.latzero;
1067 ll_bin_t lonminbin=latlong_to_bin(radians_to_latlong(LonMin))-nodes->file.lonzero;
1068 ll_bin_t lonmaxbin=latlong_to_bin(radians_to_latlong(LonMax))-nodes->file.lonzero;
1069 ll_bin_t latb,lonb;
1070 index_t i,index1,index2;
1071
1072 /* Loop through all of the nodes. */
1073
1074 if(latminbin<0) latminbin=0;
1075 if(latmaxbin>nodes->file.latbins) latmaxbin=nodes->file.latbins-1;
1076
1077 if(lonminbin<0) lonminbin=0;
1078 if(lonmaxbin>nodes->file.lonbins) lonmaxbin=nodes->file.lonbins-1;
1079
1080 for(latb=latminbin;latb<=latmaxbin;latb++)
1081 for(lonb=lonminbin;lonb<=lonmaxbin;lonb++)
1082 {
1083 ll_bin2_t llbin=lonb*nodes->file.latbins+latb;
1084
1085 if(llbin<0 || llbin>(nodes->file.latbins*nodes->file.lonbins))
1086 continue;
1087
1088 index1=LookupNodeOffset(nodes,llbin);
1089 index2=LookupNodeOffset(nodes,llbin+1);
1090
1091 for(i=index1;i<index2;i++)
1092 {
1093 Node *nodep=LookupNode(nodes,i,1);
1094
1095 double lat=latlong_to_radians(bin_to_latlong(nodes->file.latzero+latb)+off_to_latlong(nodep->latoffset));
1096 double lon=latlong_to_radians(bin_to_latlong(nodes->file.lonzero+lonb)+off_to_latlong(nodep->lonoffset));
1097
1098 if(lat>LatMin && lat<LatMax && lon>LonMin && lon<LonMax)
1099 (*callback)(i,lat,lon);
1100 }
1101 }
1102 }
1103
1104
1105 /*++++++++++++++++++++++++++++++++++++++
1106 Output the data for error logs within the region.
1107
1108 ErrorLogs *errorlogs The set of error logs to use.
1109
1110 double latmin The minimum latitude.
1111
1112 double latmax The maximum latitude.
1113
1114 double lonmin The minimum longitude.
1115
1116 double lonmax The maximum longitude.
1117 ++++++++++++++++++++++++++++++++++++++*/
1118
1119 void OutputErrorLog(ErrorLogs *errorlogs,double latmin,double latmax,double lonmin,double lonmax)
1120 {
1121 ll_bin_t latminbin=latlong_to_bin(radians_to_latlong(latmin))-errorlogs->file.latzero;
1122 ll_bin_t latmaxbin=latlong_to_bin(radians_to_latlong(latmax))-errorlogs->file.latzero;
1123 ll_bin_t lonminbin=latlong_to_bin(radians_to_latlong(lonmin))-errorlogs->file.lonzero;
1124 ll_bin_t lonmaxbin=latlong_to_bin(radians_to_latlong(lonmax))-errorlogs->file.lonzero;
1125 ll_bin_t latb,lonb;
1126 index_t i,index1,index2;
1127
1128 /* Loop through all of the error logs. */
1129
1130 for(latb=latminbin;latb<=latmaxbin;latb++)
1131 for(lonb=lonminbin;lonb<=lonmaxbin;lonb++)
1132 {
1133 ll_bin2_t llbin=lonb*errorlogs->file.latbins+latb;
1134
1135 if(llbin<0 || llbin>(errorlogs->file.latbins*errorlogs->file.lonbins))
1136 continue;
1137
1138 index1=LookupErrorLogOffset(errorlogs,llbin);
1139 index2=LookupErrorLogOffset(errorlogs,llbin+1);
1140
1141 if(index2>errorlogs->file.number_geo)
1142 index2=errorlogs->file.number_geo;
1143
1144 for(i=index1;i<index2;i++)
1145 {
1146 ErrorLog *errorlogp=LookupErrorLog(errorlogs,i,1);
1147
1148 double lat=latlong_to_radians(bin_to_latlong(errorlogs->file.latzero+latb)+off_to_latlong(errorlogp->latoffset));
1149 double lon=latlong_to_radians(bin_to_latlong(errorlogs->file.lonzero+lonb)+off_to_latlong(errorlogp->lonoffset));
1150
1151 if(lat>latmin && lat<latmax && lon>lonmin && lon<lonmax)
1152 printf("errorlog%"Pindex_t" %.6f %.6f\n",i,radians_to_degrees(lat),radians_to_degrees(lon));
1153 }
1154 }
1155 }

Properties

Name Value
cvs:description Functions for data visualisation.