LayerControl class
class LayerControl extends MapControl { static const _TEMPLATE = """ <div class="layer-control"> <table> </table> </div> """; LayerControl([MapViewport map]) : super(map); final Map<int, StreamSubscription> _layerSubscriptions = new Map<int, StreamSubscription>(); static const _ROW_TEMPLATE = """ <tr> <td class="layer-visibility"><input type="checkbox"></td> <td class="layer-name"><span title=""></span></td> </tr> """; void detach() { super.detach(); _layerSubscriptions.keys.forEach((id) { _layerSubscriptions[id].cancel(); }); _layerSubscriptions.clear(); } Element _buildLayerRow(Layer layer) { //TODO: replace with a kind of builder. Element.html will probably disapear var tr = new Element.html(_ROW_TEMPLATE); var span = tr.query("td.layer-name").query("span"); span.innerHtml = layer.name; span.attributes["title"] = layer.name; // tooltip var cb = tr.query("input"); _cbSetChecked(cb, layer.visible); cb.dataset["layerId"] = layer.id.toString(); tr.dataset["layerId"] = layer.id.toString(); return tr; } _buildHtml() { _root = new Element.html(_TEMPLATE); var size = _map.viewportSize; var left = size.width - 20 - 200; _root.style ..left = "${left}px" ..top = "20px"; var rows = _map.layers.map((l) => _buildLayerRow(l)); _root.query("table").children ..clear() ..addAll(rows); } _wireEventListeners() { // click events in the layer control _subscriptions.add( _root.onClick.listen(_handleClick) ); // layer events (add, remove, move) in the map viewport _subscriptions.add( _map.onLayersChanged.listen(_handleLayerEvent) ); // layer properties (name, visible) in a layer _map.layers.forEach((l) { _layerSubscriptions[l.id] = l.onPropertyChanged.listen(_handleLayerPropertyChange); }); } _handleClick(evt) { var target = evt.target; if (evt.target is InputElement) { _toggleLayerVisibility(evt); } } _layerTr(lid) => _root .queryAll("tr") .firstWhere((e)=>e.dataset["layerId"] == lid.toString()); _handleLayerEvent(LayerEvent evt) { handleAdded(LayerEvent evt) { var tr = _buildLayerRow(evt.layer); _root.query("table").children.add(tr); _layerSubscriptions[evt.layer.id] = evt.layer.onPropertyChanged.listen(_handleLayerPropertyChange); } handleRemoved(LayerEvent evt) { var lid = evt.layer.id; var tr = _layerTr(lid); if (tr == null) { print("warning: didn't find table row for layer with id $lid"); return; } var table = _root.query("table"); table.children.remove(tr); var subscription = _layerSubscriptions[lid]; if (subscription != null) { subscription.cancel(); } } switch(evt.type) { case LayerEvent.ADDED: handleAdded(evt); break; case LayerEvent.REMOVED: handleRemoved(evt); break; default: /* ignore */ } } _cbSetChecked(cb, value) { if (value) { cb.attributes["checked"] = "checked"; } else { cb.attributes.remove("checked"); } } _handleLayerPropertyChange(evt) { handleNameChange(evt) { var lid = evt.source.id; var span = _layerTr(lid).query("span"); span.innerHtml = evt.newValue; } handleVisibleChange(evt) { var lid = evt.source.id; var cb = _layerTr(lid).query("input"); _cbSetChecked(cb, evt.newValue); } switch(evt.name) { case "name": handleNameChange(evt); break; case "visible": handleVisibleChange(evt);break; default: /* ignore */ } } _toggleLayerVisibility(evt) { if (evt.target is! InputElement) return; var cb = evt.target; var lid = cb.dataset["layerId"]; if (lid == null) return; //TODO: warning try { lid = int.parse(lid); } catch(e) { //TODO: warning return; } var layer = _map.layers.firstWhere((l) => l.id == lid); if (layer == null) { //TODO: warning return; } var visible = !layer.visible; layer.visible = visible; } @override void build() { _buildHtml(); _wireEventListeners(); } var _defaultPosition = null; @override get defaultPosition { if (_defaultPosition == null && map != null) { var vs = map.viewportSize; _defaultPosition = new Point2D(vs.width-200, 20); } return _defaultPosition; } }
Extends
MapControl > LayerControl
Constructors
new LayerControl([MapViewport map]) #
LayerControl([MapViewport map]) : super(map);
Properties
final defaultPosition #
the default position of the control if no position has been
set explicitly using placeAt
.
Override in subclasses.
docs inherited from MapControl
@override get defaultPosition { if (_defaultPosition == null && map != null) { var vs = map.viewportSize; _defaultPosition = new Point2D(vs.width-200, 20); } return _defaultPosition; }
final MapViewport map #
inherited from MapControl
the map this control is attached to, or null
MapViewport get map => _map;
final Element root #
inherited from MapControl
the root DOM element for this map control
Element get root => _root;
Methods
void applyPosition() #
inherited from MapControl
Applies the current position to the appropriate DOM element.
void applyPosition() { if (root == null) return; var pos = _position == null ? defaultPosition : _position; if (pos == null) { //TODO: log a warning ? return; } root.style ..left = "${pos.x}px" ..top = "${pos.y}px"; }
void attach(MapViewport viewport) #
inherited from MapControl
Attaches this control to the map viewport.
void attach(MapViewport viewport) { _require(viewport != null, "viewport must not be null"); // already attached ? if (_map != null) { if (_map == viewport) { return; // don't attach again } else { detach(); // detach the currently attached, then attach the new one } } this._map = viewport; var controlsPane = _map.controlsPane; //TODO: log a warning? if (controlsPane == null) return; build(); controlsPane.controls.add(this); controlsPane.root.children.add(root); applyPosition(); }
void build() #
Abstract method which builds the DOM tree for the control. Override in subclasses.
docs inherited from MapControl
@override void build() { _buildHtml(); _wireEventListeners(); }
void detach() #
Detaches this control from the map viewport it is currently attached to (if any).
docs inherited from MapControl
void detach() { super.detach(); _layerSubscriptions.keys.forEach((id) { _layerSubscriptions[id].cancel(); }); _layerSubscriptions.clear(); }
void layout() #
inherited from MapControl
Invoke this to force to (re-)layout the map control in the current map viewport.
void layout() {}
void placeAt(int x, int y) #
inherited from MapControl
Places the control at the position ( x, y).
void placeAt(int x, int y) { _position = new Point2D(x,y); applyPosition(); }