Completed
Push — development ( 1b87d2...43bb99 )
by Thomas
06:02
created

htdocs/lib2/logic/coordinate.class.php (2 issues)

Upgrade to new PHP Analysis Engine

These results are based on our legacy PHP analysis, consider migrating to our new PHP analysis engine instead. Learn more

1
<?php
2
/***************************************************************************
3
 * for license information see LICENSE.md
4
 ***************************************************************************/
5
6
class coordinate
7
{
8
    public $nLat = 0;
9
    public $nLon = 0;
10
11
    public function __construct($nNewLat, $nNewLon)
12
    {
13
        $this->nLat = $nNewLat;
14
        $this->nLon = $nNewLon;
15
    }
16
17
    /* get-Functions return array([lat] => string, [lon] => string)
18
     */
19
20
    public function getFloat()
21
    {
22
        return [
23
            'lat' => $this->nLat,
24
            'lon' => $this->nLon,
25
        ];
26
    }
27
28
    // d.ddddd°
29
    public function getDecimal()
30
    {
31 View Code Duplication
        if ($this->nLat < 0) {
32
            $sLat = 'S ' . sprintf('%08.5f', - $this->nLat) . '°';
33
        } else {
34
            $sLat = 'N ' . sprintf('%08.5f', $this->nLat) . '°';
35
        }
36
37 View Code Duplication
        if ($this->nLon < 0) {
38
            $sLon = 'W ' . sprintf('%09.5f', - $this->nLon) . '°';
39
        } else {
40
            $sLon = 'E ' . sprintf('%09.5f', $this->nLon) . '°';
41
        }
42
43
        return [
44
            'lat' => $sLat,
45
            'lon' => $sLon,
46
        ];
47
    }
48
49
    // d° mm.mmm
50
    public function getDecimalMinutes($hideMinutFractions = false)
51
    {
52
        $minute_format = ($hideMinutFractions ? '%02.0f.***' : '%06.3f');
53
54
        // Ocprop: ([N|S].*?)&#039;
55
        $nLat = $this->nLat;
56
        $bLatN = ($nLat < 0) ? false : true;
57
        if (!$bLatN) {
58
            $nLat = - $nLat;
59
        }
60
        $nLatDeg = floor($nLat);
61
        $nLatMin = ($nLat - $nLatDeg) * 60;
62
        if ($bLatN) {
63
            $sLat = 'N ' . sprintf('%02d', $nLatDeg) . '° ' . sprintf($minute_format, $nLatMin) . '\'';
64
        } else {
65
            $sLat = 'S ' . sprintf('%02d', $nLatDeg) . '° ' . sprintf($minute_format, $nLatMin) . '\'';
66
        }
67
68
        // Ocprop: ([E|W].*?)&#039;
69
        $nLon = $this->nLon;
70
        $bLonE = ($nLon < 0) ? false : true;
71
        if (!$bLonE) {
72
            $nLon = - $nLon;
73
        }
74
        $nLonDeg = floor($nLon);
75
        $nLonMin = ($nLon - $nLonDeg) * 60;
76
        if ($bLonE) {
77
            $sLon = 'E ' . sprintf('%03d', $nLonDeg) . '° ' . sprintf($minute_format, $nLonMin) . '\'';
78
        } else {
79
            $sLon = 'W ' . sprintf('%03d', $nLonDeg) . '° ' . sprintf($minute_format, $nLonMin) . '\'';
80
        }
81
82
        return [
83
            'lat' => $sLat,
84
            'lon' => $sLon,
85
        ];
86
    }
87
88
    // dd° mm' ss''
89
    public function getDecimalMinutesSeconds()
90
    {
91
        $nLat = $this->nLat;
92
        $bLatN = ($nLat < 0) ? false : true;
93
        if (!$bLatN) {
94
            $nLat = - $nLat;
95
        }
96
        $nLatDeg = floor($nLat);
97
        $nLatMin = ($nLat - $nLatDeg) * 60;
98
        $nLatSec = $nLatMin - floor($nLatMin);
99
        $nLatMin = ($nLatMin - $nLatSec);
100
        $nLatSec = $nLatSec * 60;
101
        $sLat = $bLatN ? 'N ' : 'S ';
102
        $sLat .= sprintf("%02d° %02d' %02d''", $nLatDeg, $nLatMin, $nLatSec);
103
104
        $nLon = $this->nLon;
105
        $bLonE = ($nLon < 0) ? false : true;
106
        if (!$bLonE) {
107
            $nLon = - $nLon;
108
        }
109
        $nLonDeg = floor($nLon);
110
        $nLonMin = ($nLon - $nLonDeg) * 60;
111
        $nLonSec = $nLonMin - floor($nLonMin);
112
        $nLonMin -= $nLonSec;
113
        $nLonSec *= 60;
114
        $sLon = $bLonE ? 'E ' : 'W ';
115
        $sLon .= sprintf("%03d° %02d' %02d''", $nLonDeg, $nLonMin, $nLonSec);
116
117
        return [
118
            'lat' => $sLat,
119
            'lon' => $sLon,
120
        ];
121
    }
122
123
    // array(zone, letter, north, east)
124
    public function getUTM()
125
    {
126
        /* Copyright (c) 2006, HELMUT H. HEIMEIER
127
           Permission is hereby granted, free of charge, to any person obtaining a
128
           copy of this software and associated documentation files (the "Software"),
129
           to deal in the Software without restriction, including without limitation
130
           the rights to use, copy, modify, merge, publish, distribute, sublicense,
131
           and/or sell copies of the Software, and to permit persons to whom the
132
           Software is furnished to do so, subject to the following conditions:
133
           The above copyright notice and this permission notice shall be included
134
           in all copies or substantial portions of the Software.*/
135
136
        /* Die Funktion wandelt geographische Koordinaten in UTM Koordinaten
137
           um. Geographische Länge lw und Breite bw müssen im WGS84 Datum
138
           gegeben sein. Berechnet werden UTM Zone, Ostwert ew und Nordwert nw.*/
139
140
        //Geographische Länge lw und Breite bw im WGS84 Datum
141
        if ($this->nLon == 0 || $this->nLat == 0) {
142
            return [
143
                'zone' => '',
144
                'letter' => '',
145
                'north' => 'N ' . 0,
146
                'east' => 'E ' . 0,
147
            ];
148
        }
149
        if ($this->nLon <= - 180 || $this->nLon > 180 || $this->nLat <= - 80 || $this->nLat >= 84) {
150
            // Werte nicht im Bereich des UTM Systems -180° <= nLon < +180°, -80° < nLat < 84° N
151
            return [
152
                '',
153
                '',
154
                0,
155
                0,
156
            ];
157
        }
158
        $lw = (float) $this->nLon;
159
        $bw = (float) $this->nLat;
160
161
        //WGS84 Datum
162
        //Große Halbachse a und Abplattung f
163
        $a = 6378137.000;
164
        $f = 3.35281068e-3;
165
        $b_sel = 'CDEFGHJKLMNPQRSTUVWXX';
166
167
        //Polkrümmungshalbmesser c
168
        $c = $a / (1 - $f);
169
170
        //Quadrat der zweiten numerischen Exzentrizität
171
        $ex2 = (2 * $f - $f * $f) / ((1 - $f) * (1 - $f));
172
        $ex4 = $ex2 * $ex2;
173
        $ex6 = $ex4 * $ex2;
174
        $ex8 = $ex4 * $ex4;
175
176
        //Koeffizienten zur Berechnung der Meridianbogenlänge
177
        $e0 = $c * (pi() / 180) * (1 - 3 * $ex2 / 4 + 45 * $ex4 / 64 - 175 * $ex6 / 256 + 11025 * $ex8 / 16384);
178
        $e2 = $c * (-3 * $ex2 / 8 + 15 * $ex4 / 32 - 525 * $ex6 / 1024 + 2205 * $ex8 / 4096);
179
        $e4 = $c * (15 * $ex4 / 256 - 105 * $ex6 / 1024 + 2205 * $ex8 / 16384);
180
        $e6 = $c * (-35 * $ex6 / 3072 + 315 * $ex8 / 12288);
181
182
        //Längenzone lz und Breitenzone (Band) bz
183
        $lzn = intval(($lw + 180) / 6) + 1;
184
185
        if ($bw >= 56.0 && $bw < 64.0 && $lw >= 3.0 && $lw < 12.0) {
186
            $lzn = 32;
187
        }
188
189
        // Special zones for Svalbard.
190
        if ($bw >= 72.0 && $bw < 84.0) {
191
            if ($lw >= 0.0 && $lw < 9.0) {
192
                $lzn = 31;
193
            } elseif ($lw >= 9.0 && $lw < 21.0) {
194
                $lzn = 33;
195
            } elseif ($lw >= 21.0 && $lw < 33.0) {
196
                $lzn = 35;
197
            } elseif ($lw >= 33.0 && $lw < 42.0) {
198
                $lzn = 37;
199
            }
200
        }
201
202
        $lz = "$lzn";
203
        if ($lzn < 10) {
204
            $lz = '0' . $lzn;
205
        }
206
        $bd = (int) (1 + ($bw + 80) / 8);
207
        $bz = substr($b_sel, $bd - 1, 1);
208
209
        //Geographische Breite in Radianten br
210
        $br = $bw * pi() / 180;
211
212
        $tan1 = tan($br);
213
        $tan2 = $tan1 * $tan1;
214
        $tan4 = $tan2 * $tan2;
215
216
        $cos1 = cos($br);
217
        $cos2 = $cos1 * $cos1;
218
        $cos4 = $cos2 * $cos2;
219
        $cos3 = $cos2 * $cos1;
220
        $cos5 = $cos4 * $cos1;
221
222
        $etasq = $ex2 * $cos2;
223
224
        //Querkrümmungshalbmesser nd
225
        $nd = $c / sqrt(1 + $etasq);
226
227
        //Meridianbogenlänge g aus gegebener geographischer Breite bw
228
        $g = ($e0 * $bw) + ($e2 * sin(2 * $br)) + ($e4 * sin(4 * $br)) + ($e6 * sin(6 * $br));
229
230
        //Längendifferenz dl zum Bezugsmeridian lh
231
        $lh = ($lzn - 30) * 6 - 3;
232
        $dl = ($lw - $lh) * pi() / 180;
233
        $dl2 = $dl * $dl;
234
        $dl4 = $dl2 * $dl2;
235
        $dl3 = $dl2 * $dl;
236
        $dl5 = $dl4 * $dl;
237
238
        //Maßstabsfaktor auf dem Bezugsmeridian bei UTM Koordinaten m = 0.9996
239
        //Nordwert nw und Ostwert ew als Funktion von geographischer Breite und Länge
240
241
        if ($bw < 0) {
242
            $nw = 10e6 + 0.9996 * ($g + $nd * $cos2 * $tan1 * $dl2 / 2 +
243
                    $nd * $cos4 * $tan1 * (5 - $tan2 + 9 * $etasq) * $dl4 / 24);
244
        } else {
245
            $nw = 0.9996 * ($g + $nd * $cos2 * $tan1 * $dl2 / 2 +
246
                    $nd * $cos4 * $tan1 * (5 - $tan2 + 9 * $etasq) * $dl4 / 24);
247
        }
248
        $ew = 0.9996 * ($nd * $cos1 * $dl + $nd * $cos3 * (1 - $tan2 + $etasq) * $dl3 / 6 +
249
                $nd * $cos5 * (5 - 18 * $tan2 + $tan4) * $dl5 / 120) + 500000;
250
251
        $nk = $nw - (int) $nw;
252
        if ($nk < 0.5) {
253
            $nw = '' . (int) $nw;
254
        } else {
255
            $nw = '' . ((int) $nw + 1);
256
        }
257
258
        while (strlen($nw) < 7) {
259
            $nw = '0' . $nw;
260
        }
261
262
        $nk = $ew - (int) $ew;
263
        if ($nk < 0.5) {
264
            $ew = '0' . (int) $ew;
265
        } else {
266
            $ew = '0' . intval($ew + 1);
267
        }
268
269
        return [
270
            'zone' => $lz,
271
            'letter' => $bz,
272
            'north' => 'N ' . floor($nw),
273
            'east' => 'E ' . floor($ew),
274
        ];
275
    }
276
277
    // return string
278
    public function getGK()
279
    {
280
        $pdResult = $this->wgs2pot($this->nLat, $this->nLon);
281
        $result = $this->geo2gk($pdResult[1], $pdResult[0]);
282
283
        return 'R ' . floor($result[0]) . ' H ' . floor($result[1]);
284
    }
285
286
    /**
287
     * @param int $bw
288
     * @param int $lw
289
     * @return array
290
     */
291
    public function wgs2pot($bw, $lw)
292
    {
293
        /* Copyright (c) 2006, HELMUT H. HEIMEIER
294
           Permission is hereby granted, free of charge, to any person obtaining a
295
           copy of this software and associated documentation files (the "Software"),
296
           to deal in the Software without restriction, including without limitation
297
           the rights to use, copy, modify, merge, publish, distribute, sublicense,
298
           and/or sell copies of the Software, and to permit persons to whom the
299
           Software is furnished to do so, subject to the following conditions:
300
           The above copyright notice and this permission notice shall be included
301
           in all copies or substantial portions of the Software.*/
302
303
        /* Die Funktion verschiebt das Kartenbezugssystem (map datum) vom
304
           WGS84 Datum (World Geodetic System 84) zum in Deutschland
305
           gebräuchlichen Potsdam-Datum. Geographische Länge lw und Breite
306
           bw gemessen in grad auf dem WGS84 Ellipsoid müssen
307
           gegeben sein. Ausgegeben werden geographische Länge lp
308
           und Breite bp (in grad) auf dem Bessel-Ellipsoid.
309
           Bei der Transformation werden die Ellipsoidachsen parallel
310
           verschoben um dx = -606 m, dy = -23 m und dz = -413 m.*/
311
312
        // Geographische Länge lw und Breite bw im WGS84 Datum
313
        if ($lw == '' || $bw == '') {
314
            return [
315
                0,
316
                0,
317
            ];
318
        }
319
        $lw = (float) $lw;
320
        $bw = (float) $bw;
321
322
        // Quellsystem WGS 84 Datum
323
        // Große Halbachse a und Abplattung fq
324
        $a = 6378137.000;
325
        $fq = 3.35281066e-3;
326
327
        // Zielsystem Potsdam Datum
328
        // Abplattung f
329
        $f = $fq - 1.003748e-5;
330
331
        // Parameter für datum shift
332
        $dx = - 606;
333
        $dy = - 23;
334
        $dz = - 413;
335
336
        // Quadrat der ersten numerischen Exzentrizität in Quell- und Zielsystem
337
        $e2q = (2 * $fq - $fq * $fq);
338
        $e2 = (2 * $f - $f * $f);
339
340
        // Breite und Länge in Radianten
341
        $b1 = $bw * (pi() / 180);
342
        $l1 = $lw * (pi() / 180);
343
344
        // Querkrümmungshalbmesser nd
345
        $nd = $a / sqrt(1 - $e2q * sin($b1) * sin($b1));
346
347
        // Kartesische Koordinaten des Quellsystems WGS84
348
        $xw = $nd * cos($b1) * cos($l1);
349
        $yw = $nd * cos($b1) * sin($l1);
350
        $zw = (1 - $e2q) * $nd * sin($b1);
351
352
        // Kartesische Koordinaten des Zielsystems (datum shift) Potsdam
353
        $x = $xw + $dx;
354
        $y = $yw + $dy;
355
        $z = $zw + $dz;
356
357
        // Berechnung von Breite und Länge im Zielsystem
358
        $rb = sqrt($x * $x + $y * $y);
359
        $b2 = (180 / pi()) * atan(($z / $rb) / (1 - $e2));
360
361
        if ($x > 0) {
362
            $l2 = (180 / pi()) * atan($y / $x);
363
        } elseif ($x < 0 && $y > 0) {
364
            $l2 = (180 / pi()) * atan($y / $x) + 180;
365
        } else {
366
            $l2 = (180 / pi()) * atan($y / $x) - 180;
367
        }
368
369
        return [
370
            $l2,
371
            $b2,
372
        ];
373
    }
374
375
    public function geo2gk($bp, $lp)
376
    {
377
        /* Copyright (c) 2006, HELMUT H. HEIMEIER
378
           Permission is hereby granted, free of charge, to any person obtaining a
379
           copy of this software and associated documentation files (the "Software"),
380
           to deal in the Software without restriction, including without limitation
381
           the rights to use, copy, modify, merge, publish, distribute, sublicense,
382
           and/or sell copies of the Software, and to permit persons to whom the
383
           Software is furnished to do so, subject to the following conditions:
384
           The above copyright notice and this permission notice shall be included
385
           in all copies or substantial portions of the Software.*/
386
387
        /* Die Funktion wandelt geographische Koordinaten in GK Koordinaten
388
           um. Geographische Länge lp und Breite bp müssen im Potsdam Datum
389
           gegeben sein. Berechnet werden Rechtswert rw und Hochwert hw.*/
390
391
        //Geographische Länge lp und Breite bp im Potsdam Datum
392
        if ($lp == '' || $bp == '') {
393
            return [
394
                0,
395
                0,
396
            ];
397
        }
398
        $lp = (float) $lp;
399
        $bp = (float) $bp;
400
401
        // Potsdam Datum
402
        // Große Halbachse a und Abplattung f
403
        $a = 6377397.155; // + $falseeasting;
404
        $f = 3.34277321e-3;
405
406
        // Polkrümmungshalbmesser c
407
        $c = $a / (1 - $f);
408
409
        // Quadrat der zweiten numerischen Exzentrizität
410
        $ex2 = (2 * $f - $f * $f) / ((1 - $f) * (1 - $f));
411
        $ex4 = $ex2 * $ex2;
412
        $ex6 = $ex4 * $ex2;
413
        $ex8 = $ex4 * $ex4;
414
415
        // Koeffizienten zur Berechnung der Meridianbogenlänge
416
        $e0 = $c * (pi() / 180) * (1 - 3 * $ex2 / 4 + 45 * $ex4 / 64 - 175 * $ex6 / 256 + 11025 * $ex8 / 16384);
417
        $e2 = $c * (-3 * $ex2 / 8 + 15 * $ex4 / 32 - 525 * $ex6 / 1024 + 2205 * $ex8 / 4096);
418
        $e4 = $c * (15 * $ex4 / 256 - 105 * $ex6 / 1024 + 2205 * $ex8 / 16384);
419
        $e6 = $c * (-35 * $ex6 / 3072 + 315 * $ex8 / 12288);
420
421
        // Breite in Radianten
422
        $br = $bp * pi() / 180;
423
424
        $tan1 = tan($br);
425
        $tan2 = $tan1 * $tan1;
426
        $tan4 = $tan2 * $tan2;
427
428
        $cos1 = cos($br);
429
        $cos2 = $cos1 * $cos1;
430
        $cos4 = $cos2 * $cos2;
431
        $cos3 = $cos2 * $cos1;
432
        $cos5 = $cos4 * $cos1;
433
434
        $etasq = $ex2 * $cos2;
435
436
        // Querkrümmungshalbmesser nd
437
        $nd = $c / sqrt(1 + $etasq);
438
439
        // Meridianbogenlänge g aus gegebener geographischer Breite bp
440
        $g = $e0 * $bp + $e2 * sin(2 * $br) + $e4 * sin(4 * $br) + $e6 * sin(6 * $br);
441
442
        // Längendifferenz dl zum Bezugsmeridian lh
443
        $kz = round($lp / 3);
444
        $lh = $kz * 3;
445
        $dl = ($lp - $lh) * pi() / 180;
446
        $dl2 = $dl * $dl;
447
        $dl4 = $dl2 * $dl2;
448
        $dl3 = $dl2 * $dl;
449
        $dl5 = $dl4 * $dl;
450
451
        // Hochwert hw und Rechtswert rw als Funktion von geographischer Breite und Länge
452
        $hw = ($g + $nd * $cos2 * $tan1 * $dl2 / 2 + $nd * $cos4 * $tan1 * (5 - $tan2 + 9 * $etasq)
453
            * $dl4 / 24);
454
        $rw = ($nd * $cos1 * $dl + $nd * $cos3 * (1 - $tan2 + $etasq) * $dl3 / 6 +
455
            $nd * $cos5 * (5 - 18 * $tan2 + $tan4) * $dl5 / 120 + $kz * 1e6 + 500000);
456
457
        $nk = $hw - (int) $hw;
458
        if ($nk < 0.5) {
459
            $hw = (int) $hw;
460
        } else {
461
            $hw = ((int) $hw) + 1;
462
        }
463
464
        $nk = $rw - (int) $rw;
465
        if ($nk < 0.5) {
466
            $rw = (int) $rw;
467
        } else {
468
            $rw = (int) ($rw + 1);
469
        }
470
471
        return [
472
            $rw,
473
            $hw,
474
        ];
475
    }
476
477
    // return string
478
    public function getRD()
479
    {
480
        // X0,Y0             Base RD coordinates Amersfoort
481
        $rdx_base = 155000;
482
        $rdy_base = 463000;
483
        // ?0, ?0            Same base, but as wgs84 coordinates
484
        $lat_base = 52.15517440;
485
        $lon_base = 5.38720621;
486
487
        for ($i = 0; $i <= 6; $i++) {
488
            for ($j = 0; $j <= 5; $j++) {
489
                $rpq[$i][$j] = 0;
490
                $spq[$i][$j] = 0;
491
            }
492
        }
493
        //#coefficients
494
        $rpq[0][1] = 190094.945;
0 ignored issues
show
The variable $rpq does not seem to be defined for all execution paths leading up to this point.

If you define a variable conditionally, it can happen that it is not defined for all execution paths.

Let’s take a look at an example:

function myFunction($a) {
    switch ($a) {
        case 'foo':
            $x = 1;
            break;

        case 'bar':
            $x = 2;
            break;
    }

    // $x is potentially undefined here.
    echo $x;
}

In the above example, the variable $x is defined if you pass “foo” or “bar” as argument for $a. However, since the switch statement has no default case statement, if you pass any other value, the variable $x would be undefined.

Available Fixes

  1. Check for existence of the variable explicitly:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        if (isset($x)) { // Make sure it's always set.
            echo $x;
        }
    }
    
  2. Define a default value for the variable:

    function myFunction($a) {
        $x = ''; // Set a default which gets overridden for certain paths.
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        echo $x;
    }
    
  3. Add a value for the missing path:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
    
            // We add support for the missing case.
            default:
                $x = '';
                break;
        }
    
        echo $x;
    }
    
