source: trunk/mapbender/http/navn/alkisnav_adr.php @ 364

Revision 364, 14.6 KB checked in by frank.jaeger, 8 years ago (diff)

Verbesserungen an NAV und Buchauskunft

Line 
1<?php
2/*      Navigation mit ALKIS-Daten im Mapbender 2.7 - Teil Adressen-Suche
3        Diese Version des Programms verwendet die Datenbank-Struktur aus dem norGIS-ALKIS-Importer.
4
5Version vom
6        2016-02-11      Version fÃŒr norGIS-ALKIS-Import aus Version Classic abgeleitet.
7        2016-03-02  $gemeinde auf feste LÀnge korrigieren
8
9        ToDo:
10        -       Gruppierung (mit Zeile) der Straßenliste nach Gemeinde
11        -       Eingabe aus "Balken" von Buchauskunft "Lage" zulassen: Numerisch: Gem-Str-Haus-lfd
12                -- lfd (NebengebÀude) als Untergliederung der geklickten Haus-Nr anzeigen
13                Analog zur Zerlegung des FS-Kennz in _fls
14        -       Mouse-Over in Straßenliste soll Position zeigen.
15                Dazu in der DB eine Tabelle mit Koordinate zum StraßenschlÃŒssel aufbauen.
16*/
17
18// Variable Initialisieren
19$str_schl="";
20$skey="";
21
22$cntget = extract($_GET);
23$gemeinde=str_pad($gemeinde, 3, "0", STR_PAD_LEFT); // temporÀr
24include("../../conf/alkisnav_conf.php");
25include("alkisnav_fkt.php"); // Funktionen
26$con_string = "host=".$host." port=".$port." dbname=".$dbname.$gkz." user=".$user." password=".$password;
27$con = pg_connect ($con_string) or die ("Fehler bei der Verbindung zur Datenbank ".$dbname.$gkz);
28
29echo <<<END
30
31<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
32<html>
33<head>
34        <meta http-equiv="cache-control" content="no-cache">
35        <meta http-equiv="pragma" content="no-cache">
36        <meta http-equiv="expires" content="0">
37        <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
38        <title>ALKIS-Suche Adressen</title>
39        <link rel="stylesheet" type="text/css" href="alkisnav.css">
40        <script type='text/javascript'>
41                function transtitle (trans) { // Titel der letzten Transaktion anzeigen
42                        document.getElementById('transaktiontitle').innerHTML = trans;
43                }
44                function imFenster(dieURL) {
45                        var link = encodeURI(dieURL);
46                        window.open(link,'','left=10,top=10,width=620,height=800,resizable=yes,menubar=no,toolbar=no,location=no,status=no,scrollbars=yes');
47                }
48        </script>
49</head>
50<body>
51<a href='javascript:history.back()'>
52        <img src="ico/zurueck.png" width="16" height="16" alt="&lt;&lt;" title="zur&uuml;ck">
53</a>&nbsp;
54<span title='zuletzt ausgef&uuml;hrte Aktion'>
55        <dfn class='title' id='transaktiontitle'></dfn>
56</span>
57
58END;
59
60function suchStrName() {
61        // Strassen nach Name(-nsanfang)
62        global $street, $scalestr, $str_schl, $gkz, $gemeinde, $epsg, $gfilter, $debug, $auskpath;
63        //if ($debug > 1) {echo "<p class='dbg'>function suchStrName()<p>";} // Ablauf-Verfolgung
64
65        $linelimit=120;  // -> in Conf?
66        $str_schl=""; // Loeschen vorh. Ergebnis
67        preg_match("/^(\D+)(\d*)(\D*)/",$street,$matches); # 4 matches name/nr/zusatz
68        //echo "match: 1='".$matches[1]."', 2='".$matches[2]."', 3='".$matches[3]."'";
69        $matches[1] = preg_replace("/strasse/i","str", $matches[1]);
70        $matches[1] = preg_replace("/str\./i","str", $matches[1]);
71
72        if(preg_match("/\*/",$matches[1])){
73                $match=trim(preg_replace("/\*/i","%", strtoupper($matches[1])));
74        } else {
75                $match=trim($matches[1])."%";
76        }
77
78        $sql ="SELECT g.gemeinde, g.bezeichnung AS gemname, k.gml_id, k.bezeichnung, k.schluesselgesamt, k.lage
79        FROM ax_lagebezeichnungkatalogeintrag k
80        JOIN ax_gemeinde g ON k.land=g.land AND k.regierungsbezirk=g.regierungsbezirk AND k.kreis=g.kreis AND k.gemeinde=g.gemeinde
81        WHERE k.bezeichnung ILIKE $1 AND k.endet IS NULL AND g.endet IS NULL ";
82
83        switch ($gfilter) {
84                case 1: // Einzelwert
85                        $sql.="AND k.gemeinde='".$gemeinde."' ";
86                        break;
87                case 2: // Liste
88                        $sql.="AND k.gemeinde in (".str_replace(",", "','", $gemeinde).") ";
89                        break;
90                default: // kein Filter
91                        break;
92        }
93        $sql.="ORDER BY g.bezeichnung, k.bezeichnung, k.lage LIMIT $2 ;";
94        $v=array($match,$linelimit);
95        $res=pg_prepare("", $sql);
96        $res=pg_execute("", $v);
97
98        if (!$res) {
99                echo "\n<p class='err'>Fehler bei Name</p>";
100                if ($debug > 2) {echo "<p class='dbg'>SQL = '".$sql."'<p>";}
101                return;
102        }
103
104        $cnt = 0;
105        $gwgem="";
106        while($row = pg_fetch_array($res)) {
107                $gemname=$row["gemname"];
108                $gemnr=$row["gemeinde"] ;
109                if ($gwgem != $gemname) {
110                        if ($gfilter != 1) {
111                                zeile_gemeinde($gemnr, $gemname, false); // ToDo: aber ohne Link oder Link verarbeiten können
112                        }
113                        $gwgem=$gemname;
114                }
115                $gkey=$row["schluesselgesamt"]; // Land-RegBez-Kreis-Gem-Strasse - fÃŒr weitere Suche
116                $skey=$row["lage"]; // Nur Str.-schl. daraus
117                $kgml=$row["gml_id"]; // ID von Katalog
118                $sname=htmlentities($row["bezeichnung"], ENT_QUOTES, "UTF-8");
119                zeile_strasse ($gkey, $skey, $sname, $kgml, $gemname);
120                $cnt++;
121        }
122
123        if($cnt == 0) {
124                echo "<pclass='anz'>Keine Stra&szlig;e</p>";
125                if ($debug > 2) {echo "<p class='err'>SQL = '".$sql."'<br>$1 = '".$match."'<p>";} // ++ Nur Entw.
126        } elseif($cnt == 1) { // Eindeutig
127                $str_schl=$gkey; // dann gleich weiter
128        } elseif($cnt >= $linelimit) {
129                echo "<p class='anz'>".$cnt." Stra&szlig;en ... und weitere</p>";                       
130        } elseif ($cnt > 1) {
131                echo "\n<p class='anz'>".$cnt." Stra&szlig;en</p>";     
132        }
133        return;
134}
135
136function suchStrKey() { // Strassen nach num. Schluessel
137        global $street, $scalestr, $str_schl, $gkz, $gemeinde, $epsg, $gfilter, $debug, $auskpath;
138        //if ($debug > 1) {echo "<p class='dbg'>function suchStrKey()<p>";} // Ablauf-Verfolgung
139        $linelimit=60;
140        if(preg_match("/\*/",$street)) {
141                $match=trim(preg_replace("/\*/i","%",$street));
142                // fuehrende Nullen eingeben oder fuehrende Wildcard
143        } else {
144                $match=str_pad($street, 5, "0", STR_PAD_LEFT); // "Wie eine Zahl" verarbeiten
145        }
146        $sql ="SELECT g.bezeichnung AS gemname, k.gml_id, k.bezeichnung, k.schluesselgesamt, k.lage
147        FROM ax_lagebezeichnungkatalogeintrag as k
148        JOIN ax_gemeinde g ON k.land=g.land AND k.regierungsbezirk=g.regierungsbezirk AND k.kreis=g.kreis AND k.gemeinde=g.gemeinde
149        WHERE k.lage LIKE $1 AND k.endet IS NULL AND g.endet IS NULL ";
150        switch ($gfilter) {
151                case 1: // Einzelwert
152                        $sql.="AND k.gemeinde='".$gemeinde."' ";
153                        break;
154                case 2: // Liste
155                        $sql.="AND k.gemeinde in ('".str_replace(",", "','", $gemeinde)."') ";
156                        break;
157        }
158        $sql.="ORDER BY k.lage, k.bezeichnung LIMIT $2 ;";
159
160        $v=array($match,$linelimit);
161        $res=pg_prepare("", $sql);
162        $res=pg_execute("", $v);
163        if (!$res) {
164                echo "\n<p class='err'>Fehler bei Schl&uuml;ssel</p>";
165                return;
166        }
167        $cnt = 0;
168        while($row = pg_fetch_array($res)) {
169                $sname=htmlentities($row["bezeichnung"], ENT_QUOTES, "UTF-8");         
170                $gkey=$row["schluesselgesamt"];
171                $gemname=htmlentities($row["gemname"], ENT_QUOTES, "UTF-8");
172                $skey=$row["lage"];
173                $kgml=$row["gml_id"]; // ID von Katalog
174                zeile_strasse ($gkey, $skey, $sname, $kgml, $gemname);
175                $cnt++;
176        }
177        if($cnt == 0) {
178                echo "\n<p class='anz'>Keine Stra&szlig;e mit Schl&uuml;ssel ".$match."</p>";
179        } elseif($cnt == 1) { // Eindeutig
180                $str_schl=$gkey; // dann gleich weiter
181        } elseif ($cnt >= $linelimit) {
182                echo "\n<p>".$cnt." Stra&szlig;en ... und weitere</p>";                 
183        } elseif ($cnt > 1) {
184                echo "\n<p class='anz'>".$cnt." Stra&szlig;en</p>";     
185        }       
186        return;
187}
188
189function suchHausZurStr($showParent) { // Haeuser zu einer Strasse
190        global $str_schl, $gkz, $scalestr, $scalehs, $epsg, $gemeinde, $epsg, $gfilter, $debug, $auskpath;
191        //if ($debug > 1) {echo "<p class='dbg'>function suchHausZurStr()<p>";} // Ablauf-Verfolgung
192
193        // Head
194        // Strasse zum Strassenschluessel
195        $sql ="SELECT g.bezeichnung AS gemname, k.gml_id AS kgml, k.bezeichnung, k.land, k.regierungsbezirk, k.kreis, k.gemeinde, k.lage
196        FROM ax_lagebezeichnungkatalogeintrag as k
197        JOIN ax_gemeinde g ON k.land=g.land AND k.regierungsbezirk=g.regierungsbezirk AND k.kreis=g.kreis AND k.gemeinde=g.gemeinde
198        WHERE k.schluesselgesamt = $1 AND k.endet IS NULL AND g.endet IS NULL LIMIT 1";
199
200        $v=array($str_schl);    // Schluessel-Gesamt ..
201        $res=pg_prepare("", $sql);
202        $res=pg_execute("", $v);
203        if (!$res) {
204                echo "\n<p class='err'>Fehler bei Name zum Stra&szlig;enschl&uuml;ssel</p>";
205                if ($debug > 2) {echo "<p class='dbg'>SQL = '".$sql."'<p>";}
206                return;
207        }
208
209        if($row = pg_fetch_array($res)) { // .. gefunden
210                $kgml=$row["kgml"]; // ID aus Katalog
211                $sname=$row["bezeichnung"];
212                $land =$row["land"];    // Einzel-Felder fÃŒr JOIN _lagebezeichnung_
213                $regb =$row["regierungsbezirk"];
214                $kreis=$row["kreis"];
215                $gemnd=$row["gemeinde"];
216                $nr=$row["lage"];
217                $gemname=htmlentities($row["gemname"], ENT_QUOTES, "UTF-8");
218                if ($showParent) {
219                        // EINE Koordinate zur Strasse besorgen
220                        // ax_Flurstueck >zeigtAuf> ax_LagebezeichnungOhneHausnummer
221                        $sqlko ="SELECT ";
222                        if($epsg == "25832") { // Transform nicht notwendig
223                                $sqlko.="st_x(st_Centroid(f.wkb_geometry)) AS x, ";
224                                $sqlko.="st_y(st_Centroid(f.wkb_geometry)) AS y ";
225                        } else {
226                                $sqlko.="st_x(st_transform(st_Centroid(f.wkb_geometry), ".$epsg.")) AS x, ";
227                                $sqlko.="st_y(st_transform(st_Centroid(f.wkb_geometry), ".$epsg.")) AS y ";
228                        }
229                        $sqlko.="FROM ax_lagebezeichnungohnehausnummer o ";
230                        $sqlko.="JOIN ax_flurstueck f ON o.gml_id=ANY(f.zeigtauf) ";
231                        $sqlko.="WHERE o.land= $1 AND o.regierungsbezirk= $2 AND o.kreis= $3 AND o.gemeinde= $4 AND o.lage= $5 ";       
232                        $sqlko.="LIMIT 1;"; // die erstbeste Koordinate
233
234                        $v=array($land,$regb,$kreis,$gemnd,$nr);
235                        $resko=pg_prepare("", $sqlko);
236                        $resko=pg_execute("", $v);
237                        if ($resko) {
238                                $rowko=pg_fetch_array($resko);
239                                $x=$rowko["x"];
240                                $y=$rowko["y"];
241                        } else {               
242                                echo "\n<p class='err'>Fehler bei Koordinate zur Stra&szlig;e</p>";
243                        }
244
245                        // "function zeile_strasse()" hier nicht verwendbar. ZusÀtzlicher Map-Link mit Koordinate
246                        // Icon -> Buchnachweis
247                        echo "\n\t<br><a href='javascript:imFenster(\"".$auskpath."alkisstrasse.php?gkz=".$gkz."&amp;gmlid=".$kgml."\")'>";
248                                echo "\n\t\t<img class='nwlink' src='ico/Lage_mit_Haus.png' width='16' height='16' alt='STR' title='Buchauskunft zur Stra&szlig;e'>";
249                        echo "\n\t</a>";
250
251                        if ($x > 0) { // Koord. bekommen?
252                                echo "\n\t<a title='Positionieren 1:".$scalestr."' href='javascript:"; // mit Link
253                                                echo "transtitle(\"auf Stra&szlig;e positioniert\"); ";
254                                                echo "parent.parent.parent.mb_repaintScale(\"mapframe1\",".$x.",".$y.",".$scalestr."); ";
255                                                echo "parent.parent.showHighlight(".$x.",".$y."); ";
256                                        //      echo "document.location.href=\"".$_SERVER['SCRIPT_NAME']."?gkz=".$gkz."&amp;gemeinde=".$gemeinde."&amp;epsg=".$epsg."&amp;str_schl=".$str_schl."\"";
257                                        echo "' "; // end href
258                                        echo "\n\t\tonmouseover='parent.parent.showHighlight(" .$x. "," .$y. ")' ";
259                                        echo "\n\t\tonmouseout='parent.parent.hideHighlight()'";
260                                echo ">\n\t\t".$sname." (".$nr.")\n\t</a>";
261                        } else { // keine Koord. gefunden
262                                echo $sname." (".$nr.")"; // nur Anzeige, ohne Link
263                        }
264                        switch ($gfilter) {
265                                case 0: // Kein Filter
266                                        echo " in ".$gemname;
267                                        break;
268                                case 2: // Liste
269                                        echo " in ".$gemname;
270                                        break;
271                        }                       
272                }
273                echo "\n<hr>";
274
275                // Body
276                // Haeuser zum Strassenschluessel
277                $sql="SELECT min(replace(h.hausnummer,' ','')) AS hsnr, ";
278                if($epsg == "25832") { // Transform nicht notwendig
279                        $sql.="avg (st_x(p.wkb_geometry)) AS x, ";
280                        $sql.="avg (st_y(p.wkb_geometry)) AS y ";               
281                } else { 
282                        $sql.="avg (st_x(st_transform(p.wkb_geometry,".$epsg."))) AS x, ";
283                        $sql.="avg (st_y(st_transform(p.wkb_geometry,".$epsg."))) AS y ";               
284                }
285                $sql.="FROM ap_pto p JOIN ax_lagebezeichnungmithausnummer h ON h.gml_id=ANY(p.dientzurdarstellungvon)
286                WHERE p.art='HNR' AND h.land= $1 AND h.regierungsbezirk= $2 AND h.kreis= $3 AND h.gemeinde= $4 AND h.lage= $5
287                AND p.endet IS NULL AND h.endet IS NULL
288                GROUP BY lpad(split_part(hausnummer,' ',1), 4, '0'), split_part(hausnummer,' ',2)
289                ORDER BY lpad(split_part(hausnummer,' ',1), 4, '0'), split_part(hausnummer,' ',2);";
290                // Problem: In der Datenbank gibt es mehrere hausnummern-Koordinaten fÃŒr verschiedene
291                // MaßstÀbe der Kartendarstellung
292                // Diese sollten nicht mehrfach gelistet werden. FÃŒr die Positionierung "irgendeine" nehmen.
293                // Lösung: ÃŒber GROUP BY in SQL. Alternative Lösungen wÀren:
294                //  1. Gruppenwechsel bei Abarbeitung des Result
295                //  2. Subquery mit LIMIT 1 statt JOIN
296                //  3. Koordinate aus dem Mittelpunkt der GebÀude-Geometrie verwenden statt aus dem PrÀsentationsobjekt der Hausnummer
297
298                $v=array($land,$regb,$kreis,$gemnd,$nr);
299                $resh=pg_prepare("", $sql);
300                $resh=pg_execute("", $v);
301                if (!$resh) {
302                        echo "\n<p class='err'>Fehler bei H&auml;user zum Stra&szlig;enschl&uuml;ssel</p>";
303                        if ($debug > 2) {echo "<p class='dbg'>SQL='".$sql."'<br>Array=".$v."</p>";}
304                        return;
305                }
306
307                $cnt=0;
308                $count=0;
309                echo "\n<table>";
310                while($rowh = pg_fetch_array($resh)) { // mehrere HsNr je Zeile
311                        if($count == 0) {echo "\n<tr>";}       
312                        $hsnr=$rowh["hsnr"];
313                        $x=$rowh["x"];
314                        $y=$rowh["y"];
315                        echo "\n\t<td class='hsnr'>";
316                                echo "<a href='";
317                                        echo "javascript:";
318                                        echo "transtitle(\"auf Haus ".$hsnr." positioniert\"); ";
319                                        echo "parent.parent.parent.mb_repaintScale(\"mapframe1\",".$x.",".$y.",".$scalehs."); ";
320                                        echo "parent.parent.showHighlight(".$x.",".$y.");' ";
321                                echo "onmouseover='parent.parent.showHighlight(".$x.",".$y.")' ";
322                                echo "onmouseout='parent.parent.hideHighlight()";
323                                echo "'>".$hsnr."</a>";
324                        echo "</td>";
325                        $cnt++;
326                        $count++;
327                        if($count == 7) { // Max. Hausnummern je Zeile (Test: 3stellige HsNr mit Zusatz)
328                                echo "\n</tr>";
329                                $count = 0;
330                        }
331                }
332                if($count > 0) {echo "\n</tr>";}
333                echo "\n</table>";
334                if ($cnt > 1) {
335                        echo "\n<p class='anz'>".$cnt." Hausnummern</p>";
336                }
337        } else {
338                echo "\n<p class='anz'>Keine Stra&szlig;e</p>";
339        }
340        return;
341}
342// ===========
343// Start hier!
344// ===========
345if(isset($epsg)) {
346        $epsg = str_replace("EPSG:", "" , $_REQUEST["epsg"]);   
347} else {
348        $epsg=$gui_epsg; // aus Conf
349}
350
351// Filter auf Zustaendigkeit z.B. ein Stadtgebiet
352if ($gemeinde == "") {
353        $gfilter = 0; // ungefiltert
354} elseif(strpos($gemeinde, ",") === false) {
355        $gfilter = 1; // Einzelwert
356} else {
357        $gfilter = 2; // Liste
358}
359// ax_lagebezeichnungkatalogeintrag.gemeinde: z.B. Classic='40' / NorBit  = '040'
360// Im Mapbender mit fuehrenden Nullen eingeben: gazetteer_alkis.SRC
361// alkisnav.htm?..&gemeinde=040&..
362
363// +++Zerlegung Eingabe aus "Balken" von Buchauskunft "Lage": Numerisch: Gem-Str-Haus-lfd
364
365if ($str_schl != "") { // Wert kommt aus aus Link
366        $trans="Hausnummern zur Stra&szlig;e";
367        suchHausZurStr(true);
368// Wert aus Eingabe in Formular
369} elseif($street != "") {
370        if (trim($street, "*,0..9, ") == "") { // Zahl, ggf. mit Wildcard
371                $trans="Suche Stra&szlig;enschl&uuml;ssel \"".$street."\"";
372                suchStrKey();
373        } else { // Name suchen
374                $trans="Suche Stra&szlig;enname \"".$street."*\"";
375                suchStrName();
376        }
377        if($str_schl != "") { // EINdeutiges Ergebnis
378                $trans="1 Stra&szlig;e gefunden, Hausnummern";
379                suchHausZurStr(false);
380        }
381} else {
382        $trans="keine Eingabe";
383}
384
385// Nach Durchlaufen des PHP-Scriptes die zuletzt ausgefÃŒhrte Transaktion
386//  im Kopf des Ergebnisrahmens anzeigen.
387// Dazu die im HTML-Header definierte Javascript-Function benutzen.
388// Alternativ wird auch aus dem Javascript "positionieren Karte" dieser Titel gesetzt.
389echo "
390<script type='text/javascript'>
391        transtitle ('".$trans."') ;
392</script>";
393
394?>
395
396</body>
397</html>
Note: See TracBrowser for help on using the repository browser.