Skip to content

Commit

Permalink
fix: re-add sources and layers after style change
Browse files Browse the repository at this point in the history
fix #43
  • Loading branch information
Wykks committed Aug 4, 2018
1 parent 69739bf commit 4c49629
Show file tree
Hide file tree
Showing 8 changed files with 198 additions and 101 deletions.
58 changes: 37 additions & 21 deletions projects/ngx-mapbox-gl/src/lib/layer/layer.component.ts
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,8 @@ import {
VectorSource,
VideoSource
} from 'mapbox-gl';
import { fromEvent, Subscription } from 'rxjs';
import { filter } from 'rxjs/operators';
import { MapService } from '../map/map.service';

@Component({
Expand Down Expand Up @@ -60,34 +62,20 @@ export class LayerComponent implements OnInit, OnDestroy, OnChanges, Layer {
@Output() mouseMove = new EventEmitter<MapMouseEvent>();

private layerAdded = false;
private sub: Subscription;

constructor(
private MapService: MapService
) { }

ngOnInit() {
this.MapService.mapLoaded$.subscribe(() => {
this.MapService.addLayer({
layerOptions: {
id: this.id,
type: this.type,
source: this.source,
metadata: this.metadata,
'source-layer': this.sourceLayer,
minzoom: this.minzoom,
maxzoom: this.maxzoom,
filter: this.filter,
layout: this.layout,
paint: this.paint
},
layerEvents: {
click: this.click,
mouseEnter: this.mouseEnter,
mouseLeave: this.mouseLeave,
mouseMove: this.mouseMove
}
}, this.before);
this.layerAdded = true;
this.init(true);
this.sub = fromEvent(this.MapService.mapInstance, 'styledata').pipe(
filter(() => !this.MapService.mapInstance.getLayer(this.id))
).subscribe(() => {
this.init(false);
});
});
}

Expand Down Expand Up @@ -119,5 +107,33 @@ export class LayerComponent implements OnInit, OnDestroy, OnChanges, Layer {
if (this.layerAdded) {
this.MapService.removeLayer(this.id);
}
if (this.sub) {
this.sub.unsubscribe();
}
}

private init(bindEvents: boolean) {
const layer = {
layerOptions: {
id: this.id,
type: this.type,
source: this.source,
metadata: this.metadata,
'source-layer': this.sourceLayer,
minzoom: this.minzoom,
maxzoom: this.maxzoom,
filter: this.filter,
layout: this.layout,
paint: this.paint
},
layerEvents: {
click: this.click,
mouseEnter: this.mouseEnter,
mouseLeave: this.mouseLeave,
mouseMove: this.mouseMove
}
};
this.MapService.addLayer(layer, bindEvents, this.before);
this.layerAdded = true;
}
}
50 changes: 26 additions & 24 deletions projects/ngx-mapbox-gl/src/lib/map/map.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -217,7 +217,7 @@ export class MapService {
});
}