Loading history...
495
        $rpq[1][1] = - 11832.228;
496
        $rpq[2][1] = - 114.221;
497
        $rpq[0][3] = - 32.391;
498
        $rpq[1][0] = - 0.705;
499
        $rpq[3][1] = - 2.340;
500
        $rpq[1][3] = - 0.608;
501
        $rpq[0][2] = - 0.008;
502
        $rpq[2][3] = 0.148;
503
504
        $spq[1][0] = 309056.544;
0 ignored issues
show
The variable $spq does not seem to be defined for all execution paths leading up to this point.

If you define a variable conditionally, it can happen that it is not defined for all execution paths.

Let’s take a look at an example:

function myFunction($a) {
    switch ($a) {
        case 'foo':
            $x = 1;
            break;

        case 'bar':
            $x = 2;
            break;
    }

    // $x is potentially undefined here.
    echo $x;
}

In the above example, the variable $x is defined if you pass “foo” or “bar” as argument for $a. However, since the switch statement has no default case statement, if you pass any other value, the variable $x would be undefined.

Available Fixes

  1. Check for existence of the variable explicitly:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        if (isset($x)) { // Make sure it's always set.
            echo $x;
        }
    }
    
  2. Define a default value for the variable:

    function myFunction($a) {
        $x = ''; // Set a default which gets overridden for certain paths.
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        echo $x;
    }
    
  3. Add a value for the missing path:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
    
            // We add support for the missing case.
            default:
                $x = '';
                break;
        }
    
        echo $x;
    }
    
