2016-10-19 4 views
1

Ich habe eine OpenLayers 2-Kartenanwendung auf OpenLayers 3 umgestellt. Die Karte besteht aus zwei Gruppenebenen (Basiskarten und Overlays), die im Javascript-Code definiert sind. Wenn die Seite jedoch geladen (oder automatisch aktualisiert) wird, liest sie eine XML-Datei und lädt Layer von Features dynamisch in die Map.OpenLayers 3 removeLayer Fehler?

Dieser Teil funktioniert alles gut. Woran ich ein Problem habe, ist die Routine, die als Teil der automatischen Aktualisierungsfunktion der Seite alle dynamisch hinzugefügten Ebenen entfernen soll.

Mein ursprünglicher Code:

function erase_and_reload(){ 
 
\t \t console.log("erase_and_reload has fired!"); 
 
\t \t map.getLayers().forEach(function(layer){ 
 
\t \t \t console.log("Existing layer that needs to be removed ?:"); 
 
\t \t \t console.log(layer); 
 
\t \t \t 
 
\t \t \t var name = layer.get('name'); 
 
\t \t \t var title = layer.get('title'); 
 
\t \t \t console.log("layer name = " + name + " layer title = " + title); 
 
      
 
\t \t \t if (name){ 
 
\t \t \t \t console.log("Found layer named = " + name); 
 
\t \t \t \t console.log("Removing layer named: " + name); 
 
\t \t \t \t map.removeLayer(layer); 
 
\t \t \t } 
 
\t \t \t 
 
\t \t \t 
 
\t \t }); 
 

 
// reload 
 
\t read_WW_xml(); 
 
}

(. Ja, ich habe hier ein Protokoll der console.log Einträge bekam, um zu versuchen, Dinge herauszufinden)

So , wenn ich das so wie es ist ... der Protokolleintrag von "vorhandener Layer, der entfernt werden muss?" wird 10 mal geschrieben und zeigt mir an, dass es 10 Schichten gibt. Wenn ich mir die Layer-Objekte anschaue, sehe ich die Base Maps, die Overlays und einige andere. Bestimmte andere Layer, die tatsächlich "name" -Eigenschaften haben, fehlen jedoch vollständig.

Aber wenn ich dies mit der Zeile "map.removeLayer (layer)" auskommentiert habe, jetzt, dass "Existing layer" Zeile 17 Mal geschrieben wird! Sieben weitere Ebenenobjekte werden angezeigt!

(FYI: Der Ausdruck "title" ist immer noch da, weil ich zuerst dachte, das Problem habe etwas mit der Eigenschaft 'name' zu tun, also habe ich stattdessen versucht, die Eigenschaft 'title' abzugleichen. ". wenn der Titel nicht ist‚Basiskarten‘oder‚Overlays‘, dann removeLayer. Aber das genau die gleiche Art und Weise verhalten hat.)

Auch wenn .removeLayer versagt die Schicht zu entfernen, ich denke, ich bin nicht sicher, warum ist das alles irgendwie Abbruch der Schleife für 7 Iterationen ... bis zu dem Punkt, wo es nicht einmal die ersten beiden console.logs schreiben ??

Dank!

- = Dave = -

+0

Haben Sie versuchen, 'map.getOverlays() zu verwenden, klar();' und 'map.getLayers(). clear();'? – Sefran2

+0

Es sieht so aus, als wenn ich "layer.getSource(). Clear();" .... aber Layer mit den Titeln "Base maps" und "Overlays" umblättere (die also ihre verschachtelten Layer umgehen) ... das scheint die Features von jeder Ebene zum Neuzeichnen effektiv zu löschen. ABER, ob eine bestimmte dynamisch gespeiste Ebene bei der nächsten Seitenaktualisierung benötigt wird oder nicht, kann sich ändern. Also, wenn ich dieses Ding für ein paar Tage laufen lasse, könnte es eine Ansammlung von unnötigen Schichten geben. Ich wünschte, der removeLayer würde funktionieren! – DaveyBoy

Antwort

3

Es ist nicht wirklich jene 7 Iterationen abbrechen, überspringt es nur diese Array-Elemente.

In Ihrem forEach-Zyklus gibt es eine Reihe von Referenzen auf Kartenebenen. Wenn Sie ein Element dieses Arrays nehmen (Referenz ist "Layer") und es aus der Map entfernen, entfernen Sie den Verweis, so dass er weder in der Map noch in Ihrem Array mehr vorhanden ist und versehentlich eine andere Referenz darauf existiert Index.

Also, wenn Sie Array:

0: Layer0, name "Layer0"

1: layer1, name "layer1"

2: Layer2

nach diesem forEach wird es bleiben

0: layer1, name "layer1"

1: layer2

weil nach dem Entfernen von Schicht0, ist Schicht1 auf dem Index 0 und AFTER dass forEach entlang (zum Index 1) bewegt, wo es bereits Schicht ohne Namen findet.

Um das zu lösen, nur Funktionen getArray() und slice() (das Referenzfeld kopieren), dass so etwas wie:.

var refArray = map.getLayers().getArray().slice(); 
ref.forEach(function(layer) 
{ 
    //your stuff 
} 
+0

Das scheint zu funktionieren! Vielen Dank für die Erklärung! – DaveyBoy

0

Sie könnten versuchen,

function erase_and_reload(){ 
    map.getOverlays().clear(); 
    map.getLayers().clear(); 

    // reload 
    read_WW_xml(); 
} 
+0

Nun, ich möchte lieber keine Ressourcen verschwenden, die die Base Map Layergroup und die Overlays Layergroup neu zeichnen. Das wird sich nicht ändern. map.getLayers(). Clear() scheint alle Ebenen zu löschen ... alles .... – DaveyBoy