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 1248 - (show annotations) (download) (as text)
Thu Jan 24 19:35:05 2013 UTC (12 years, 1 month ago) by amb
File MIME type: text/x-csrc
File size: 28398 byte(s)
Add the ability for the visualiser to display highways that have a particular
property.

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

Properties

Name Value
cvs:description Functions for data visualisation.