Loading history...
505
        $spq[0][2] = 3638.893;
506
        $spq[2][0] = 73.077;
507
        $spq[1][2] = - 157.984;
508
        $spq[3][0] = 59.788;
509
        $spq[0][1] = 0.433;
510
        $spq[2][2] = - 6.439;
511
        $spq[1][1] = - 0.032;
512
        $spq[0][4] = 0.092;
513
        $spq[1][4] = - 0.054;
514
515
        // Calculate X, Y of origin
516
        $latDiff = $this->nLat - $lat_base;
517
        $dlat = 0.36 * $latDiff;
518
        $lonDiff = $this->nLon - $lon_base;
519
        $dlon = 0.36 * $lonDiff;
520
        $xOrigin = 0;
521
        $yOrigin = 0;
522
523
        for ($q = 0; $q <= 5; $q++) {
524
            for ($p = 0; $p <= 6; $p++) {
525
                $xOrigin = $xOrigin + ($rpq[$p][$q] * ((pow($dlat, $p)) * (pow($dlon, $q))));
526
                $yOrigin = $yOrigin + ($spq[$p][$q] * ((pow($dlat, $p)) * (pow($dlon, $q))));
527
            }
528
        }
529
        $xOrigin = $xOrigin + $rdx_base;
530
        $yOrigin = $yOrigin + $rdy_base;
