Hallo,
ich versuche mich gerade daran für unseren Ort eine OSM Map zuerstellen. Mit der vorlage von http://www.einbeispiel.de/maps/maps/rahlstedt/karte.htm, aber was mich stört sind die popups von den markern, weil die nur durch ein erneutes klicken schließen.
Leider sind meine Kenntnisse nicht ausreichend, mir würde auch schon ein rotes kreuz(oben rechts) zum schließen der popups reichen.
Füge mal vor Deinem layer eine Definition von “OpenLayers.Feature.prototype.popupClass” ein, sowas ungefähr:
...
Popup_mit_X=new OpenLayers.Class(OpenLayers.Popup,{'closeBox': true ... weitere Optionen wie autosize, minsize ... });
OpenLayers.Feature.prototype.popupClass=Popup_mit_X;
var layerxxx = new OpenLayers.Layer.Text( "Blabla",....
Das geht leider nicht mit allen Arten von Popups – ich verwende gern “Popup.FramedCloud”, sprechblasenähnlich mit runden Ecken --aber mit den normalen eckigen Popups geht da.
Grüße, Max
PS: hab grad beim rumbasteln festgestellt, dass ein derartiges Popup sich zwar per [x] schliessen lässt, aber danach nicht wieder aufgepopt werden kann…
die definition hab ich gar nicht. meine until.js sieht so aus
/*
* Einige Funktionen die ursprünglich von http://wiki.openstreetmap.org/wiki/DE:Karte_in_Webseite_einbinden stammen,
* teilweise modifiziert
*
* Some functions from the example at http://wiki.openstreetmap.org/wiki/DE:Karte_in_Webseite_einbinden, some
* slightly modified
*/
function jumpTo(lon, lat, zoom) {
var x = Lon2Merc(lon);
var y = Lat2Merc(lat);
map.setCenter(new OpenLayers.LonLat(x, y), zoom);
return false;
}
function Lon2Merc(lon) {
return 20037508.34 * lon / 180;
}
function Lat2Merc(lat) {
var PI = 3.14159265358979323846;
lat = Math.log(Math.tan( (90 + lat) * PI / 360)) / (PI / 180);
return 20037508.34 * lat / 180;
}
function addMarker(layer, lon, lat, popupContentHTML, showPopupOnLoad, iconId) {
// Koordinaten in LonLat umwandeln
var ll = new OpenLayers.LonLat(Lon2Merc(lon), Lat2Merc(lat));
// Feature erstellen und konfigurieren (Popup und Marker)
var feature = new OpenLayers.Feature(layer, ll);
feature.closeBox = true;
feature.popupClass = OpenLayers.Class(OpenLayers.Popup.FramedCloud, {minSize: new OpenLayers.Size(200, 120) } );
feature.data.popupContentHTML = popupContentHTML;
feature.data.overflow = "auto";
feature.data.icon = makeIcon(iconId);
// Marker erstellen
var marker = feature.createMarker();
/*
* Handler Funktionen für die Mouse-Events
*/
// Click
var markerClick = function(evt) {
// Wenn das Popup nicht sichtbar ist, dann kann es nicht fest sichtbar sein
if (!this.popup.visible())
this.popup.clicked = false;
if (this.popup.clicked == true) {
this.popup.clicked = false;
this.popup.hide();
}
else {
this.popup.clicked = true;
if (!this.popup.visible())
this.popup.show();
}
OpenLayers.Event.stop(evt);
};
// Hover
var markerHover = function(evt) {
// Wenn das Popup nicht sichtbar ist, dann kann es nicht fest sichtbar sein
if (!this.popup.visible())
this.popup.clicked = false;
if (!this.popup.clicked)
this.popup.show();
OpenLayers.Event.stop(evt);
}
// Hover End
var markerHoverEnd = function(evt) {
if (!this.popup.clicked) {
this.popup.hide();
}
OpenLayers.Event.stop(evt);
}
// Events auf den Marker registrieren und als Objekt das Feature übergeben
marker.events.register("mousedown", feature, markerClick);
if (showPopupOnHover) {
marker.events.register("mouseover", feature, markerHover);
marker.events.register("mouseout", feature, markerHoverEnd);
}
// Erstellten Marker der Ebene hinzufügen
layer.addMarker(marker);
// Popup erstellen, der Karte hinzufügen und anzeigen, falls gewünscht
map.addPopup(feature.createPopup(feature.closeBox));
if (showPopupOnLoad != true) {
// Wenn das Popup nicht angezeigt werden soll, verstecken und auf 'nicht angeklickt' setzen
feature.popup.hide();
feature.popup.clicked = false;
} else {
// Das Popup wird direkt angezeigt und zwar solange bis man es explizit schließt
feature.popup.clicked = true;
}
return marker;
}
/*
*
* Creates a new marker icon
*
* using the icons-array (defined in the html-file)
*
* index
* 0 address to the image
* 1 width of the image
* 2 height
* 3 factor by which the image should be offset horizontally
* 4 factor by which the image should be offset vertically
*
* please see the icon array itself for examples of values
*/
function makeIcon(iconId) {
var size = new OpenLayers.Size(icons[iconId][1],icons[iconId][2]);
var offset = new OpenLayers.Pixel(-(size.w*icons[iconId][3]), -(size.h*icons[iconId][4]));
var icon = new OpenLayers.Icon(icons[iconId][0],size,offset);
return icon;
}
function getCycleTileURL(bounds) {
var res = this.map.getResolution();
var x = Math.round((bounds.left - this.maxExtent.left) / (res * this.tileSize.w));
var y = Math.round((this.maxExtent.top - bounds.top) / (res * this.tileSize.h));
var z = this.map.getZoom();
var limit = Math.pow(2, z);
if (y < 0 || y >= limit)
{
return null;
}
else
{
x = ((x % limit) + limit) % limit;
return this.url + z + "/" + x + "/" + y + "." + this.type;
}
}
/*
* Funktion zum Zerlegen der URL um die Parameter zu erhalten (für den Permalink)
* Splits the URL in its parameters
*/
function get_parameters() {
// erzeugt für jeden in der url übergebenen parameter einen wert
// bsp: x.htm?nachname=Munch&vorname=Alex&bildfile=wasserfall.jpg erzeugt
// variable nachname mit wert Munch und
// variable vorname mit wert Alex
// variable bildfile mit wert wasserfall.jpg
var hier = document.URL;
var parameterzeile = hier.substr((hier.indexOf("?")+1));
var trennpos;
var endpos;
var paramname;
var paramwert;
var parameters = new Object();
while (parameterzeile != "") {
trennpos = parameterzeile.indexOf("=");
endpos = parameterzeile.indexOf("&");
if (endpos < 0) { endpos = 500000; }
paramname = parameterzeile.substr(0,trennpos);
paramwert = parameterzeile.substring(trennpos+1,endpos);
parameters[paramname] = paramwert;
//eval (paramname + " = \"" + paramwert + "\"");
parameterzeile = parameterzeile.substr(endpos+1);
}
return parameters;
}
/*
* Wie der Name schon sagt ebenfalls für den Permalink, überprüft ob die Parameter in der URL gefunden wurden und überschreibt
* sie gegebenenfalls.
* Checks the url for parameters of the permalink and overwrites the default values if necessary.
*/
function checkForPermalink() {
var parameters = get_parameters();
if (parameters['zoom'] != null)
zoom = parseInt(parameters['zoom']);
if (parameters['lat'] != null)
lat = parseFloat(parameters['lat']);
if (parameters['lon'] != null)
lon = parseFloat(parameters['lon']);
}
/*
* Debugging Funktion
*/
function var_dump(obj) {
if(typeof obj == "object") {
return "Type: "+typeof(obj)+((obj.constructor) ? "\nConstructor: "+obj.constructor : "")+"\nValue: " + obj;
} else {
return "Type: "+typeof(obj)+"\nValue: "+obj;
}
}//end function var_dump
/*
* Für den Layer-Switcher mit Buttons
*/
function setLayer(id) {
if (document.getElementById("layer") != null) {
for (var i=0;i<layers.length;++i)
document.getElementById(layers[i][1]).className = "";
}
varName = layers[id][0];
name = layers[id][1];
map.setBaseLayer(varName);
if (document.getElementById("layer") != null)
document.getElementById(name).className = "active";
}
/*
* Schaltet die Beschreibung der Karte an- und aus.
* Toggles the description of the map.
*/
function toggleInfo() {
var state = document.getElementById('description').className;
if (state == 'hide') {
// Info anzeigen
document.getElementById('description').className = '';
document.getElementById('descriptionToggle').innerHTML = text[1];
}
else {
// Info verstecken
document.getElementById('description').className = 'hide';
document.getElementById('descriptionToggle').innerHTML = text[0];
}
}
function checkUtilVersion(version) {
var thisFileVersion = 3;
if (version != thisFileVersion) {
alert("map.html and util.js versions do not match.\n\nPlease reload the page using your browsers 'reload' feature.\n\nIf the problem persists and you are the owner of this site, you may need to update the map's files.");
}
}
Es gibt ungefähr 17 Arten, wie OpenLayers Marker setzt und Popups ausgibt. Du mischt zwei davon…
Man macht einen Layer mit OpenLayers.Layer.Markers() und setzt dort einzeln per JavaScript die Marker. Vorteil: Man hat massig Möglichkeiten, das Verhalten dieser Marker zu beeinflussen, wenn man sich viel Mühe gibt, hinter das System von OpenLayers zu steigen. Nachteil: Man muss jedes Mal an html/javascript ran, wenn ein neuer Marker dazukommt.
Zu diesem Verfahren gehört Deine utils.js mit den Funktionen addMarker…
Man macht einen Layer mit OpenLayers.Layer.GML() oder OpenLayers.Layer.Text(), der frisst eine externe Datei (gpx, kml, text), malt die Marker und kümmert sich um den Rest selber (z.B. das das alte Popup zugeht, wenn ein neues aufgeht). Vorteil: Man muss nur diese externe Datei ändern. Nachteil: Man muss sich nicht so viel mit OpenLayers rumschlagen.
Zu diesem Verfahren gehören Deine ganzen angelegten Layer. Und mein Beispiel aus Antwort #1.
Du kannst entweder mit der OpenLayers.Layer.GML-Variante weitermachen, dann kannst Du z.B. das Zeug aus diesem Thread kopieren (da gabs eine KML-Datei mit Popup und Kreuz zum schliessen).
Oder Du kannst mit OpenLayers.Layer.Markers weitermachen, dann kannst Du diese YinYang-Karte abkupfern.
Das erste finde ich ganz sinnvoll. Und es zeigt, dass das [x] dann gut ist, wenn sich der blöde Popup über den Marker legt (bei Venedig und Zürich zu sehn), weil dann kommt die Maus nicht mehr an den Marker ran zum zuklicken.
Beim zweiten sieht man, dass Du kein [x] brauchst, wenn Du Mausover machst, das Popup geht zu, wenn Du aus dem Marker fährst, noch bevor Du das Kreuz erreichst. Ausserdem sollte man bisschen Abstand zwischen Marker und Popup lassen, weil sonst gibts lustige Blinkeffekte…
hi,
es wird für “neue” projekte angeraten, auf Layer.Markers zu verzichten und gleich Layers.Vector zu benutzen. Das erschlägt Markers mit.
gruss
walter
sind einige kleine beispiele drin. aber mit “so auf die schnelle” ist bei OL sowieso nix zu machen. der aufruf ist aber fast identisch mit markers. hab ich nie benutzt, , da ich gleich mit vector angefangen habe.
aber was ich nicht verstehe ich müsste doch mit hilfe der until.js die popups
feature.popupClass = OpenLayers.Class(OpenLayers.Popup.AnchoredBubble, {minSize: new OpenLayers.Size(700, 520) } ); .
verändern können, aber da tut sich nix oder bin ich an der falschen stelle? (das war normal framedcloud und die size war auch viel kleiner.) oder hab ich irgendwo ein denkfehler? weil 100% verstehe ich den code nicht den ich nutzte…
(einiges aus util.js rausgeworfen, addMarker() ins html geschreiben, zwei Beispiellayer und 6 POIs angelegt, die grösse des Popups bestimmt der Inhalt, z.B. bei der Ev.Kirche zu sehen. Du musst noch den Rest Deiner Marker eintragen, die weiteren Layers für Gastronomie usw. und Dir schönere Icons für die Marker suchen…)
Is halt jetzt echt quick&dirty-Programmierung. Weder Du noch ich verstehen alles was in util.js drin ist und stochern ziemlich im Nebel. Ganz rausschmeissen können wir util.js nicht, weil dort z.B. auch die Permalink-Geschichte abgefragt wird.
Das ist irgendwie kein schöner Anfang für ein Projekt, ich würde mich an wambachers Vektoren halten…
Ich hab jetzt http://kulturverein-storndorf.de/karten/ort/ mal angelegt. (marker und so müssen noch überarbeitet werden…) Die Entscheidung für was sich entschieden wird liegt nicht in meinen händen, aber so das müsste erstmal reichen.
Mir ist etwas unschönes aufgefallen. Hält man den Mauszeiger über eine Marke, pop der Text auf. Befindet sich jetzt der Zeiger im Bereich des Textes und der Marke (also wenn sich die 2 Bereiche überlappen), dann flakert der Text sehr stark. Entweder dürfen sich die beiden Bereiche nicht überlappen oder der Text darf den Hover über der Marke nicht aufheben. Wie das mit dem Hover nicht aufheben geht, weiss ich nicht, würde es aber ebenso gerne wissen.
Nur wegen der Schönheit würde ich den weissen Hintergrund des Textes etwas verkleinern (falls möglich).