addLayer(layer: SetupLayer, before?: string) {
addLayer(layer: SetupLayer, bindEvents: boolean, before?: string) {
this.zone.runOutsideAngular(() => {
Object.keys(layer.layerOptions)
.forEach((key: string) => {
Expand All @@ -227,33 +227,35 @@ export class MapService {
}
});
this.mapInstance.addLayer(layer.layerOptions, before);
if (layer.layerEvents.click.observers.length) {
this.mapInstance.on('click', layer.layerOptions.id, (evt: MapboxGl.MapMouseEvent) => {
this.zone.run(() => {
layer.layerEvents.click.emit(evt);
if (bindEvents) {
if (layer.layerEvents.click.observers.length) {
this.mapInstance.on('click', layer.layerOptions.id, (evt: MapboxGl.MapMouseEvent) => {
this.zone.run(() => {
layer.layerEvents.click.emit(evt);
});
});
});
}
if (layer.layerEvents.mouseEnter.observers.length) {
this.mapInstance.on('mouseenter', layer.layerOptions.id, (evt: MapboxGl.MapMouseEvent) => {
this.zone.run(() => {
layer.layerEvents.mouseEnter.emit(evt);
}
if (layer.layerEvents.mouseEnter.observers.length) {
this.mapInstance.on('mouseenter', layer.layerOptions.id, (evt: MapboxGl.MapMouseEvent) => {
this.zone.run(() => {
layer.layerEvents.mouseEnter.emit(evt);
});
});
});
}
if (layer.layerEvents.mouseLeave.observers.length) {
this.mapInstance.on('mouseleave', layer.layerOptions.id, (evt: MapboxGl.MapMouseEvent) => {
this.zone.run(() => {
layer.layerEvents.mouseLeave.emit(evt);
}
if (layer.layerEvents.mouseLeave.observers.length) {
this.mapInstance.on('mouseleave', layer.layerOptions.id, (evt: MapboxGl.MapMouseEvent) => {
this.zone.run(() => {
layer.layerEvents.mouseLeave.emit(evt);
});
});
});
}
if (layer.layerEvents.mouseMove.observers.length) {
this.mapInstance.on('mousemove', layer.layerOptions.id, (evt: MapboxGl.MapMouseEvent) => {
this.zone.run(() => {
layer.layerEvents.mouseMove.emit(evt);
}
if (layer.layerEvents.mouseMove.observers.length) {
this.mapInstance.on('mousemove', layer.layerOptions.id, (evt: MapboxGl.MapMouseEvent) => {
this.zone.run(() => {
layer.layerEvents.mouseMove.emit(evt);
});
});
});
}
}
});
}
Expand Down
30 changes: 22 additions & 8 deletions projects/ngx-mapbox-gl/src/lib/source/canvas-source.component.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
import { ChangeDetectionStrategy, Component, Input, OnChanges, OnDestroy, OnInit, SimpleChanges } from '@angular/core';
import { CanvasSourceOptions } from 'mapbox-gl';
import { fromEvent, Subscription } from 'rxjs';
import { filter } from 'rxjs/operators';
import { MapService } from '../map/map.service';

@Component({
Expand All @@ -17,21 +19,21 @@ export class CanvasSourceComponent implements OnInit, OnDestroy, OnChanges, Canv
@Input() animate?: boolean;

private sourceAdded = false;
private sub = new Subscription();

constructor(
private MapService: MapService
) { }

ngOnInit() {
this.MapService.mapLoaded$.subscribe(() => {
const source = {
type: 'canvas',
coordinates: this.coordinates,
canvas: this.canvas,
animate: this.animate,
};
this.MapService.addSource(this.id, source);
this.sourceAdded = true;
this.init();
const sub = fromEvent(this.MapService.mapInstance, 'styledata').pipe(
filter(() => !this.MapService.mapInstance.getSource(this.id))
).subscribe(() => {
this.init();
});
this.sub.add(sub);
});
}

Expand All @@ -50,8 +52,20 @@ export class CanvasSourceComponent implements OnInit, OnDestroy, OnChanges, Canv
}

ngOnDestroy() {
this.sub.unsubscribe();
if (this.sourceAdded) {
this.MapService.removeSource(this.id);
}
}

private init() {
const source = {
type: 'canvas',
coordinates: this.coordinates,
canvas: this.canvas,
animate: this.animate,
};
this.MapService.addSource(this.id, source);
this.sourceAdded = true;
}
}
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { ChangeDetectionStrategy, Component, Input, OnChanges, OnDestroy, OnInit, SimpleChanges } from '@angular/core';
import { GeoJSONGeometry, GeoJSONSource, GeoJSONSourceOptions } from 'mapbox-gl';
import { Subject, Subscription } from 'rxjs';
import { debounceTime } from 'rxjs/operators';
import { fromEvent, Subject, Subscription } from 'rxjs';
import { debounceTime, filter } from 'rxjs/operators';
import { MapService } from '../../map/map.service';

@Component({
Expand All @@ -25,7 +25,7 @@ export class GeoJSONSourceComponent implements OnInit, OnDestroy, OnChanges, Geo

updateFeatureData = new Subject();

private sub: Subscription;
private sub = new Subscription();
private sourceAdded = false;
private featureIdCounter = 0;

Expand All @@ -41,24 +41,13 @@ export class GeoJSONSourceComponent implements OnInit, OnDestroy, OnChanges, Geo
};
}
this.MapService.mapLoaded$.subscribe(() => {
this.MapService.addSource(this.id, {
type: 'geojson',
data: this.data,
maxzoom: this.maxzoom,
minzoom: this.minzoom,
buffer: this.buffer,
tolerance: this.tolerance,
cluster: this.cluster,
clusterRadius: this.clusterRadius,
clusterMaxZoom: this.clusterMaxZoom,
});
this.sub = this.updateFeatureData.pipe(
debounceTime(0)
this.init();
const sub = fromEvent(this.MapService.mapInstance, 'styledata').pipe(
filter(() => !this.MapService.mapInstance.getSource(this.id))
).subscribe(() => {
const source = this.MapService.getSource<GeoJSONSource>(this.id);
source.setData(this.data!);
this.init();
});
this.sourceAdded = true;
this.sub.add(sub);
});
}

Expand All @@ -85,8 +74,8 @@ export class GeoJSONSourceComponent implements OnInit, OnDestroy, OnChanges, Geo
}

ngOnDestroy() {
this.sub.unsubscribe();
if (this.sourceAdded) {
this.sub.unsubscribe();
this.MapService.removeSource(this.id);
}
}
Expand All @@ -109,4 +98,24 @@ export class GeoJSONSourceComponent implements OnInit, OnDestroy, OnChanges, Geo
getNewFeatureId() {
return ++this.featureIdCounter;
}

private init() {
this.MapService.addSource(this.id, {
type: 'geojson',
data: this.data,
maxzoom: this.maxzoom,
minzoom: this.minzoom,
buffer: this.buffer,
tolerance: this.tolerance,
cluster: this.cluster,
clusterRadius: this.clusterRadius,
clusterMaxZoom: this.clusterMaxZoom,
});
const sub = this.updateFeatureData.pipe(debounceTime(0)).subscribe(() => {
const source = this.MapService.getSource<GeoJSONSource>(this.id);
source.setData(this.data!);
});
this.sub.add(sub);
this.sourceAdded = true;
}
}
24 changes: 19 additions & 5 deletions projects/ngx-mapbox-gl/src/lib/source/image-source.component.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
import { ChangeDetectionStrategy, Component, Input, OnChanges, OnDestroy, OnInit, SimpleChanges } from '@angular/core';
import { ImageSourceOptions } from 'mapbox-gl';
import { fromEvent, Subscription } from 'rxjs';
import { filter } from 'rxjs/operators';
import { MapService } from '../map/map.service';

@Component({
Expand All @@ -16,19 +18,21 @@ export class ImageSourceComponent implements OnInit, OnDestroy, OnChanges, Image
@Input() coordinates: number[][];

private sourceAdded = false;
private sub = new Subscription();

constructor(
private MapService: MapService
) { }

ngOnInit() {
this.MapService.mapLoaded$.subscribe(() => {
this.MapService.addSource(this.id, {
type: 'image',
url: this.url,
coordinates: this.coordinates
this.init();
const sub = fromEvent(this.MapService.mapInstance, 'styledata').pipe(
filter(() => !this.MapService.mapInstance.getSource(this.id))
).subscribe(() => {
this.init();
});
this.sourceAdded = true;
this.sub.add(sub);
});
}

Expand All @@ -46,8 +50,18 @@ export class ImageSourceComponent implements OnInit, OnDestroy, OnChanges, Image
}

ngOnDestroy() {
this.sub.unsubscribe();
if (this.sourceAdded) {
this.MapService.removeSource(this.id);
}
}

private init() {
this.MapService.addSource(this.id, {
type: 'image',
url: this.url,
coordinates: this.coordinates
});
this.sourceAdded = true;
}
}
Loading

0 comments on commit 4c49629

Please sign in to comment.