V této ukázce přidáme k interaktivní mapě propojení se službou OpenStreetMap Nominatim, které umožní hledat určitou adresu (překlad z adresy na geografické souřadnice). Podobné služby poskytuji i služba Google Geocoding, ovšem její použití je možné pouze pro soukromé účely.
1. Nominatim
Abychom vyhledali souřadnice určité adresy, je nutné metodou GET zažádat o stránku,
http://nominatim.openstreetmap.org/search?q=Brno,CZ&format=xml
kde parametr q obsahuje dotazovaný řetězec a format definuje požadovaný výstupní formát. Odpověď vypadá následovně.
<searchresults
timestamp="Tue, 20 Feb 10 18:29:52 +0000"
attribution="Data Copyright OpenStreetMap Contributors, Some Rights Reserved. CC-BY-SA 2.0."
querystring="Brno,CZ" polygon="false"
exclude_place_ids="16290"
>
<place
place_id="16290" osm_type="node" osm_id="21308975"
boundingbox="49.0349487,49.3549487,16.4493039,16.7693039"
lat="49.1949487" lon="16.6093039"
display_name="Brno, Jihomoravský kraj, Česká Republika, Europe"
class="place" type="city"
icon="http://nominatim.openstreetmap.org/images/mapicons/poi_place_city.p.20.png"
/>
</searchresults>
2. Zdrojový kód
Zdrojový kód se skládá ze dvou částí. V první části používáme obdobu kódu uvedeného v příkladu Ovládání mapy, kde zinicializujeme mapu a vytvoříme jednoduchou nástrojovou lištu obsahující textové pole, do kterého bude možné zadat hledanou adresu a dále tlačítko pomocí kterého se odešle požadavek. Při úspěšné odpovědi služby Geocoding se nastaví mapa na souřadnice obdržené v odpovědi a v pravém horním rohu se vypíše výsledek dotazu.
example03.hx
import flash.display.Sprite;
import flash.events.Event;
import map.Canvas;
import map.LngLat;
import map.TileLayer;
import map.MapService;
import com.Button;
import com.ToolBar;
import com.StatusBar;
class Example03 extends Sprite {
var canvas:Canvas;
var toolbar:ToolBar;
var gc:OSMGeoCoding;
static public function main()
{
flash.Lib.current.stage.scaleMode = flash.display.StageScaleMode.NO_SCALE;
var t:Example03 = new Example03();
flash.Lib.current.stage.addEventListener(Event.RESIZE, t.stageResized);
flash.Lib.current.stage.addChildAt(t,0);
}
function new()
{
super();
toolbar = new ToolBar();
canvas = new Canvas();
toolbar.move(0, 0);
canvas.move(0, 0);
canvas.setCenter(new LngLat(16.720,49.570));
canvas.addLayer(new TileLayer(new OpenStreetMapService(14), 8));
stageResized(null);
initToolbar();
addChild(canvas);
addChild(toolbar);
canvas.initialize();
gc = new OSMGeoCoding();
gc.addEventListener(OSMGeoCoding.QUERY_FINISHED, queryFinished);
}
function queryFinished(e:Event)
{
toolbar.setText("Address:" + gc.address);
canvas.setCenter(gc.point);
}
function initToolbar()
{
var me = this;
var tf = toolbar.addTextField(200,"Božetěchova, Brno, CZ","Address:", -10);
toolbar.addButton(new SearchButton(), "Find", function(b:CustomButton) { me.gc.query(tf.text); });
tf.addEventListener(flash.events.KeyboardEvent.KEY_DOWN,
function(e:flash.events.KeyboardEvent) {
if (e.keyCode == flash.ui.Keyboard.ENTER) me.gc.query(tf.text);
}
);
}
public function stageResized(e:Event)
{
toolbar.setSize(flash.Lib.current.stage.stageWidth, 30);
canvas.setSize(flash.Lib.current.stage.stageWidth, flash.Lib.current.stage.stageHeight-20);
}
}
V druhé části je implementován jednoduchý Geocoding client, který umí odeslat požadavek na server a dekódovat odpověď. Jedná se o zjednodušenou implementaci, neboť a) vracíme první bod v odpovědi ačkoliv může obsahovat více výsledků, b) ignorujeme informaci o nejvhodnější úrovni přiblížení.
example03.hx
import flash.net.URLLoader;
import flash.net.URLRequest;
import flash.net.URLVariables;
class OSMGeoCoding extends URLLoader {
//Info:
//-----------------------------------------------------------------------------
// http://wiki.openstreetmap.org/wiki/Nominatim
public static var QUERY_FINISHED:String = "queryfinished";
public var point:LngLat;
public var address:String;
public function new()
{
super();
this.point = null;
this.address = "";
}
public function query(text:String)
{
var request:URLRequest = new URLRequest("http://nominatim.openstreetmap.org/search");
request.data = new URLVariables();
request.data.format = "xml";
request.data.q = text;
request.method = flash.net.URLRequestMethod.GET;
try {
dataFormat = flash.net.URLLoaderDataFormat.TEXT;
load(request);
addEventListener(Event.COMPLETE, getResponse);
} catch (unknown : Dynamic) {
trace("Error:"+unknown);
};
}
function getResponse(e:Event)
{
removeEventListener(Event.COMPLETE, getResponse);
try {
var resp:Xml = Xml.parse(data);
//trace("Response:" + resp);
var el:Xml = resp.firstElement();
if ((el != null) && (el.nodeName == "searchresults")) {
for (ep in el.elementsNamed("place"))
if (ep.exists("lat") && ep.exists("lon") && ep.exists("display_name"))
{
this.point = new LngLat(Std.parseFloat(ep.get("lon")), Std.parseFloat(ep.get("lat")));
this.address = ep.get("display_name");
dispatchEvent(new Event(QUERY_FINISHED));
return;
}
}
} catch (unknown : Dynamic) {
trace("Error:"+unknown);
};
}
}
3. Překlad a Html kód
Pro překlad platí informace uvedené v Ukázka použití s tím rozdílem, že nyní použijeme výchozí třídu Example03, kterou jsme implementovali v souboru example03.hx. Pro vložení do Html stránky lze využít kód uvedený v předchozím příkladu.
> haxe -swf output.swf -swf-version 9 -main Example03 -swf-header 800:600:25:ffffff -cp haxemaps
4. Výsledek
Kliknutím na tlačítko případně stisknutím klávesy Enter dojde k odeslání požadavku a v případě přijetí odpovědi dojde k nastavení středu mapy na pozici hledaného objektu.
Pro správnou funkci je vyžadován Flash player
Deprecated: Function ereg() is deprecated in
/home2/web/homes/vasicek/private/notes/web/data/map/examples.php on line
12