531
532
        return 'X ' . floor($xOrigin) . ' Y ' . floor($yOrigin);
533
    }
534
535
    // returns string
536
    public function getQTH()
537
    {
538
        $lon = $this->nLon;
539
        $lat = $this->nLat;
540
541
        $lon += 180;
542
        $l[0] = floor($lon / 20);
543
        $lon -= 20 * $l[0];
544
        $l[2] = floor($lon / 2);
545
        $lon -= 2 * $l[2];
546
        $l[4] = floor($lon * 60 / 5);
547
548
        $lat += 90;
549
        $l[1] = floor($lat / 10);
550
        $lat -= 10 * $l[1];
551
        $l[3] = floor($lat);
552
        $lat -= $l[3];
553
        $l[5] = floor($lat * 120 / 5);
554
555
        return sprintf('%c%c%c%c%c%c', $l[0] + 65, $l[1] + 65, $l[2] + 48, $l[3] + 48, $l[4] + 65, $l[5] + 65);
556
    }
557
558
    // return string
559
    public function getSwissGrid()
560
    {
561
        $nLat = $this->nLat * 3600;
562
        $nLon = $this->nLon * 3600;
563
564
        // Quelle: http://www.swisstopo.admin.ch/internet/swisstopo/de/home/apps/calc.html
565
        // Hilfsgrössen
566
        $b = ($nLat - 169028.66) / 10000.0;
567
        $l = ($nLon - 26782.5) / 10000.0;
568
569
        // Nord x
570
        $x = 200147.07 + 308807.95 * $b + 3745.25 * $l * $l + 76.63 * $b * $b + 119.79 * $b * $b * $b - 194.56 * $b * $l * $l;
571
        $x = floor($x);
572
573
        // Ost y
574
        $y = 600072.37 + 211455.93 * $l - 10938.51 * $l * $b - 0.36 * $l * $b * $b - 44.54 * $l * $l * $l;
575
        $y = floor($y);
576
577
        // Namen: "CH1903", "Schweizer Landeskoordinaten" oder "Swiss Grid"
578
        $swissgrid = "$y / $x";
579
        // Karten Links
580
        $mapplus = "<a href=\"http://www.mapplus.ch/frame.php?map=&x=$y&y=$x&zl=13\" target=\"_blank\">MapPlus</a>";
581
        $mapsearch = "<a href=\"http://map.search.ch/$y,$x\" target=\"_blank\">map.search.ch</a>";
582
583
        return [
584
            'coord' => $swissgrid,
585
            $mapplus,
586
            $mapsearch,
587
        ];
588
    }
