-
Notifications
You must be signed in to change notification settings - Fork 18
Enable drawing mode
Before starting this tutorial, I recommend going through the Enable edit mode page, as this is required for the drawing mode to work.
Please note that this feature is still in development.
The files used for csMap are located in the Development-edit branch and the files for csWeb in the Development branch.
We need to make changes to both csWeb and csMap in order to enable this functionality. Please follow these steps:
1 The following files have been changed for this feature, please copy them:
- directives/FeatureTypes/FeatureTypes.tpl.html
- directives/FeatureTypes/FeatureTypesCtrl.ts
- directives/PropertyTypes/PropertyTypes.tpl.html
- directives/PropertyTypes/PropertyTypesCtrl.ts
- directives/LayersList/LayersDirective.tpl.html
- directives/LayersList/LayersDirectiveCtrl.ts
1 Add the interface IDrawTypes
javascript
export interface IDrawTypes {
name : string;
drawingMode : string;
iconUri : string;
description : string;
}
2 Add these variables in the IMapLayersScope
```javascript
drawItems: IDrawTypes[];
selectedFeatureLayer: string;
initDrawMode: boolean;
3 Add these dependencies in the $inject variable
'messageBusService',
'layerService'
4 And add this in the constructor of the class
private $messageBusService : csComp.Services.MessageBusService,
private $layerService : csComp.Services.LayerService
and
$scope.selectedFeatureLayer = '';
$scope.initDrawMode = false;
this.$messageBusService.subscribe("drawmode", this.drawModeMessageReceived);
5 Finally add these methods to finish the MapCtrl.ts
/**
* Enables of disables the Leaflet.Draw toolbar depending on the received message
*/
private drawModeMessageReceived = (title: string): void => {
if (!this.$scope.initDrawMode) {
// Get all the features
var drawTypes = this.updateDrawTypes();
// Add the items to the (current) map layer
this.$mapService.initDrawableMap(drawTypes);
this.$scope.initDrawMode = true;
}
if (title !== '') {
if (this.$scope.selectedFeatureLayer != '' && title != this.$scope.selectedFeatureLayer) {
// Remove the Leaflet.Draw from the layer if it exists
this.$mapService.disableDrawableMap();
}
// Show the Leaflet.Draw toolbar
this.$mapService.enableDrawableMap(drawTypes);
} else {
// Remove the Leaflet.Draw toolbar
this.$mapService.disableDrawableMap();
}
this.$scope.selectedFeatureLayer = title;
// NOTE EV: You need to call apply only when an event is received outside the angular scope.
// However, make sure you are not calling this inside an angular apply cycle, as it will generate an error.
if (this.$scope.$root.$$phase != '$apply' && this.$scope.$root.$$phase != '$digest') {
this.$scope.$apply();
}
}
private updateDrawTypes() {
var drawItems: Array<IDrawTypes> = [];
var existingItems: Array<String> = [];
for (var key in this.$layerService.featureTypes) {
var ft = this.$layerService.featureTypes[key];
var name = this.getName(key, ft);
var drawingMode = ft.style.drawingMode;
var iconUri = this.getImageUri(ft);
var description = 'Klik op het icoon om een nieuw ' + name + ' aan te maken.';
this.injectIconCSS(name, iconUri);
var existingItem = name;
if (existingItems.indexOf(existingItem) < 0) {
existingItems.push(existingItem);
drawItems.push({
"name": name,
"drawingMode": drawingMode,
"iconUri": iconUri,
"description": description
});
}
}
drawItems.sort((a: IDrawTypes, b: IDrawTypes) => {
if (a.name > b.name) return 1;
if (a.name < b.name) return -1;
return 0;
});
return drawItems;
}
private getImageUri(ft: csComp.Services.IFeatureType): string {
if (ft.style != null && ft.style.drawingMode != null && ft.style.drawingMode.toLowerCase() != "point") {
if (ft.style.iconUri && ft.style.iconUri.indexOf('_Media') < 0)
return ft.style.iconUri;
else
return "includes/images/polygon.png";
}
else if (ft.style != null && ft.style.iconUri != null) {
return ft.style.iconUri;
}
else {
return "includes/images/marker.png";
}
}
private getName(key: string, ft: csComp.Services.IFeatureType): string {
if (ft.name != null) {
return ft.name;
}
else {
return key;
}
}
private injectIconCSS(name, iconUri) {
var t = "{\"." + name.replace(/\s+/g, '-').toLowerCase() + "\":";
if (iconUri != null) {
t += " { \"background-image\": \"url('" + iconUri + "') !important\",";
};
t += " \"background-size\": \"20px 20px\",\"background-color\": \"#fff !important\",\"border-style\": \"none\"} }";
var json = $.parseJSON(t);
(<any>$).injectCSS(json);
}
1 Add the following variables to MapService.ts
private drawControl: any;
private drawnItems: any;
2 Add the following code to MapService.ts
/**
* Generates the Leaflet.Draw toolbar with the features
*/
public initDrawableMap(drawTypes) {
this.drawnItems = L.featureGroup().addTo(this.map);
// Generate the ModeHandlers for the features
this.setModeHandlers(drawTypes);
// Draws the control panel object
this.drawControl = new (<any>L).Control.Draw({
edit: { featureGroup: this.drawnItems },
position: 'bottomleft'
});
// Listener for when a item gets created
this.map.on('draw:created', function (event) {
this.saveDrawnItem(event);
console.log(event);
}.bind(this));
}
/**
* Shows the Leaflet.Draw toolbar
*/
public enableDrawableMap(drawTypes) {
this.map.addControl(this.drawControl);
}
/**
* Disables the Leaflet.Draw toolbar
*/
public disableDrawableMap() {
this.map.removeControl(this.drawControl);
}
/**
* Gets called upon when an item gets drawed by the user
*/
public saveDrawnItem(item) {
var layer = item.layer;
var type = item.layerType;
this.drawnItems.addLayer(layer);
// TODO: Identify item and save values
// TODO: Open sidebar with available properties
}
/**
* Overwrite the default Leaflet.Draw mode handlers with the features mode handlers
*/
public setModeHandlers(drawTypes) {
(<any>L).DrawToolbar.include({
getModeHandlers: function (map) {
var modeHandlers = [];
for (feature in drawTypes) {
var feature = drawTypes[feature];
var drawingMode = undefined;
// Add more drawing types here when they become available
switch (feature.drawingMode) {
case ('Point'):
drawingMode = new (<any>L).Draw.Marker(map);
break;
case ('Polygon'):
drawingMode = new (<any>L).Draw.Polygon(map);
break;
}
var modeHandler = {
enabled: true,
handler: drawingMode,
title: feature.description,
name: feature.name
}
modeHandlers.push(modeHandler);
}
return modeHandlers;
}
});
}
Don't forget to recompile the project with Visual Studio!
1 Add the following code to bower.json under "dependencies"
"leaflet-draw": "~0.2.3"
2 Add the following code to index.html
<link href="bower_components/leaflet-draw/dist/leaflet.draw.css" rel="stylesheet" />
<script src="js/cs/leaflet.draw.js"></script>
3 Add the following code to css/style.css
.selectedFeature {
color: #0097cf;
}
4 Add the js/cs/leaflet.draw.js file to your project
5 In order to wrap things up in csMap you need to run bower install
in your terminal