589
590
    /**
591
     * @param string $name
592
     * @return bool
593
     */
594 View Code Duplication
    public static function parseRequestLat($name)
595
    {
596
        if (!isset($_REQUEST[$name . 'NS']) || !isset($_REQUEST[$name . 'Lat']) || !isset($_REQUEST[$name . 'LatMin'])) {
597
            return false;
598
        }
599
600
        $coordNS = $_REQUEST[$name . 'NS'];
601
        $coordLat = $_REQUEST[$name . 'Lat'] + 0;
602
        $coordLatMin = str_replace(',', '.', $_REQUEST[$name . 'LatMin']) + 0;
603
604
        $lat = $coordLat + $coordLatMin / 60;
605
        if ($coordNS == 'S') {
606
            $lat = - $lat;
607
        }
608
609
        return $lat;
610
    }
611
612
    /**
613
     * @param string $name
614
     * @return bool
615
     */
616 View Code Duplication
    public static function parseRequestLon($name)
617
    {
618
        if (!isset($_REQUEST[$name . 'EW']) || !isset($_REQUEST[$name . 'Lon']) || !isset($_REQUEST[$name . 'LonMin'])) {
619
            return false;
620
        }
621
622
        $coordEW = $_REQUEST[$name . 'EW'];
623
        $coordLon = $_REQUEST[$name . 'Lon'] + 0;
624
        $coordLonMin = str_replace(',', '.', $_REQUEST[$name . 'LonMin']) + 0;
625
626
        $lon = $coordLon + $coordLonMin / 60;
627
        if ($coordEW == 'W') {
628
            $lon = - $lon;
629
        }
630
631
        return $lon;
632
    }
633
634
    public function getW3W($language)
635
    {
636
        global $opt;
637
638
        if (!$opt['lib']['w3w']['apikey']) {
639
            return false;
640
        }
641
642
        $params = [
643
            'key' => $opt['lib']['w3w']['apikey'],
644
            'coords' => sprintf('%f,%f', $this->nLat, $this->nLon),
645
            'lang' => strtolower($language),
646
        ];
647
        $params_str = http_build_query($params);
648
649
        $result = @file_get_contents('https://api.what3words.com/v2/reverse?' . $params_str);
650
        if ($result === false) {
651
            return false;
652
        }
653
654
        $json = json_decode($result, true);
655
        if (!isset($json['words'])) {
656
            return false;
657
        }
658
659
        return $json['words'];
660
    }
661
}
662