diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 3fd1ee5a..6524ac4e 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -89,7 +89,7 @@ Software development life-cycle ------------------------------- There are a some Grunt tasks defined to ease the development cycle. Let's see how to use them: -First, make sure you have npm and grunt-cli installed globally. Let's install the dependencies. +First, make sure you have npm, bower and grunt-cli installed globally. Let's install the dependencies. ``` # Inside the project dir, install the dependencies @@ -110,6 +110,17 @@ npm http GET https://registry.npmjs.org/grunt-ngmin ├── useragent@2.0.7 (lru-cache@2.2.4) ├── connect@2.8.8 (methods@0.0.1, uid2@0.0.2, fresh@0.2.0, cookie@0.1.0, ..., send@0.1.4) └── socket.io@0.9.16 (base64id@0.1.0, policyfile@0.0.4, redis@0.7.3, socket.io-client@0.9.16) +... +$ bower install +... +bower jquery#* install jquery#3.2.1 +bower angular#1.4.9 install angular#1.4.9 +bower angular-sanitize#1.4.9 install angular-sanitize#1.4.9 +bower js-polyfills#^0.1.20 install js-polyfills#0.1.34 +bower angular-mocks#1.4.9 install angular-mocks#1.4.9 +bower angular-route#1.4.9 install angular-route#1.4.9 +bower openlayers#* install openlayers#e-tag:a8ff409d6 +... $ ``` diff --git a/dist/angular-openlayers-directive.js b/dist/angular-openlayers-directive.js index ad957872..9f401332 100644 --- a/dist/angular-openlayers-directive.js +++ b/dist/angular-openlayers-directive.js @@ -1936,11 +1936,41 @@ angular.module('openlayers-directive').factory('olHelpers', ["$q", "$log", "$htt var createAttribution = function(source) { var attributions = []; if (isDefined(source.attribution)) { - attributions.unshift(new ol.Attribution({html: source.attribution})); + // opt-out -> default tries to show an attribution + if (!(source.attribution === false)) { // jshint ignore:line + // we got some HTML so display that as the attribution + attributions.unshift(new ol.Attribution({html: source.attribution})); + } + } else { + // try to infer automatically + var attrib = extractAttributionFromSource(source); + if (attrib) { + attributions.unshift(attrib); + } } + return attributions; }; + var extractAttributionFromSource = function(source) { + if (source && source.type) { + var ol3SourceInstance = ol.source[source.type]; + if (ol3SourceInstance) { + // iterate over the object's props and try + // to find the attribution one as it differs + for (var prop in ol3SourceInstance) { + if (ol3SourceInstance.hasOwnProperty(prop)) { + if (prop.toLowerCase().indexOf('attribution') > -1) { + return ol.source[source.type][prop]; + } + } + } + } + } + + return null; + }; + var createGroup = function(name) { var olGroup = new ol.layer.Group(); olGroup.set('name', name); diff --git a/dist/angular-openlayers-directive.min.js b/dist/angular-openlayers-directive.min.js index 00996b23..ba20c654 100644 --- a/dist/angular-openlayers-directive.min.js +++ b/dist/angular-openlayers-directive.min.js @@ -27,6 +27,6 @@ * @authors https://github.com/tombatossals/angular-openlayers-directive/graphs/contributors */ -/*! angular-openlayers-directive 24-03-2017 */ -!function(a,b){if("function"==typeof require&&"object"==typeof exports){var c=require("openlayers");exports.angularOpenlayersDirective=b(c)}else"function"==typeof define&&define.amd?define(["ol"],function(c){return a.angularOpenlayersDirective=b(c)}):a.angularOpenlayersDirective=b(a.ol)}(this,function(a){angular.module("openlayers-directive",["ngSanitize"]).directive("openlayers",["$log","$q","$compile","olHelpers","olMapDefaults","olData",function(b,c,d,e,f,g){return{restrict:"EA",transclude:!0,replace:!0,scope:{center:"=olCenter",defaults:"=olDefaults",view:"=olView",events:"=olEvents"},template:'
',controller:["$scope",function(a){var b=c.defer();a.getMap=function(){return b.promise},a.setMap=function(a){b.resolve(a)},this.getOpenlayersScope=function(){return a}}],link:function(b,c,d){var h=e.isDefined,i=e.createLayer,j=e.setMapEvents,k=e.setViewEvents,l=e.createView,m=f.setDefaults(b);h(d.width)&&(isNaN(d.width)?c.css("width",d.width):c.css("width",d.width+"px")),h(d.height)&&(isNaN(d.height)?c.css("height",d.height):c.css("height",d.height+"px")),h(d.lat)&&(m.center.lat=parseFloat(d.lat)),h(d.lon)&&(m.center.lon=parseFloat(d.lon)),h(d.zoom)&&(m.center.zoom=parseFloat(d.zoom));var n=a.control.defaults(m.controls),o=a.interaction.defaults(m.interactions),p=l(m.view),q=new a.Map({target:c[0],controls:n,interactions:o,renderer:m.renderer,view:p,loadTilesWhileAnimating:m.loadTilesWhileAnimating,loadTilesWhileInteracting:m.loadTilesWhileInteracting});if(b.$on("$destroy",function(){g.resetMap(d.id)}),!d.customLayers){var r={type:"Tile",source:{type:"OSM"}},s=i(r,p.getProjection(),"default");q.addLayer(s),q.set("default",!0)}if(!h(d.olCenter)){var t=a.proj.transform([m.center.lon,m.center.lat],m.center.projection,p.getProjection());p.setCenter(t),p.setZoom(m.center.zoom)}j(m.events,q,b),k(m.events,q,b),b.setMap(q),g.setMap(q,d.id)}}}]),angular.module("openlayers-directive").directive("olCenter",["$log","$location","olMapDefaults","olHelpers",function(b,c,d,e){return{restrict:"A",scope:!1,replace:!1,require:"openlayers",link:function(f,g,h,i){var j=e.safeApply,k=e.isValidCenter,l=e.isDefined,m=e.isArray,n=e.isNumber,o=e.isSameCenterOnMap,p=e.setCenter,q=e.setZoom,r=i.getOpenlayersScope();r.getMap().then(function(f){var g=d.getDefaults(r),i=f.getView(),s=r.center;if(h.olCenter.search("-")!==-1)return b.error('[AngularJS - Openlayers] The "center" variable can\'t use a "-" on his key name: "'+h.center+'".'),void p(i,g.view.projection,g.center,f);l(s)||(s={}),k(s)||(b.warn("[AngularJS - Openlayers] invalid 'center'"),s.lat=g.center.lat,s.lon=g.center.lon,s.zoom=g.center.zoom,s.projection=g.center.projection),s.projection||("pixel"!==g.view.projection?s.projection=g.center.projection:s.projection="pixel"),n(s.zoom)||(s.zoom=1),p(i,g.view.projection,s,f),i.setZoom(s.zoom);if(s.centerUrlHash===!0){var t=function(){var a,b=c.search();if(l(b.c)){var d=b.c.split(":");3===d.length&&(a={lat:parseFloat(d[0]),lon:parseFloat(d[1]),zoom:parseInt(d[2],10)})}return a};t(),r.$on("$locationChangeSuccess",function(){var a=t();a&&!o(a,f)&&j(r,function(b){b.center.lat=a.lat,b.center.lon=a.lon,b.center.zoom=a.zoom})})}var u;r.$watchCollection("center",function(c){if(c){if(c.projection||(c.projection=g.center.projection),c.autodiscover)return u||(u=new a.Geolocation({projection:a.proj.get(c.projection)}),u.on("change",function(){if(c.autodiscover){var a=u.getPosition();j(r,function(b){b.center.lat=a[1],b.center.lon=a[0],b.center.zoom=12,b.center.autodiscover=!1,u.setTracking(!1)})}})),void u.setTracking(!0);k(c)||(b.warn("[AngularJS - Openlayers] invalid 'center'"),c=g.center);var d=i.getCenter();if(d)if("pixel"===g.view.projection||"pixel"===c.projection)i.setCenter(c.coord);else{var e=a.proj.transform(d,g.view.projection,c.projection);e[1]===c.lat&&e[0]===c.lon||p(i,g.view.projection,c,f)}i.getZoom()!==c.zoom&&q(i,c.zoom,f)}});var v=f.on("moveend",function(){j(r,function(b){if(l(b.center)){var d=f.getView().getCenter();if(b.center.zoom=i.getZoom(),"pixel"===g.view.projection||"pixel"===b.center.projection)return void(b.center.coord=d);if(b.center){var h=a.proj.transform(d,g.view.projection,b.center.projection);if(b.center.lat=h[1],b.center.lon=h[0],e.notifyCenterUrlHashChanged(r,b.center,c.search()),m(b.center.bounds)){var j=i.calculateExtent(f.getSize()),k=b.center.projection,n=g.view.projection;b.center.bounds=a.proj.transformExtent(j,n,k)}}}})});r.$on("$destroy",function(){f.unByKey(v)})})}}}]),angular.module("openlayers-directive").directive("olLayer",["$log","$q","olMapDefaults","olHelpers",function(a,b,c,d){return{restrict:"E",scope:{properties:"=olLayerProperties",onLayerCreated:"&"},replace:!1,require:"^openlayers",link:function(a,b,e,f){var g=d.isDefined,h=d.equals,i=f.getOpenlayersScope(),j=d.createLayer,k=d.setVectorLayerEvents,l=d.detectLayerType,m=d.createStyle,n=d.isBoolean,o=d.addLayerBeforeMarkers,p=d.isNumber,q=d.insertLayer,r=d.removeLayer,s=d.addLayerToGroup,t=d.removeLayerFromGroup,u=d.getGroup;i.getMap().then(function(b){var d,f=b.getView().getProjection(),v=c.setDefaults(i),w=b.getLayers();if(a.$on("$destroy",function(){a.properties.group?t(w,d,a.properties.group):r(w,d.index),b.removeLayer(d)}),g(a.properties))a.$watch("properties",function(c,e){if(g(c.source)&&g(c.source.type)){if(!g(c.visible))return void(c.visible=!0);if(!g(c.opacity))return void(c.opacity=1);var i,x,y;if(g(d)){var z=function(a){return function(b){return b!==a}}(d);if(g(e)&&!h(c.source,e.source)){var A=d.index;y=w,x=d.get("group"),x&&(y=u(w,x).getLayers()),y.removeAt(A),d=j(c,f,a.onLayerCreated),d.set("group",x),g(d)&&(q(y,A,d),"Vector"===l(c)&&k(v.events,b,a,c.name))}(g(e)&&c.opacity!==e.opacity||z(d))&&(p(c.opacity)||p(parseFloat(c.opacity)))&&d.setOpacity(c.opacity),g(c.index)&&c.index!==d.index&&(y=w,x=d.get("group"),x&&(y=u(w,x).getLayers()),r(y,d.index),q(y,c.index,d)),g(c.group)&&c.group!==e.group&&(t(w,d,e.group),s(w,d,c.group)),g(e)&&n(c.visible)&&(c.visible!==e.visible||z(d)||d.getVisible()!==c.visible)&&d.setVisible(c.visible),(g(c.style)&&!h(c.style,e.style)||z(d))&&(i=angular.isFunction(c.style)?c.style:m(c.style),d.setStyle&&angular.isFunction(d.setStyle)&&d.setStyle(i)),h(c.minResolution,e.minResolution)&&!z(d)||g(c.minResolution)&&d.setMinResolution(c.minResolution),h(c.maxResolution,e.maxResolution)&&!z(d)||g(c.maxResolution)&&d.setMaxResolution(c.maxResolution)}else d=j(c,f,a.onLayerCreated),g(c.group)?s(w,d,c.group):g(c.index)?q(w,c.index,d):o(w,d),"Vector"===l(c)&&k(v.events,b,a,c.name),n(c.visible)&&d.setVisible(c.visible),c.opacity&&d.setOpacity(c.opacity),angular.isArray(c.extent)&&d.setExtent(c.extent),c.style&&(i=angular.isFunction(c.style)?c.style:m(c.style),d.setStyle&&angular.isFunction(d.setStyle)&&d.setStyle(i)),c.minResolution&&d.setMinResolution(c.minResolution),c.maxResolution&&d.setMaxResolution(c.maxResolution)}},!0);else if(g(e.sourceType)&&g(e.sourceUrl)){var x={source:{url:e.sourceUrl,type:e.sourceType}};d=j(x,f,e.layerName,a.onLayerCreated),"Vector"===l(x)&&k(v.events,b,a,e.name),o(w,d)}})}}}]),angular.module("openlayers-directive").directive("olPath",["$log","$q","olMapDefaults","olHelpers",function(a,b,c,d){return{restrict:"E",scope:{properties:"=olGeomProperties",style:"=olStyle"},require:"^openlayers",replace:!0,template:'',link:function(a,b,e,f){var g=d.isDefined,h=d.createFeature,i=d.createOverlay,j=d.createVectorLayer,k=d.insertLayer,l=d.removeLayer,m=f.getOpenlayersScope();m.getMap().then(function(d){var f=c.getDefaults(m),n=f.view.projection,o=j(),p=d.getLayers();if(k(p,p.getLength(),o),a.$on("$destroy",function(){l(p,o.index)}),g(e.coords)){var q=e.proj||"EPSG:4326",r=JSON.parse(e.coords),s={type:"Polygon",coords:r,projection:q,style:a.style?a.style:f.styles.path},t=h(s,n);if(o.getSource().addFeature(t),e.message){a.message=e.message;var u=t.getGeometry().getExtent(),v=i(b,u);d.addOverlay(v)}}else;})}}}]),angular.module("openlayers-directive").directive("olView",["$log","$q","olData","olMapDefaults","olHelpers",function(a,b,c,d,e){return{restrict:"A",scope:!1,replace:!1,require:"openlayers",link:function(a,b,c,f){var g=f.getOpenlayersScope(),h=e.isNumber,i=e.safeApply,j=e.createView;g.getMap().then(function(a){var b=d.getDefaults(g),c=g.view;c.projection||(c.projection=b.view.projection),c.maxZoom||(c.maxZoom=b.view.maxZoom),c.minZoom||(c.minZoom=b.view.minZoom),c.rotation||(c.rotation=b.view.rotation);var e=j(c);a.setView(e),g.$watchCollection("view",function(a){h(a.rotation)&&e.setRotation(a.rotation)});var f=e.on("change:rotation",function(){i(g,function(b){b.view.rotation=a.getView().getRotation()})});g.$on("$destroy",function(){a.unByKey(f)})})}}}]),angular.module("openlayers-directive").directive("olControl",["$log","$q","olData","olMapDefaults","olHelpers",function(a,b,c,d,e){return{restrict:"E",scope:{properties:"=olControlProperties"},replace:!1,require:"^openlayers",link:function(a,b,c,d){var f,g,h=e.isDefined,i=d.getOpenlayersScope(),j=e.getControlClasses,k=j();i.getMap().then(function(b){function d(a){a&&a.control?(f&&b.removeControl(f),f=a.control,b.addControl(f)):c.name&&(h(a)&&(g=a),f&&b.removeControl(f),f=new k[c.name](g),b.addControl(f))}a.$on("$destroy",function(){b.removeControl(f)}),a.$watch("properties",function(a){h(a)&&d(a)}),d(a.properties)})}}}]),angular.module("openlayers-directive").directive("olMarker",["$log","$q","olMapDefaults","olHelpers",function(b,c,d,e){var f=function(){return{projection:"EPSG:4326",lat:0,lon:0,coord:[],show:!0,showOnMouseOver:!1,showOnMouseClick:!1,keepOneOverlayVisible:!1}},g=function(){function a(a){return b.map(function(a){return a.map}).indexOf(a)}var b=[];return{getInst:function(c,d){var f=a(d);if(f===-1){var g=e.createVectorLayer();g.set("markers",!0),d.addLayer(g),b.push({map:d,markerLayer:g,instScopes:[]}),f=b.length-1}return b[f].instScopes.push(c),b[f].markerLayer},deregisterScope:function(c,d){var e=a(d);if(e===-1)throw Error("This map has no markers");var f=b[e].instScopes,g=f.indexOf(c);if(g===-1)throw Error("Scope wan't registered");f.splice(g,1),f.length||(d.removeLayer(b[e].markerLayer),delete b[e].markerLayer,delete b[e])}}}();return{restrict:"E",scope:{lat:"=lat",lon:"=lon",label:"=label",properties:"=olMarkerProperties",style:"=olStyle"},transclude:!0,require:"^openlayers",replace:!0,template:'',link:function(c,h,i,j){var k=e.isDefined,l=j.getOpenlayersScope(),m=e.createFeature,n=e.createOverlay,o=h.find("ng-transclude").children().length>0;l.getMap().then(function(e){function j(){c.properties&&(e.getViewport().removeEventListener("mousemove",c.properties.handleInteraction),e.getViewport().removeEventListener("click",c.properties.handleTapInteraction),e.getViewport().querySelector("canvas.ol-unselectable").removeEventListener("touchend",c.properties.handleTapInteraction),e.getViewport().removeEventListener("mousemove",c.properties.showAtLeastOneOverlay),e.getViewport().removeEventListener("click",c.properties.removeAllOverlays),e.getViewport().querySelector("canvas.ol-unselectable").removeEventListener("touchmove",c.properties.activateCooldown))}var p,q,r,s=g.getInst(c,e),t=f(),u=d.getDefaults(l),v=u.view.projection,w=null,x=null;if(c.handleDrag=function(b){var d=b.coordinate,f=e.getView().getProjection().getCode();if(d="pixel"===f?d.map(function(a){return parseInt(a,10)}):a.proj.transform(d,f,"EPSG:4326"),"pointerdown"===b.type){var g=e.forEachFeatureAtPixel(b.pixel,function(a){return a});if(!(x=g?g.get("marker"):null)||!x.draggable)return void(x=null);e.getTarget().style.cursor="pointer",w="pixel"===f?[d[0]-x.coord[0],d[1]-x.coord[1]]:[d[0]-x.lon,d[1]-x.lat],b.preventDefault()}else w&&x&&("pointerup"===b.type?(e.getTarget().style.cursor="",w=null,x=null,b.preventDefault()):"pointerdrag"===b.type&&(b.preventDefault(),c.$apply(function(){"pixel"===f?(x.coord[0]=d[0]-w[0],x.coord[1]=d[1]-w[1]):(x.lon=d[0]-w[0],x.lat=d[1]-w[1])})))},e.on("pointerdown",c.handleDrag),e.on("pointerup",c.handleDrag),e.on("pointerdrag",c.handleDrag),c.$on("$destroy",function(){s.getSource().removeFeature(r),k(p)&&e.removeOverlay(p),g.deregisterScope(c,e),e.un("pointerdown",c.handleDrag),e.un("pointerup",c.handleDrag),e.un("pointerdrag",c.handleDrag),j()}),!k(c.properties))return t.lat=c.lat?c.lat:t.lat,t.lon=c.lon?c.lon:t.lon,t.message=i.message,t.style=c.style?c.style:u.styles.marker,r=m(t,v),k(r)||b.error("[AngularJS - Openlayers] Received invalid data on the marker."),r.set("marker",c),s.getSource().addFeature(r),void((t.message||o)&&(c.message=i.message,q=a.proj.transform([t.lon,t.lat],t.projection,v),p=n(h,q),e.addOverlay(p)));c.$watch("properties",function(d){if(j(),d.handleInteraction=function(b){var c=!1;if(i.hasOwnProperty("ngClick")&&(c=!0),!d.label.show||c){var f=!1,g=e.getEventPixel(b),j=e.forEachFeatureAtPixel(g,function(a){return a}),l=!1;if(j===r){if(l=!0,f=!0,c&&("click"===b.type||"touchend"===b.type))return h.triggerHandler("click"),b.preventDefault(),void b.stopPropagation();k(p)||(q="pixel"===t.projection?d.coord:a.proj.transform([d.lon,d.lat],t.projection,v),p=n(h,q),e.addOverlay(p)),e.getTarget().style.cursor="pointer"}!f&&p&&(l=!0,e.removeOverlay(p),p=void 0,e.getTarget().style.cursor=""),l&&b.preventDefault()}},d.handleTapInteraction=function(){var a,b=!1;return d.activateCooldown=function(){b=!0,a&&clearTimeout(a),a=setTimeout(function(){b=!1,a=null},500)},d.activateCooldown&&e.getViewport().querySelector("canvas.ol-unselectable").removeEventListener("touchmove",d.activateCooldown),e.getViewport().querySelector("canvas.ol-unselectable").addEventListener("touchmove",d.activateCooldown),function(){b||(d.handleInteraction.apply(null,arguments),d.activateCooldown())}}(),d.showAtLeastOneOverlay=function(b){if(!d.label.show){var c=!1,f=e.getEventPixel(b),g=e.forEachFeatureAtPixel(f,function(a){return a}),i=!1;g===r&&(i=!0,c=!0,k(p)||(q="pixel"===t.projection?t.coord:a.proj.transform([t.lon,t.lat],t.projection,v),p=n(h,q),angular.forEach(e.getOverlays(),function(a){e.removeOverlay(a)}),e.addOverlay(p)),e.getTarget().style.cursor="pointer"),!c&&p&&(i=!0,p=void 0,e.getTarget().style.cursor=""),i&&b.preventDefault()}},d.removeAllOverlays=function(a){angular.forEach(e.getOverlays(),function(a){e.removeOverlay(a)}),a.preventDefault()},k(r)){var f;if(f="pixel"===d.projection?d.coord:a.proj.transform([d.lon,d.lat],t.projection,e.getView().getProjection()),!angular.equals(r.getGeometry().getCoordinates(),f)){var g=new a.geom.Point(f);r.setGeometry(g)}}else t.projection=d.projection?d.projection:t.projection,t.coord=d.coord?d.coord:t.coord,t.lat=d.lat?d.lat:t.lat,t.lon=d.lon?d.lon:t.lon,k(d.style)?t.style=d.style:t.style=u.styles.marker,r=m(t,v),k(r)||b.error("[AngularJS - Openlayers] Received invalid data on the marker."),r.set("marker",d),s.getSource().addFeature(r);k(p)&&e.removeOverlay(p),k(d.label)&&(c.message=d.label.message,(o||k(c.message)&&0!==c.message.length)&&(d.label&&d.label.show===!0&&(q="pixel"===t.projection?t.coord:a.proj.transform([d.lon,d.lat],t.projection,v),p=n(h,q),e.addOverlay(p)),p&&d.label&&d.label.show===!1&&(e.removeOverlay(p),p=void 0),d.label&&d.label.show===!1&&d.label.showOnMouseOver&&e.getViewport().addEventListener("mousemove",d.handleInteraction),(d.label&&d.label.show===!1&&d.label.showOnMouseClick||i.hasOwnProperty("ngClick"))&&(e.getViewport().addEventListener("click",d.handleTapInteraction),e.getViewport().querySelector("canvas.ol-unselectable").addEventListener("touchend",d.handleTapInteraction)),d.label&&d.label.show===!1&&d.label.keepOneOverlayVisible&&(e.getViewport().addEventListener("mousemove",d.showAtLeastOneOverlay),e.getViewport().addEventListener("click",d.removeAllOverlays))))},!0)})}}}]),angular.module("openlayers-directive").service("olData",["$log","$q",function(a,b){function c(b,c){var d,e;if(angular.isDefined(c))d=c;else if(1===Object.keys(b).length)for(e in b)b.hasOwnProperty(e)&&(d=e);else 0===Object.keys(b).length?d="main":a.error("[AngularJS - Openlayers] - You have more than 1 map on the DOM, you must provide the map ID to the olData.getXXX call");return d}var d={},e=function(a,b){a[c(a,b)].resolvedDefer=!0},f=function(a,d){var e,f=c(a,d);return angular.isDefined(a[f])&&a[f].resolvedDefer!==!0?e=a[f].defer:(e=b.defer(),a[f]={defer:e,resolvedDefer:!1}),e},g=function(a,b){var d=c(a,b);return angular.isDefined(a[d])&&a[d].resolvedDefer!==!1?a[d].defer:f(a,b)};this.setMap=function(a,b){f(d,b).resolve(a),e(d,b)},this.getMap=function(a){return g(d,a).promise},this.resetMap=function(a){angular.isDefined(d[a])&&delete d[a]}}]),angular.module("openlayers-directive").factory("olHelpers",["$q","$log","$http",function(b,c,d){var e=function(a){return angular.isDefined(a)},f=function(a){return angular.isDefined(a)&&null!==a},g=function(a,b,c){a.on(b,function(d){var e=d.coordinate,f=a.getView().getProjection().getCode();"pixel"===f&&(e=e.map(function(a){return parseInt(a,10)})),c.$emit("openlayers.map."+b,{coord:e,projection:f,event:d})})},h=["Road","Aerial","AerialWithLabels","collinsBart","ordnanceSurvey"],i=function(){return{attribution:a.control.Attribution,fullscreen:a.control.FullScreen,mouseposition:a.control.MousePosition,overviewmap:a.control.OverviewMap,rotate:a.control.Rotate,scaleline:a.control.ScaleLine,zoom:a.control.Zoom,zoomslider:a.control.ZoomSlider,zoomtoextent:a.control.ZoomToExtent}},j=["osm","sat","hyb"],k=["World_Imagery","World_Street_Map","World_Topo_Map","World_Physical_Map","World_Terrain_Base","Ocean_Basemap","NatGeo_World_Map"],l={style:a.style.Style,fill:a.style.Fill,stroke:a.style.Stroke,circle:a.style.Circle,icon:a.style.Icon,image:a.style.Image,regularshape:a.style.RegularShape,text:a.style.Text},m=function(a,b){return b&&a instanceof b?a:b?new b(a):a},n=function a(b,c){var d;if(c?d=b[c]:(c="style",d=b),"style"===c&&b instanceof Function)return b;if(!(d instanceof Object))return d;var e;if("[object Object]"===Object.prototype.toString.call(d)){e={};var f=l[c];if(f&&d instanceof f)return d;Object.getOwnPropertyNames(d).forEach(function(b,g,h){var i=l[b];if(f&&i&&i.prototype instanceof l[c])return console.assert(1===h.length,"Extra parameters for "+c),e=a(d,b),m(e,i);e[b]=a(d,b),"text"!==b&&"string"!=typeof e[b]&&(e[b]=m(e[b],l[b]))})}else e=d;return m(e,l[c])},o=function(a){if(a.type)return a.type;switch(a.source.type){case"ImageWMS":return"Image";case"ImageStatic":return"Image";case"GeoJSON":case"JSONP":case"TopoJSON":case"KML":case"WKT":return"Vector";case"TileVector":case"MVT":return"TileVector";default:return"Tile"}},p=function(b){var d;switch(b.projection){case"pixel":if(!e(b.extent))return void c.error("[AngularJS - Openlayers] - You must provide the extent of the image if using pixel projection");d=new a.proj.Projection({code:"pixel",units:"pixels",extent:b.extent});break;default:d=new a.proj.get(b.projection)}return d},q=function(a){return["watercolor","terrain","toner"].indexOf(a)!==-1},r=function(b,f){var g,i,l,m=new a.format.GeoJSON;switch(b.type){case"MapBox":if(!b.mapId||!b.accessToken)return void c.error("[AngularJS - Openlayers] - MapBox layer requires the map id and the access token");l="https://api.tiles.mapbox.com/v4/"+b.mapId+"/{z}/{x}/{y}.png?access_token="+b.accessToken,i=window.devicePixelRatio,i>1&&(l=l.replace(".png","@2x.png")),g=new a.source.XYZ({url:l,tileLoadFunction:b.tileLoadFunction,attributions:t(b),tilePixelRatio:i>1?2:1,wrapX:void 0===b.wrapX||b.wrapX});break;case"MapBoxStudio":if(!b.mapId||!b.accessToken||!b.userId)return void c.error("[AngularJS - Openlayers] - MapBox Studio layer requires the map id, user id and the access token");l="https://api.mapbox.com/styles/v1/"+b.userId+"/"+b.mapId+"/tiles/{z}/{x}/{y}?access_token="+b.accessToken,i=window.devicePixelRatio,i>1&&(l=l.replace("{y}?access_token","{y}@2x?access_token")),g=new a.source.XYZ({url:l,tileLoadFunction:b.tileLoadFunction,attributions:t(b),tilePixelRatio:i>1?2:1,tileSize:b.tileSize||[512,512],wrapX:void 0===b.wrapX||b.wrapX});break;case"MVT":if(!b.url)return void c.error("[AngularJS - Openlayers] - MVT layer requires the source url");g=new a.source.VectorTile({attributions:b.attributions||"",format:new a.format.MVT,tileGrid:a.tilegrid.createXYZ({maxZoom:b.maxZoom||22}),tilePixelRatio:b.tilePixelRatio||16,url:b.url});break;case"ImageWMS":b.url&&b.params||c.error("[AngularJS - Openlayers] - ImageWMS Layer needs valid server url and params properties"),g=new a.source.ImageWMS({url:b.url,imageLoadFunction:b.imageLoadFunction,attributions:t(b),crossOrigin:void 0===b.crossOrigin?"anonymous":b.crossOrigin,params:s(b.params),ratio:b.ratio});break;case"TileWMS":(b.url||b.urls)&&b.params||c.error("[AngularJS - Openlayers] - TileWMS Layer needs valid url (or urls) and params properties");var n={tileLoadFunction:b.tileLoadFunction,crossOrigin:void 0===b.crossOrigin?"anonymous":b.crossOrigin,params:s(b.params),attributions:t(b),wrapX:void 0===b.wrapX||b.wrapX};b.serverType&&(n.serverType=b.serverType),b.url&&(n.url=b.url),b.urls&&(n.urls=b.urls),g=new a.source.TileWMS(n);break;case"WMTS":(b.url||b.urls)&&b.tileGrid||c.error("[AngularJS - Openlayers] - WMTS Layer needs valid url (or urls) and tileGrid properties");var o={tileLoadFunction:b.tileLoadFunction,projection:f,layer:b.layer,attributions:t(b),matrixSet:"undefined"===b.matrixSet?f:b.matrixSet,format:"undefined"===b.format?"image/jpeg":b.format,requestEncoding:"undefined"===b.requestEncoding?"KVP":b.requestEncoding,tileGrid:new a.tilegrid.WMTS({origin:b.tileGrid.origin,resolutions:b.tileGrid.resolutions,matrixIds:b.tileGrid.matrixIds}),style:"undefined"===b.style?"normal":b.style,wrapX:void 0===b.wrapX||b.wrapX};e(b.url)&&(o.url=b.url),e(b.urls)&&(o.urls=b.urls),g=new a.source.WMTS(o);break;case"OSM":g=new a.source.OSM({tileLoadFunction:b.tileLoadFunction,attributions:t(b),wrapX:void 0===b.wrapX||b.wrapX}),b.url&&g.setUrl(b.url);break;case"BingMaps":if(!b.key)return void c.error("[AngularJS - Openlayers] - You need an API key to show the Bing Maps.");var p={key:b.key,tileLoadFunction:b.tileLoadFunction,attributions:t(b),imagerySet:b.imagerySet?b.imagerySet:h[0],culture:b.culture,wrapX:void 0===b.wrapX||b.wrapX};b.maxZoom&&(p.maxZoom=b.maxZoom),g=new a.source.BingMaps(p);break;case"MapQuest":if(!b.layer||j.indexOf(b.layer)===-1)return void c.error("[AngularJS - Openlayers] - MapQuest layers needs a valid 'layer' property.");g=new a.source.MapQuest({attributions:t(b),layer:b.layer,wrapX:void 0===b.wrapX||b.wrapX});break;case"EsriBaseMaps":if(!b.layer||k.indexOf(b.layer)===-1)return void c.error("[AngularJS - Openlayers] - ESRI layers needs a valid 'layer' property.");var r="http://services.arcgisonline.com/ArcGIS/rest/services/",u=r+b.layer+"/MapServer/tile/{z}/{y}/{x}";g=new a.source.XYZ({attributions:t(b),tileLoadFunction:b.tileLoadFunction,url:u,wrapX:void 0===b.wrapX||b.wrapX});break;case"TileArcGISRest":b.url||c.error("[AngularJS - Openlayers] - TileArcGISRest Layer needs valid url"),g=new a.source.TileArcGISRest({attributions:t(b),tileLoadFunction:b.tileLoadFunction,url:b.url,wrapX:void 0===b.wrapX||b.wrapX});break;case"GeoJSON":if(!b.geojson&&!b.url)return void c.error("[AngularJS - Openlayers] - You need a geojson property to add a GeoJSON layer.");if(e(b.url))g=new a.source.Vector({format:new a.format.GeoJSON,url:b.url});else{g=new a.source.Vector;var v,w=f;v=e(b.geojson.projection)?new a.proj.get(b.geojson.projection):f;var x=m.readFeatures(b.geojson.object,{featureProjection:w.getCode(),dataProjection:v.getCode()});g.addFeatures(x)}break;case"WKT":if(!b.wkt&&!b.wkt.data)return void c.error("[AngularJS - Openlayers] - You need a WKT property to add a WKT format vector layer.");g=new a.source.Vector;var y,z=new a.format.WKT;y=e(b.wkt.projection)?new a.proj.get(b.wkt.projection):f;var A=z.readFeatures(b.wkt.data,{featureProjection:f.getCode(),dataProjection:y.getCode()});g.addFeatures(A);break;case"JSONP":if(!b.url)return void c.error("[AngularJS - Openlayers] - You need an url properly configured to add a JSONP layer.");e(b.url)&&(g=new a.source.ServerVector({format:m,loader:function(){var a=b.url+"&outputFormat=text/javascript&format_options=callback:JSON_CALLBACK";d.jsonp(a,{cache:b.cache}).success(function(a){g.addFeatures(m.readFeatures(a))}).error(function(a){c(a)})},projection:f}));break;case"TopoJSON":if(!b.topojson&&!b.url)return void c.error("[AngularJS - Openlayers] - You need a topojson property to add a TopoJSON layer.");g=b.url?new a.source.Vector({format:new a.format.TopoJSON,url:b.url}):new a.source.Vector(angular.extend(b.topojson,{format:new a.format.TopoJSON}));break;case"TileJSON":g=new a.source.TileJSON({url:b.url,attributions:t(b),tileLoadFunction:b.tileLoadFunction,crossOrigin:"anonymous",wrapX:void 0===b.wrapX||b.wrapX});break;case"TileVector":b.url&&b.format||c.error("[AngularJS - Openlayers] - TileVector Layer needs valid url and format properties"),g=new a.source.VectorTile({url:b.url,projection:f,attributions:t(b),tileLoadFunction:b.tileLoadFunction,format:b.format,tileGrid:new a.tilegrid.createXYZ({maxZoom:b.maxZoom||19}),wrapX:void 0===b.wrapX||b.wrapX});break;case"TileTMS":b.url&&b.tileGrid||c.error("[AngularJS - Openlayers] - TileTMS Layer needs valid url and tileGrid properties"),g=new a.source.TileImage({url:b.url,maxExtent:b.maxExtent,attributions:t(b),tileLoadFunction:b.tileLoadFunction,tileGrid:new a.tilegrid.TileGrid({origin:b.tileGrid.origin,resolutions:b.tileGrid.resolutions}),tileUrlFunction:function(a){var c=a[0],d=a[1],e=a[2];return d<0||e<0?"":b.url+c+"/"+d+"/"+e+".png"},wrapX:void 0===b.wrapX||b.wrapX});break;case"TileImage":g=new a.source.TileImage({url:b.url,attributions:t(b),tileLoadFunction:b.tileLoadFunction,tileGrid:new a.tilegrid.TileGrid({origin:b.tileGrid.origin,resolutions:b.tileGrid.resolutions}),tileUrlFunction:function(a){var c=a[0],d=a[1],e=-a[2]-1;return b.url.replace("{z}",c.toString()).replace("{x}",d.toString()).replace("{y}",e.toString())},wrapX:void 0===b.wrapX||b.wrapX});break;case"KML":var B=b.extractStyles||!1;g=new a.source.Vector({url:b.url,format:new a.format.KML,radius:b.radius,extractStyles:B});break;case"Stamen":if(!b.layer||!q(b.layer))return void c.error("[AngularJS - Openlayers] - You need a valid Stamen layer.");g=new a.source.Stamen({tileLoadFunction:b.tileLoadFunction,layer:b.layer,wrapX:void 0===b.wrapX||b.wrapX});break;case"ImageStatic":if(!b.url||!angular.isArray(b.imageSize)||2!==b.imageSize.length)return void c.error("[AngularJS - Openlayers] - You need a image URL to create a ImageStatic layer.");g=new a.source.ImageStatic({url:b.url,attributions:t(b),imageSize:b.imageSize,projection:f,imageExtent:b.imageExtent?b.imageExtent:f.getExtent(),imageLoadFunction:b.imageLoadFunction});break;case"XYZ":b.url||b.tileUrlFunction||c.error("[AngularJS - Openlayers] - XYZ Layer needs valid url or tileUrlFunction properties"),g=new a.source.XYZ({url:b.url,attributions:t(b),minZoom:b.minZoom,maxZoom:b.maxZoom,projection:b.projection,tileUrlFunction:b.tileUrlFunction,tileLoadFunction:b.tileLoadFunction,wrapX:void 0===b.wrapX||b.wrapX});break;case"Zoomify":b.url&&angular.isArray(b.imageSize)&&2===b.imageSize.length||c.error("[AngularJS - Openlayers] - Zoomify Layer needs valid url and imageSize properties"),g=new a.source.Zoomify({url:b.url,size:b.imageSize,wrapX:void 0===b.wrapX||b.wrapX})}return g||c.warn('[AngularJS - Openlayers] - No source could be found for type "'+b.type+'"'),g},s=function(a){var b=a;if(a&&"object"==typeof a){b="[object Array]"===Object.prototype.toString.call(a)?[]:{};for(var c in a)b[c]=s(a[c])}return b},t=function(b){var c=[];return e(b.attribution)&&c.unshift(new a.Attribution({html:b.attribution})),c},u=function(b){var c=new a.layer.Group;return c.set("name",b),c},v=function(b,c){var d;return angular.forEach(b,function(b){if(b instanceof a.layer.Group&&b.get("name")===c)return void(d=b)}),d},w=function(a,b){for(var c,d=0;d',controller:["$scope",function(a){var b=c.defer();a.getMap=function(){return b.promise},a.setMap=function(a){b.resolve(a)},this.getOpenlayersScope=function(){return a}}],link:function(b,c,d){var h=e.isDefined,i=e.createLayer,j=e.setMapEvents,k=e.setViewEvents,l=e.createView,m=f.setDefaults(b);h(d.width)&&(isNaN(d.width)?c.css("width",d.width):c.css("width",d.width+"px")),h(d.height)&&(isNaN(d.height)?c.css("height",d.height):c.css("height",d.height+"px")),h(d.lat)&&(m.center.lat=parseFloat(d.lat)),h(d.lon)&&(m.center.lon=parseFloat(d.lon)),h(d.zoom)&&(m.center.zoom=parseFloat(d.zoom));var n=a.control.defaults(m.controls),o=a.interaction.defaults(m.interactions),p=l(m.view),q=new a.Map({target:c[0],controls:n,interactions:o,renderer:m.renderer,view:p,loadTilesWhileAnimating:m.loadTilesWhileAnimating,loadTilesWhileInteracting:m.loadTilesWhileInteracting});if(b.$on("$destroy",function(){g.resetMap(d.id)}),!d.customLayers){var r={type:"Tile",source:{type:"OSM"}},s=i(r,p.getProjection(),"default");q.addLayer(s),q.set("default",!0)}if(!h(d.olCenter)){var t=a.proj.transform([m.center.lon,m.center.lat],m.center.projection,p.getProjection());p.setCenter(t),p.setZoom(m.center.zoom)}j(m.events,q,b),k(m.events,q,b),b.setMap(q),g.setMap(q,d.id)}}}]),angular.module("openlayers-directive").directive("olCenter",["$log","$location","olMapDefaults","olHelpers",function(b,c,d,e){return{restrict:"A",scope:!1,replace:!1,require:"openlayers",link:function(f,g,h,i){var j=e.safeApply,k=e.isValidCenter,l=e.isDefined,m=e.isArray,n=e.isNumber,o=e.isSameCenterOnMap,p=e.setCenter,q=e.setZoom,r=i.getOpenlayersScope();r.getMap().then(function(f){var g=d.getDefaults(r),i=f.getView(),s=r.center;if(-1!==h.olCenter.search("-"))return b.error('[AngularJS - Openlayers] The "center" variable can\'t use a "-" on his key name: "'+h.center+'".'),void p(i,g.view.projection,g.center,f);l(s)||(s={}),k(s)||(b.warn("[AngularJS - Openlayers] invalid 'center'"),s.lat=g.center.lat,s.lon=g.center.lon,s.zoom=g.center.zoom,s.projection=g.center.projection),s.projection||("pixel"!==g.view.projection?s.projection=g.center.projection:s.projection="pixel"),n(s.zoom)||(s.zoom=1),p(i,g.view.projection,s,f),i.setZoom(s.zoom);if(!0===s.centerUrlHash){var t=function(){var a,b=c.search();if(l(b.c)){var d=b.c.split(":");3===d.length&&(a={lat:parseFloat(d[0]),lon:parseFloat(d[1]),zoom:parseInt(d[2],10)})}return a};t(),r.$on("$locationChangeSuccess",function(){var a=t();a&&!o(a,f)&&j(r,function(b){b.center.lat=a.lat,b.center.lon=a.lon,b.center.zoom=a.zoom})})}var u;r.$watchCollection("center",function(c){if(c){if(c.projection||(c.projection=g.center.projection),c.autodiscover)return u||(u=new a.Geolocation({projection:a.proj.get(c.projection)}),u.on("change",function(){if(c.autodiscover){var a=u.getPosition();j(r,function(b){b.center.lat=a[1],b.center.lon=a[0],b.center.zoom=12,b.center.autodiscover=!1,u.setTracking(!1)})}})),void u.setTracking(!0);k(c)||(b.warn("[AngularJS - Openlayers] invalid 'center'"),c=g.center);var d=i.getCenter();if(d)if("pixel"===g.view.projection||"pixel"===c.projection)i.setCenter(c.coord);else{var e=a.proj.transform(d,g.view.projection,c.projection);e[1]===c.lat&&e[0]===c.lon||p(i,g.view.projection,c,f)}i.getZoom()!==c.zoom&&q(i,c.zoom,f)}});var v=f.on("moveend",function(){j(r,function(b){if(l(b.center)){var d=f.getView().getCenter();if(b.center.zoom=i.getZoom(),"pixel"===g.view.projection||"pixel"===b.center.projection)return void(b.center.coord=d);if(b.center){var h=a.proj.transform(d,g.view.projection,b.center.projection);if(b.center.lat=h[1],b.center.lon=h[0],e.notifyCenterUrlHashChanged(r,b.center,c.search()),m(b.center.bounds)){var j=i.calculateExtent(f.getSize()),k=b.center.projection,n=g.view.projection;b.center.bounds=a.proj.transformExtent(j,n,k)}}}})});r.$on("$destroy",function(){f.unByKey(v)})})}}}]),angular.module("openlayers-directive").directive("olLayer",["$log","$q","olMapDefaults","olHelpers",function(a,b,c,d){return{restrict:"E",scope:{properties:"=olLayerProperties",onLayerCreated:"&"},replace:!1,require:"^openlayers",link:function(a,b,e,f){var g=d.isDefined,h=d.equals,i=f.getOpenlayersScope(),j=d.createLayer,k=d.setVectorLayerEvents,l=d.detectLayerType,m=d.createStyle,n=d.isBoolean,o=d.addLayerBeforeMarkers,p=d.isNumber,q=d.insertLayer,r=d.removeLayer,s=d.addLayerToGroup,t=d.removeLayerFromGroup,u=d.getGroup;i.getMap().then(function(b){var d,f=b.getView().getProjection(),v=c.setDefaults(i),w=b.getLayers();if(a.$on("$destroy",function(){a.properties.group?t(w,d,a.properties.group):r(w,d.index),b.removeLayer(d)}),g(a.properties))a.$watch("properties",function(c,e){if(g(c.source)&&g(c.source.type)){if(!g(c.visible))return void(c.visible=!0);if(!g(c.opacity))return void(c.opacity=1);var i,x,y;if(g(d)){var z=function(a){return function(b){return b!==a}}(d);if(g(e)&&!h(c.source,e.source)){var A=d.index;y=w,x=d.get("group"),x&&(y=u(w,x).getLayers()),y.removeAt(A),d=j(c,f,a.onLayerCreated),d.set("group",x),g(d)&&(q(y,A,d),"Vector"===l(c)&&k(v.events,b,a,c.name))}(g(e)&&c.opacity!==e.opacity||z(d))&&(p(c.opacity)||p(parseFloat(c.opacity)))&&d.setOpacity(c.opacity),g(c.index)&&c.index!==d.index&&(y=w,x=d.get("group"),x&&(y=u(w,x).getLayers()),r(y,d.index),q(y,c.index,d)),g(c.group)&&c.group!==e.group&&(t(w,d,e.group),s(w,d,c.group)),g(e)&&n(c.visible)&&(c.visible!==e.visible||z(d)||d.getVisible()!==c.visible)&&d.setVisible(c.visible),(g(c.style)&&!h(c.style,e.style)||z(d))&&(i=angular.isFunction(c.style)?c.style:m(c.style),d.setStyle&&angular.isFunction(d.setStyle)&&d.setStyle(i)),h(c.minResolution,e.minResolution)&&!z(d)||g(c.minResolution)&&d.setMinResolution(c.minResolution),h(c.maxResolution,e.maxResolution)&&!z(d)||g(c.maxResolution)&&d.setMaxResolution(c.maxResolution)}else d=j(c,f,a.onLayerCreated),g(c.group)?s(w,d,c.group):g(c.index)?q(w,c.index,d):o(w,d),"Vector"===l(c)&&k(v.events,b,a,c.name),n(c.visible)&&d.setVisible(c.visible),c.opacity&&d.setOpacity(c.opacity),angular.isArray(c.extent)&&d.setExtent(c.extent),c.style&&(i=angular.isFunction(c.style)?c.style:m(c.style),d.setStyle&&angular.isFunction(d.setStyle)&&d.setStyle(i)),c.minResolution&&d.setMinResolution(c.minResolution),c.maxResolution&&d.setMaxResolution(c.maxResolution)}},!0);else if(g(e.sourceType)&&g(e.sourceUrl)){var x={source:{url:e.sourceUrl,type:e.sourceType}};d=j(x,f,e.layerName,a.onLayerCreated),"Vector"===l(x)&&k(v.events,b,a,e.name),o(w,d)}})}}}]),angular.module("openlayers-directive").directive("olPath",["$log","$q","olMapDefaults","olHelpers",function(a,b,c,d){return{restrict:"E",scope:{properties:"=olGeomProperties",style:"=olStyle"},require:"^openlayers",replace:!0,template:'',link:function(a,b,e,f){var g=d.isDefined,h=d.createFeature,i=d.createOverlay,j=d.createVectorLayer,k=d.insertLayer,l=d.removeLayer,m=f.getOpenlayersScope();m.getMap().then(function(d){var f=c.getDefaults(m),n=f.view.projection,o=j(),p=d.getLayers();if(k(p,p.getLength(),o),a.$on("$destroy",function(){l(p,o.index)}),g(e.coords)){var q=e.proj||"EPSG:4326",r=JSON.parse(e.coords),s={type:"Polygon",coords:r,projection:q,style:a.style?a.style:f.styles.path},t=h(s,n);if(o.getSource().addFeature(t),e.message){a.message=e.message;var u=t.getGeometry().getExtent(),v=i(b,u);d.addOverlay(v)}}else;})}}}]),angular.module("openlayers-directive").directive("olView",["$log","$q","olData","olMapDefaults","olHelpers",function(a,b,c,d,e){return{restrict:"A",scope:!1,replace:!1,require:"openlayers",link:function(a,b,c,f){var g=f.getOpenlayersScope(),h=e.isNumber,i=e.safeApply,j=e.createView;g.getMap().then(function(a){var b=d.getDefaults(g),c=g.view;c.projection||(c.projection=b.view.projection),c.maxZoom||(c.maxZoom=b.view.maxZoom),c.minZoom||(c.minZoom=b.view.minZoom),c.rotation||(c.rotation=b.view.rotation);var e=j(c);a.setView(e),g.$watchCollection("view",function(a){h(a.rotation)&&e.setRotation(a.rotation)});var f=e.on("change:rotation",function(){i(g,function(b){b.view.rotation=a.getView().getRotation()})});g.$on("$destroy",function(){a.unByKey(f)})})}}}]),angular.module("openlayers-directive").directive("olControl",["$log","$q","olData","olMapDefaults","olHelpers",function(a,b,c,d,e){return{restrict:"E",scope:{properties:"=olControlProperties"},replace:!1,require:"^openlayers",link:function(a,b,c,d){var f,g,h=e.isDefined,i=d.getOpenlayersScope(),j=e.getControlClasses,k=j();i.getMap().then(function(b){function d(a){a&&a.control?(f&&b.removeControl(f),f=a.control,b.addControl(f)):c.name&&(h(a)&&(g=a),f&&b.removeControl(f),f=new k[c.name](g),b.addControl(f))}a.$on("$destroy",function(){b.removeControl(f)}),a.$watch("properties",function(a){h(a)&&d(a)}),d(a.properties)})}}}]),angular.module("openlayers-directive").directive("olMarker",["$log","$q","olMapDefaults","olHelpers",function(b,c,d,e){var f=function(){return{projection:"EPSG:4326",lat:0,lon:0,coord:[],show:!0,showOnMouseOver:!1,showOnMouseClick:!1,keepOneOverlayVisible:!1}},g=function(){function a(a){return b.map(function(a){return a.map}).indexOf(a)}var b=[];return{getInst:function(c,d){var f=a(d);if(-1===f){var g=e.createVectorLayer();g.set("markers",!0),d.addLayer(g),b.push({map:d,markerLayer:g,instScopes:[]}),f=b.length-1}return b[f].instScopes.push(c),b[f].markerLayer},deregisterScope:function(c,d){var e=a(d);if(-1===e)throw Error("This map has no markers");var f=b[e].instScopes,g=f.indexOf(c);if(-1===g)throw Error("Scope wan't registered");f.splice(g,1),f.length||(d.removeLayer(b[e].markerLayer),delete b[e].markerLayer,delete b[e])}}}();return{restrict:"E",scope:{lat:"=lat",lon:"=lon",label:"=label",properties:"=olMarkerProperties",style:"=olStyle"},transclude:!0,require:"^openlayers",replace:!0,template:'',link:function(c,h,i,j){var k=e.isDefined,l=j.getOpenlayersScope(),m=e.createFeature,n=e.createOverlay,o=h.find("ng-transclude").children().length>0;l.getMap().then(function(e){function j(){c.properties&&(e.getViewport().removeEventListener("mousemove",c.properties.handleInteraction),e.getViewport().removeEventListener("click",c.properties.handleTapInteraction),e.getViewport().querySelector("canvas.ol-unselectable").removeEventListener("touchend",c.properties.handleTapInteraction),e.getViewport().removeEventListener("mousemove",c.properties.showAtLeastOneOverlay),e.getViewport().removeEventListener("click",c.properties.removeAllOverlays),e.getViewport().querySelector("canvas.ol-unselectable").removeEventListener("touchmove",c.properties.activateCooldown))}var p,q,r,s=g.getInst(c,e),t=f(),u=d.getDefaults(l),v=u.view.projection,w=null,x=null;if(c.handleDrag=function(b){var d=b.coordinate,f=e.getView().getProjection().getCode();if(d="pixel"===f?d.map(function(a){return parseInt(a,10)}):a.proj.transform(d,f,"EPSG:4326"),"pointerdown"===b.type){var g=e.forEachFeatureAtPixel(b.pixel,function(a){return a});if(!(x=g?g.get("marker"):null)||!x.draggable)return void(x=null);e.getTarget().style.cursor="pointer",w="pixel"===f?[d[0]-x.coord[0],d[1]-x.coord[1]]:[d[0]-x.lon,d[1]-x.lat],b.preventDefault()}else w&&x&&("pointerup"===b.type?(e.getTarget().style.cursor="",w=null,x=null,b.preventDefault()):"pointerdrag"===b.type&&(b.preventDefault(),c.$apply(function(){"pixel"===f?(x.coord[0]=d[0]-w[0],x.coord[1]=d[1]-w[1]):(x.lon=d[0]-w[0],x.lat=d[1]-w[1])})))},e.on("pointerdown",c.handleDrag),e.on("pointerup",c.handleDrag),e.on("pointerdrag",c.handleDrag),c.$on("$destroy",function(){s.getSource().removeFeature(r),k(p)&&e.removeOverlay(p),g.deregisterScope(c,e),e.un("pointerdown",c.handleDrag),e.un("pointerup",c.handleDrag),e.un("pointerdrag",c.handleDrag),j()}),!k(c.properties))return t.lat=c.lat?c.lat:t.lat,t.lon=c.lon?c.lon:t.lon,t.message=i.message,t.style=c.style?c.style:u.styles.marker,r=m(t,v),k(r)||b.error("[AngularJS - Openlayers] Received invalid data on the marker."),r.set("marker",c),s.getSource().addFeature(r),void((t.message||o)&&(c.message=i.message,q=a.proj.transform([t.lon,t.lat],t.projection,v),p=n(h,q),e.addOverlay(p)));c.$watch("properties",function(d){if(j(),d.handleInteraction=function(b){var c=!1;if(i.hasOwnProperty("ngClick")&&(c=!0),!d.label.show||c){var f=!1,g=e.getEventPixel(b),j=e.forEachFeatureAtPixel(g,function(a){return a}),l=!1;if(j===r){if(l=!0,f=!0,c&&("click"===b.type||"touchend"===b.type))return h.triggerHandler("click"),b.preventDefault(),void b.stopPropagation();k(p)||(q="pixel"===t.projection?d.coord:a.proj.transform([d.lon,d.lat],t.projection,v),p=n(h,q),e.addOverlay(p)),e.getTarget().style.cursor="pointer"}!f&&p&&(l=!0,e.removeOverlay(p),p=void 0,e.getTarget().style.cursor=""),l&&b.preventDefault()}},d.handleTapInteraction=function(){var a,b=!1;return d.activateCooldown=function(){b=!0,a&&clearTimeout(a),a=setTimeout(function(){b=!1,a=null},500)},d.activateCooldown&&e.getViewport().querySelector("canvas.ol-unselectable").removeEventListener("touchmove",d.activateCooldown),e.getViewport().querySelector("canvas.ol-unselectable").addEventListener("touchmove",d.activateCooldown),function(){b||(d.handleInteraction.apply(null,arguments),d.activateCooldown())}}(),d.showAtLeastOneOverlay=function(b){if(!d.label.show){var c=!1,f=e.getEventPixel(b),g=e.forEachFeatureAtPixel(f,function(a){return a}),i=!1;g===r&&(i=!0,c=!0,k(p)||(q="pixel"===t.projection?t.coord:a.proj.transform([t.lon,t.lat],t.projection,v),p=n(h,q),angular.forEach(e.getOverlays(),function(a){e.removeOverlay(a)}),e.addOverlay(p)),e.getTarget().style.cursor="pointer"),!c&&p&&(i=!0,p=void 0,e.getTarget().style.cursor=""),i&&b.preventDefault()}},d.removeAllOverlays=function(a){angular.forEach(e.getOverlays(),function(a){e.removeOverlay(a)}),a.preventDefault()},k(r)){var f;if(f="pixel"===d.projection?d.coord:a.proj.transform([d.lon,d.lat],t.projection,e.getView().getProjection()),!angular.equals(r.getGeometry().getCoordinates(),f)){var g=new a.geom.Point(f);r.setGeometry(g)}}else t.projection=d.projection?d.projection:t.projection,t.coord=d.coord?d.coord:t.coord,t.lat=d.lat?d.lat:t.lat,t.lon=d.lon?d.lon:t.lon,k(d.style)?t.style=d.style:t.style=u.styles.marker,r=m(t,v),k(r)||b.error("[AngularJS - Openlayers] Received invalid data on the marker."),r.set("marker",d),s.getSource().addFeature(r);k(p)&&e.removeOverlay(p),k(d.label)&&(c.message=d.label.message,(o||k(c.message)&&0!==c.message.length)&&(d.label&&!0===d.label.show&&(q="pixel"===t.projection?t.coord:a.proj.transform([d.lon,d.lat],t.projection,v),p=n(h,q),e.addOverlay(p)),p&&d.label&&!1===d.label.show&&(e.removeOverlay(p),p=void 0),d.label&&!1===d.label.show&&d.label.showOnMouseOver&&e.getViewport().addEventListener("mousemove",d.handleInteraction),(d.label&&!1===d.label.show&&d.label.showOnMouseClick||i.hasOwnProperty("ngClick"))&&(e.getViewport().addEventListener("click",d.handleTapInteraction),e.getViewport().querySelector("canvas.ol-unselectable").addEventListener("touchend",d.handleTapInteraction)),d.label&&!1===d.label.show&&d.label.keepOneOverlayVisible&&(e.getViewport().addEventListener("mousemove",d.showAtLeastOneOverlay),e.getViewport().addEventListener("click",d.removeAllOverlays))))},!0)})}}}]),angular.module("openlayers-directive").service("olData",["$log","$q",function(a,b){function c(b,c){var d,e;if(angular.isDefined(c))d=c;else if(1===Object.keys(b).length)for(e in b)b.hasOwnProperty(e)&&(d=e);else 0===Object.keys(b).length?d="main":a.error("[AngularJS - Openlayers] - You have more than 1 map on the DOM, you must provide the map ID to the olData.getXXX call");return d}var d={},e=function(a,b){a[c(a,b)].resolvedDefer=!0},f=function(a,d){var e,f=c(a,d);return angular.isDefined(a[f])&&!0!==a[f].resolvedDefer?e=a[f].defer:(e=b.defer(),a[f]={defer:e,resolvedDefer:!1}),e},g=function(a,b){var d=c(a,b);return angular.isDefined(a[d])&&!1!==a[d].resolvedDefer?a[d].defer:f(a,b)};this.setMap=function(a,b){f(d,b).resolve(a),e(d,b)},this.getMap=function(a){return g(d,a).promise},this.resetMap=function(a){angular.isDefined(d[a])&&delete d[a]}}]),angular.module("openlayers-directive").factory("olHelpers",["$q","$log","$http",function(b,c,d){var e=function(a){return angular.isDefined(a)},f=function(a){return angular.isDefined(a)&&null!==a},g=function(a,b,c){a.on(b,function(d){var e=d.coordinate,f=a.getView().getProjection().getCode();"pixel"===f&&(e=e.map(function(a){return parseInt(a,10)})),c.$emit("openlayers.map."+b,{coord:e,projection:f,event:d})})},h=["Road","Aerial","AerialWithLabels","collinsBart","ordnanceSurvey"],i=function(){return{attribution:a.control.Attribution,fullscreen:a.control.FullScreen,mouseposition:a.control.MousePosition,overviewmap:a.control.OverviewMap,rotate:a.control.Rotate,scaleline:a.control.ScaleLine,zoom:a.control.Zoom,zoomslider:a.control.ZoomSlider,zoomtoextent:a.control.ZoomToExtent}},j=["osm","sat","hyb"],k=["World_Imagery","World_Street_Map","World_Topo_Map","World_Physical_Map","World_Terrain_Base","Ocean_Basemap","NatGeo_World_Map"],l={style:a.style.Style,fill:a.style.Fill,stroke:a.style.Stroke,circle:a.style.Circle,icon:a.style.Icon,image:a.style.Image,regularshape:a.style.RegularShape,text:a.style.Text},m=function(a,b){return b&&a instanceof b?a:b?new b(a):a},n=function a(b,c){var d;if(c?d=b[c]:(c="style",d=b),"style"===c&&b instanceof Function)return b;if(!(d instanceof Object))return d;var e;if("[object Object]"===Object.prototype.toString.call(d)){e={};var f=l[c];if(f&&d instanceof f)return d;Object.getOwnPropertyNames(d).forEach(function(b,g,h){var i=l[b];if(f&&i&&i.prototype instanceof l[c])return console.assert(1===h.length,"Extra parameters for "+c),e=a(d,b),m(e,i);e[b]=a(d,b),"text"!==b&&"string"!=typeof e[b]&&(e[b]=m(e[b],l[b]))})}else e=d;return m(e,l[c])},o=function(a){if(a.type)return a.type;switch(a.source.type){case"ImageWMS":case"ImageStatic":return"Image";case"GeoJSON":case"JSONP":case"TopoJSON":case"KML":case"WKT":return"Vector";case"TileVector":case"MVT":return"TileVector";default:return"Tile"}},p=function(b){var d;switch(b.projection){case"pixel":if(!e(b.extent))return void c.error("[AngularJS - Openlayers] - You must provide the extent of the image if using pixel projection");d=new a.proj.Projection({code:"pixel",units:"pixels",extent:b.extent});break;default:d=new a.proj.get(b.projection)}return d},q=function(a){return-1!==["watercolor","terrain","toner"].indexOf(a)},r=function(b,f){var g,i,l,m=new a.format.GeoJSON;switch(b.type){case"MapBox":if(!b.mapId||!b.accessToken)return void c.error("[AngularJS - Openlayers] - MapBox layer requires the map id and the access token");l="https://api.tiles.mapbox.com/v4/"+b.mapId+"/{z}/{x}/{y}.png?access_token="+b.accessToken,i=window.devicePixelRatio,i>1&&(l=l.replace(".png","@2x.png")),g=new a.source.XYZ({url:l,tileLoadFunction:b.tileLoadFunction,attributions:t(b),tilePixelRatio:i>1?2:1,wrapX:void 0===b.wrapX||b.wrapX});break;case"MapBoxStudio":if(!b.mapId||!b.accessToken||!b.userId)return void c.error("[AngularJS - Openlayers] - MapBox Studio layer requires the map id, user id and the access token");l="https://api.mapbox.com/styles/v1/"+b.userId+"/"+b.mapId+"/tiles/{z}/{x}/{y}?access_token="+b.accessToken,i=window.devicePixelRatio,i>1&&(l=l.replace("{y}?access_token","{y}@2x?access_token")),g=new a.source.XYZ({url:l,tileLoadFunction:b.tileLoadFunction,attributions:t(b),tilePixelRatio:i>1?2:1,tileSize:b.tileSize||[512,512],wrapX:void 0===b.wrapX||b.wrapX});break;case"MVT":if(!b.url)return void c.error("[AngularJS - Openlayers] - MVT layer requires the source url");g=new a.source.VectorTile({attributions:b.attributions||"",format:new a.format.MVT,tileGrid:a.tilegrid.createXYZ({maxZoom:b.maxZoom||22}),tilePixelRatio:b.tilePixelRatio||16,url:b.url});break;case"ImageWMS":b.url&&b.params||c.error("[AngularJS - Openlayers] - ImageWMS Layer needs valid server url and params properties"),g=new a.source.ImageWMS({url:b.url,imageLoadFunction:b.imageLoadFunction,attributions:t(b),crossOrigin:void 0===b.crossOrigin?"anonymous":b.crossOrigin,params:s(b.params),ratio:b.ratio});break;case"TileWMS":(b.url||b.urls)&&b.params||c.error("[AngularJS - Openlayers] - TileWMS Layer needs valid url (or urls) and params properties");var n={tileLoadFunction:b.tileLoadFunction,crossOrigin:void 0===b.crossOrigin?"anonymous":b.crossOrigin,params:s(b.params),attributions:t(b),wrapX:void 0===b.wrapX||b.wrapX};b.serverType&&(n.serverType=b.serverType),b.url&&(n.url=b.url),b.urls&&(n.urls=b.urls),g=new a.source.TileWMS(n);break;case"WMTS":(b.url||b.urls)&&b.tileGrid||c.error("[AngularJS - Openlayers] - WMTS Layer needs valid url (or urls) and tileGrid properties");var o={tileLoadFunction:b.tileLoadFunction,projection:f,layer:b.layer,attributions:t(b),matrixSet:"undefined"===b.matrixSet?f:b.matrixSet,format:"undefined"===b.format?"image/jpeg":b.format,requestEncoding:"undefined"===b.requestEncoding?"KVP":b.requestEncoding,tileGrid:new a.tilegrid.WMTS({origin:b.tileGrid.origin,resolutions:b.tileGrid.resolutions,matrixIds:b.tileGrid.matrixIds}),style:"undefined"===b.style?"normal":b.style,wrapX:void 0===b.wrapX||b.wrapX};e(b.url)&&(o.url=b.url),e(b.urls)&&(o.urls=b.urls),g=new a.source.WMTS(o);break;case"OSM":g=new a.source.OSM({tileLoadFunction:b.tileLoadFunction,attributions:t(b),wrapX:void 0===b.wrapX||b.wrapX}),b.url&&g.setUrl(b.url);break;case"BingMaps":if(!b.key)return void c.error("[AngularJS - Openlayers] - You need an API key to show the Bing Maps.");var p={key:b.key,tileLoadFunction:b.tileLoadFunction,attributions:t(b),imagerySet:b.imagerySet?b.imagerySet:h[0],culture:b.culture,wrapX:void 0===b.wrapX||b.wrapX};b.maxZoom&&(p.maxZoom=b.maxZoom),g=new a.source.BingMaps(p);break;case"MapQuest":if(!b.layer||-1===j.indexOf(b.layer))return void c.error("[AngularJS - Openlayers] - MapQuest layers needs a valid 'layer' property.");g=new a.source.MapQuest({attributions:t(b),layer:b.layer,wrapX:void 0===b.wrapX||b.wrapX});break;case"EsriBaseMaps":if(!b.layer||-1===k.indexOf(b.layer))return void c.error("[AngularJS - Openlayers] - ESRI layers needs a valid 'layer' property.");var r="http://services.arcgisonline.com/ArcGIS/rest/services/",u=r+b.layer+"/MapServer/tile/{z}/{y}/{x}";g=new a.source.XYZ({attributions:t(b),tileLoadFunction:b.tileLoadFunction,url:u,wrapX:void 0===b.wrapX||b.wrapX});break;case"TileArcGISRest":b.url||c.error("[AngularJS - Openlayers] - TileArcGISRest Layer needs valid url"),g=new a.source.TileArcGISRest({attributions:t(b),tileLoadFunction:b.tileLoadFunction,url:b.url,wrapX:void 0===b.wrapX||b.wrapX});break;case"GeoJSON":if(!b.geojson&&!b.url)return void c.error("[AngularJS - Openlayers] - You need a geojson property to add a GeoJSON layer.");if(e(b.url))g=new a.source.Vector({format:new a.format.GeoJSON,url:b.url});else{g=new a.source.Vector;var v,w=f;v=e(b.geojson.projection)?new a.proj.get(b.geojson.projection):f;var x=m.readFeatures(b.geojson.object,{featureProjection:w.getCode(),dataProjection:v.getCode()});g.addFeatures(x)}break;case"WKT":if(!b.wkt&&!b.wkt.data)return void c.error("[AngularJS - Openlayers] - You need a WKT property to add a WKT format vector layer.");g=new a.source.Vector;var y,z=new a.format.WKT;y=e(b.wkt.projection)?new a.proj.get(b.wkt.projection):f;var A=z.readFeatures(b.wkt.data,{featureProjection:f.getCode(),dataProjection:y.getCode()});g.addFeatures(A);break;case"JSONP":if(!b.url)return void c.error("[AngularJS - Openlayers] - You need an url properly configured to add a JSONP layer.");e(b.url)&&(g=new a.source.ServerVector({format:m,loader:function(){var a=b.url+"&outputFormat=text/javascript&format_options=callback:JSON_CALLBACK";d.jsonp(a,{cache:b.cache}).success(function(a){g.addFeatures(m.readFeatures(a))}).error(function(a){c(a)})},projection:f}));break;case"TopoJSON":if(!b.topojson&&!b.url)return void c.error("[AngularJS - Openlayers] - You need a topojson property to add a TopoJSON layer.");g=b.url?new a.source.Vector({format:new a.format.TopoJSON,url:b.url}):new a.source.Vector(angular.extend(b.topojson,{format:new a.format.TopoJSON}));break;case"TileJSON":g=new a.source.TileJSON({url:b.url,attributions:t(b),tileLoadFunction:b.tileLoadFunction,crossOrigin:"anonymous",wrapX:void 0===b.wrapX||b.wrapX});break;case"TileVector":b.url&&b.format||c.error("[AngularJS - Openlayers] - TileVector Layer needs valid url and format properties"),g=new a.source.VectorTile({url:b.url,projection:f,attributions:t(b),tileLoadFunction:b.tileLoadFunction,format:b.format,tileGrid:new a.tilegrid.createXYZ({maxZoom:b.maxZoom||19}),wrapX:void 0===b.wrapX||b.wrapX});break;case"TileTMS":b.url&&b.tileGrid||c.error("[AngularJS - Openlayers] - TileTMS Layer needs valid url and tileGrid properties"),g=new a.source.TileImage({url:b.url,maxExtent:b.maxExtent,attributions:t(b),tileLoadFunction:b.tileLoadFunction,tileGrid:new a.tilegrid.TileGrid({origin:b.tileGrid.origin,resolutions:b.tileGrid.resolutions}),tileUrlFunction:function(a){var c=a[0],d=a[1],e=a[2];return d<0||e<0?"":b.url+c+"/"+d+"/"+e+".png"},wrapX:void 0===b.wrapX||b.wrapX});break;case"TileImage":g=new a.source.TileImage({url:b.url,attributions:t(b),tileLoadFunction:b.tileLoadFunction,tileGrid:new a.tilegrid.TileGrid({origin:b.tileGrid.origin,resolutions:b.tileGrid.resolutions}),tileUrlFunction:function(a){var c=a[0],d=a[1],e=-a[2]-1;return b.url.replace("{z}",c.toString()).replace("{x}",d.toString()).replace("{y}",e.toString())},wrapX:void 0===b.wrapX||b.wrapX});break;case"KML":var B=b.extractStyles||!1;g=new a.source.Vector({url:b.url,format:new a.format.KML,radius:b.radius,extractStyles:B});break;case"Stamen":if(!b.layer||!q(b.layer))return void c.error("[AngularJS - Openlayers] - You need a valid Stamen layer.");g=new a.source.Stamen({tileLoadFunction:b.tileLoadFunction,layer:b.layer,wrapX:void 0===b.wrapX||b.wrapX});break;case"ImageStatic":if(!b.url||!angular.isArray(b.imageSize)||2!==b.imageSize.length)return void c.error("[AngularJS - Openlayers] - You need a image URL to create a ImageStatic layer.");g=new a.source.ImageStatic({url:b.url,attributions:t(b),imageSize:b.imageSize,projection:f,imageExtent:b.imageExtent?b.imageExtent:f.getExtent(),imageLoadFunction:b.imageLoadFunction});break;case"XYZ":b.url||b.tileUrlFunction||c.error("[AngularJS - Openlayers] - XYZ Layer needs valid url or tileUrlFunction properties"),g=new a.source.XYZ({url:b.url,attributions:t(b),minZoom:b.minZoom,maxZoom:b.maxZoom,projection:b.projection,tileUrlFunction:b.tileUrlFunction,tileLoadFunction:b.tileLoadFunction,wrapX:void 0===b.wrapX||b.wrapX});break;case"Zoomify":b.url&&angular.isArray(b.imageSize)&&2===b.imageSize.length||c.error("[AngularJS - Openlayers] - Zoomify Layer needs valid url and imageSize properties"),g=new a.source.Zoomify({url:b.url,size:b.imageSize,wrapX:void 0===b.wrapX||b.wrapX})}return g||c.warn('[AngularJS - Openlayers] - No source could be found for type "'+b.type+'"'),g},s=function(a){var b=a;if(a&&"object"==typeof a){b="[object Array]"===Object.prototype.toString.call(a)?[]:{};for(var c in a)b[c]=s(a[c])}return b},t=function(b){var c=[];if(e(b.attribution))!1!==b.attribution&&c.unshift(new a.Attribution({html:b.attribution}));else{var d=u(b);d&&c.unshift(d)}return c},u=function(b){if(b&&b.type){var c=a.source[b.type];if(c)for(var d in c)if(c.hasOwnProperty(d)&&d.toLowerCase().indexOf("attribution")>-1)return a.source[b.type][d]}return null},v=function(b){var c=new a.layer.Group;return c.set("name",b),c},w=function(b,c){var d;return angular.forEach(b,function(b){if(b instanceof a.layer.Group&&b.get("name")===c)return void(d=b)}),d},x=function(a,b){for(var c,d=0;d',controller:["$scope",function(a){var b=c.defer();a.getMap=function(){return b.promise},a.setMap=function(a){b.resolve(a)},this.getOpenlayersScope=function(){return a}}],link:function(b,c,d){var h=e.isDefined,i=e.createLayer,j=e.setMapEvents,k=e.setViewEvents,l=e.createView,m=f.setDefaults(b);h(d.width)&&(isNaN(d.width)?c.css("width",d.width):c.css("width",d.width+"px")),h(d.height)&&(isNaN(d.height)?c.css("height",d.height):c.css("height",d.height+"px")),h(d.lat)&&(m.center.lat=parseFloat(d.lat)),h(d.lon)&&(m.center.lon=parseFloat(d.lon)),h(d.zoom)&&(m.center.zoom=parseFloat(d.zoom));var n=a.control.defaults(m.controls),o=a.interaction.defaults(m.interactions),p=l(m.view),q=new a.Map({target:c[0],controls:n,interactions:o,renderer:m.renderer,view:p,loadTilesWhileAnimating:m.loadTilesWhileAnimating,loadTilesWhileInteracting:m.loadTilesWhileInteracting});if(b.$on("$destroy",function(){g.resetMap(d.id)}),!d.customLayers){var r={type:"Tile",source:{type:"OSM"}},s=i(r,p.getProjection(),"default");q.addLayer(s),q.set("default",!0)}if(!h(d.olCenter)){var t=a.proj.transform([m.center.lon,m.center.lat],m.center.projection,p.getProjection());p.setCenter(t),p.setZoom(m.center.zoom)}j(m.events,q,b),k(m.events,q,b),b.setMap(q),g.setMap(q,d.id)}}}]),angular.module("openlayers-directive").directive("olCenter",["$log","$location","olMapDefaults","olHelpers",function(b,c,d,e){return{restrict:"A",scope:!1,replace:!1,require:"openlayers",link:function(f,g,h,i){var j=e.safeApply,k=e.isValidCenter,l=e.isDefined,m=e.isArray,n=e.isNumber,o=e.isSameCenterOnMap,p=e.setCenter,q=e.setZoom,r=i.getOpenlayersScope();r.getMap().then(function(f){var g=d.getDefaults(r),i=f.getView(),s=r.center;if(h.olCenter.search("-")!==-1)return b.error('[AngularJS - Openlayers] The "center" variable can\'t use a "-" on his key name: "'+h.center+'".'),void p(i,g.view.projection,g.center,f);l(s)||(s={}),k(s)||(b.warn("[AngularJS - Openlayers] invalid 'center'"),s.lat=g.center.lat,s.lon=g.center.lon,s.zoom=g.center.zoom,s.projection=g.center.projection),s.projection||("pixel"!==g.view.projection?s.projection=g.center.projection:s.projection="pixel"),n(s.zoom)||(s.zoom=1),p(i,g.view.projection,s,f),i.setZoom(s.zoom);if(s.centerUrlHash===!0){var t=function(){var a,b=c.search();if(l(b.c)){var d=b.c.split(":");3===d.length&&(a={lat:parseFloat(d[0]),lon:parseFloat(d[1]),zoom:parseInt(d[2],10)})}return a};t(),r.$on("$locationChangeSuccess",function(){var a=t();a&&!o(a,f)&&j(r,function(b){b.center.lat=a.lat,b.center.lon=a.lon,b.center.zoom=a.zoom})})}var u;r.$watchCollection("center",function(c){if(c){if(c.projection||(c.projection=g.center.projection),c.autodiscover)return u||(u=new a.Geolocation({projection:a.proj.get(c.projection)}),u.on("change",function(){if(c.autodiscover){var a=u.getPosition();j(r,function(b){b.center.lat=a[1],b.center.lon=a[0],b.center.zoom=12,b.center.autodiscover=!1,u.setTracking(!1)})}})),void u.setTracking(!0);k(c)||(b.warn("[AngularJS - Openlayers] invalid 'center'"),c=g.center);var d=i.getCenter();if(d)if("pixel"===g.view.projection||"pixel"===c.projection)i.setCenter(c.coord);else{var e=a.proj.transform(d,g.view.projection,c.projection);e[1]===c.lat&&e[0]===c.lon||p(i,g.view.projection,c,f)}i.getZoom()!==c.zoom&&q(i,c.zoom,f)}});var v=f.on("moveend",function(){j(r,function(b){if(l(b.center)){var d=f.getView().getCenter();if(b.center.zoom=i.getZoom(),"pixel"===g.view.projection||"pixel"===b.center.projection)return void(b.center.coord=d);if(b.center){var h=a.proj.transform(d,g.view.projection,b.center.projection);if(b.center.lat=h[1],b.center.lon=h[0],e.notifyCenterUrlHashChanged(r,b.center,c.search()),m(b.center.bounds)){var j=i.calculateExtent(f.getSize()),k=b.center.projection,n=g.view.projection;b.center.bounds=a.proj.transformExtent(j,n,k)}}}})});r.$on("$destroy",function(){f.unByKey(v)})})}}}]),angular.module("openlayers-directive").directive("olLayer",["$log","$q","olMapDefaults","olHelpers",function(a,b,c,d){return{restrict:"E",scope:{properties:"=olLayerProperties",onLayerCreated:"&"},replace:!1,require:"^openlayers",link:function(a,b,e,f){var g=d.isDefined,h=d.equals,i=f.getOpenlayersScope(),j=d.createLayer,k=d.setVectorLayerEvents,l=d.detectLayerType,m=d.createStyle,n=d.isBoolean,o=d.addLayerBeforeMarkers,p=d.isNumber,q=d.insertLayer,r=d.removeLayer,s=d.addLayerToGroup,t=d.removeLayerFromGroup,u=d.getGroup;i.getMap().then(function(b){var d,f=b.getView().getProjection(),v=c.setDefaults(i),w=b.getLayers();if(a.$on("$destroy",function(){a.properties.group?t(w,d,a.properties.group):r(w,d.index),b.removeLayer(d)}),g(a.properties))a.$watch("properties",function(c,e){if(g(c.source)&&g(c.source.type)){if(!g(c.visible))return void(c.visible=!0);if(!g(c.opacity))return void(c.opacity=1);var i,x,y;if(g(d)){var z=function(a){return function(b){return b!==a}}(d);if(g(e)&&!h(c.source,e.source)){var A=d.index;y=w,x=d.get("group"),x&&(y=u(w,x).getLayers()),y.removeAt(A),d=j(c,f,a.onLayerCreated),d.set("group",x),g(d)&&(q(y,A,d),"Vector"===l(c)&&k(v.events,b,a,c.name))}(g(e)&&c.opacity!==e.opacity||z(d))&&(p(c.opacity)||p(parseFloat(c.opacity)))&&d.setOpacity(c.opacity),g(c.index)&&c.index!==d.index&&(y=w,x=d.get("group"),x&&(y=u(w,x).getLayers()),r(y,d.index),q(y,c.index,d)),g(c.group)&&c.group!==e.group&&(t(w,d,e.group),s(w,d,c.group)),g(e)&&n(c.visible)&&(c.visible!==e.visible||z(d)||d.getVisible()!==c.visible)&&d.setVisible(c.visible),(g(c.style)&&!h(c.style,e.style)||z(d))&&(i=angular.isFunction(c.style)?c.style:m(c.style),d.setStyle&&angular.isFunction(d.setStyle)&&d.setStyle(i)),h(c.minResolution,e.minResolution)&&!z(d)||g(c.minResolution)&&d.setMinResolution(c.minResolution),h(c.maxResolution,e.maxResolution)&&!z(d)||g(c.maxResolution)&&d.setMaxResolution(c.maxResolution)}else d=j(c,f,a.onLayerCreated),g(c.group)?s(w,d,c.group):g(c.index)?q(w,c.index,d):o(w,d),"Vector"===l(c)&&k(v.events,b,a,c.name),n(c.visible)&&d.setVisible(c.visible),c.opacity&&d.setOpacity(c.opacity),angular.isArray(c.extent)&&d.setExtent(c.extent),c.style&&(i=angular.isFunction(c.style)?c.style:m(c.style),d.setStyle&&angular.isFunction(d.setStyle)&&d.setStyle(i)),c.minResolution&&d.setMinResolution(c.minResolution),c.maxResolution&&d.setMaxResolution(c.maxResolution)}},!0);else if(g(e.sourceType)&&g(e.sourceUrl)){var x={source:{url:e.sourceUrl,type:e.sourceType}};d=j(x,f,e.layerName,a.onLayerCreated),"Vector"===l(x)&&k(v.events,b,a,e.name),o(w,d)}})}}}]),angular.module("openlayers-directive").directive("olPath",["$log","$q","olMapDefaults","olHelpers",function(a,b,c,d){return{restrict:"E",scope:{properties:"=olGeomProperties",style:"=olStyle"},require:"^openlayers",replace:!0,template:'',link:function(a,b,e,f){var g=d.isDefined,h=d.createFeature,i=d.createOverlay,j=d.createVectorLayer,k=d.insertLayer,l=d.removeLayer,m=f.getOpenlayersScope();m.getMap().then(function(d){var f=c.getDefaults(m),n=f.view.projection,o=j(),p=d.getLayers();if(k(p,p.getLength(),o),a.$on("$destroy",function(){l(p,o.index)}),g(e.coords)){var q=e.proj||"EPSG:4326",r=JSON.parse(e.coords),s={type:"Polygon",coords:r,projection:q,style:a.style?a.style:f.styles.path},t=h(s,n);if(o.getSource().addFeature(t),e.message){a.message=e.message;var u=t.getGeometry().getExtent(),v=i(b,u);d.addOverlay(v)}}else;})}}}]),angular.module("openlayers-directive").directive("olView",["$log","$q","olData","olMapDefaults","olHelpers",function(a,b,c,d,e){return{restrict:"A",scope:!1,replace:!1,require:"openlayers",link:function(a,b,c,f){var g=f.getOpenlayersScope(),h=e.isNumber,i=e.safeApply,j=e.createView;g.getMap().then(function(a){var b=d.getDefaults(g),c=g.view;c.projection||(c.projection=b.view.projection),c.maxZoom||(c.maxZoom=b.view.maxZoom),c.minZoom||(c.minZoom=b.view.minZoom),c.rotation||(c.rotation=b.view.rotation);var e=j(c);a.setView(e),g.$watchCollection("view",function(a){h(a.rotation)&&e.setRotation(a.rotation)});var f=e.on("change:rotation",function(){i(g,function(b){b.view.rotation=a.getView().getRotation()})});g.$on("$destroy",function(){a.unByKey(f)})})}}}]),angular.module("openlayers-directive").directive("olControl",["$log","$q","olData","olMapDefaults","olHelpers",function(a,b,c,d,e){return{restrict:"E",scope:{properties:"=olControlProperties"},replace:!1,require:"^openlayers",link:function(a,b,c,d){var f,g,h=e.isDefined,i=d.getOpenlayersScope(),j=e.getControlClasses,k=j();i.getMap().then(function(b){function d(a){a&&a.control?(f&&b.removeControl(f),f=a.control,b.addControl(f)):c.name&&(h(a)&&(g=a),f&&b.removeControl(f),f=new k[c.name](g),b.addControl(f))}a.$on("$destroy",function(){b.removeControl(f)}),a.$watch("properties",function(a){h(a)&&d(a)}),d(a.properties)})}}}]),angular.module("openlayers-directive").directive("olMarker",["$log","$q","olMapDefaults","olHelpers",function(b,c,d,e){var f=function(){return{projection:"EPSG:4326",lat:0,lon:0,coord:[],show:!0,showOnMouseOver:!1,showOnMouseClick:!1,keepOneOverlayVisible:!1}},g=function(){function a(a){return b.map(function(a){return a.map}).indexOf(a)}var b=[];return{getInst:function(c,d){var f=a(d);if(f===-1){var g=e.createVectorLayer();g.set("markers",!0),d.addLayer(g),b.push({map:d,markerLayer:g,instScopes:[]}),f=b.length-1}return b[f].instScopes.push(c),b[f].markerLayer},deregisterScope:function(c,d){var e=a(d);if(e===-1)throw Error("This map has no markers");var f=b[e].instScopes,g=f.indexOf(c);if(g===-1)throw Error("Scope wan't registered");f.splice(g,1),f.length||(d.removeLayer(b[e].markerLayer),delete b[e].markerLayer,delete b[e])}}}();return{restrict:"E",scope:{lat:"=lat",lon:"=lon",label:"=label",properties:"=olMarkerProperties",style:"=olStyle"},transclude:!0,require:"^openlayers",replace:!0,template:'',link:function(c,h,i,j){var k=e.isDefined,l=j.getOpenlayersScope(),m=e.createFeature,n=e.createOverlay,o=h.find("ng-transclude").children().length>0;l.getMap().then(function(e){function j(){c.properties&&(e.getViewport().removeEventListener("mousemove",c.properties.handleInteraction),e.getViewport().removeEventListener("click",c.properties.handleTapInteraction),e.getViewport().querySelector("canvas.ol-unselectable").removeEventListener("touchend",c.properties.handleTapInteraction),e.getViewport().removeEventListener("mousemove",c.properties.showAtLeastOneOverlay),e.getViewport().removeEventListener("click",c.properties.removeAllOverlays),e.getViewport().querySelector("canvas.ol-unselectable").removeEventListener("touchmove",c.properties.activateCooldown))}var p,q,r,s=g.getInst(c,e),t=f(),u=d.getDefaults(l),v=u.view.projection,w=null,x=null;if(c.handleDrag=function(b){var d=b.coordinate,f=e.getView().getProjection().getCode();if(d="pixel"===f?d.map(function(a){return parseInt(a,10)}):a.proj.transform(d,f,"EPSG:4326"),"pointerdown"===b.type){var g=e.forEachFeatureAtPixel(b.pixel,function(a){return a});if(!(x=g?g.get("marker"):null)||!x.draggable)return void(x=null);e.getTarget().style.cursor="pointer",w="pixel"===f?[d[0]-x.coord[0],d[1]-x.coord[1]]:[d[0]-x.lon,d[1]-x.lat],b.preventDefault()}else w&&x&&("pointerup"===b.type?(e.getTarget().style.cursor="",w=null,x=null,b.preventDefault()):"pointerdrag"===b.type&&(b.preventDefault(),c.$apply(function(){"pixel"===f?(x.coord[0]=d[0]-w[0],x.coord[1]=d[1]-w[1]):(x.lon=d[0]-w[0],x.lat=d[1]-w[1])})))},e.on("pointerdown",c.handleDrag),e.on("pointerup",c.handleDrag),e.on("pointerdrag",c.handleDrag),c.$on("$destroy",function(){s.getSource().removeFeature(r),k(p)&&e.removeOverlay(p),g.deregisterScope(c,e),e.un("pointerdown",c.handleDrag),e.un("pointerup",c.handleDrag),e.un("pointerdrag",c.handleDrag),j()}),!k(c.properties))return t.lat=c.lat?c.lat:t.lat,t.lon=c.lon?c.lon:t.lon,t.message=i.message,t.style=c.style?c.style:u.styles.marker,r=m(t,v),k(r)||b.error("[AngularJS - Openlayers] Received invalid data on the marker."),r.set("marker",c),s.getSource().addFeature(r),void((t.message||o)&&(c.message=i.message,q=a.proj.transform([t.lon,t.lat],t.projection,v),p=n(h,q),e.addOverlay(p)));c.$watch("properties",function(d){if(j(),d.handleInteraction=function(b){var c=!1;if(i.hasOwnProperty("ngClick")&&(c=!0),!d.label.show||c){var f=!1,g=e.getEventPixel(b),j=e.forEachFeatureAtPixel(g,function(a){return a}),l=!1;if(j===r){if(l=!0,f=!0,c&&("click"===b.type||"touchend"===b.type))return h.triggerHandler("click"),b.preventDefault(),void b.stopPropagation();k(p)||(q="pixel"===t.projection?d.coord:a.proj.transform([d.lon,d.lat],t.projection,v),p=n(h,q),e.addOverlay(p)),e.getTarget().style.cursor="pointer"}!f&&p&&(l=!0,e.removeOverlay(p),p=void 0,e.getTarget().style.cursor=""),l&&b.preventDefault()}},d.handleTapInteraction=function(){var a,b=!1;return d.activateCooldown=function(){b=!0,a&&clearTimeout(a),a=setTimeout(function(){b=!1,a=null},500)},d.activateCooldown&&e.getViewport().querySelector("canvas.ol-unselectable").removeEventListener("touchmove",d.activateCooldown),e.getViewport().querySelector("canvas.ol-unselectable").addEventListener("touchmove",d.activateCooldown),function(){b||(d.handleInteraction.apply(null,arguments),d.activateCooldown())}}(),d.showAtLeastOneOverlay=function(b){if(!d.label.show){var c=!1,f=e.getEventPixel(b),g=e.forEachFeatureAtPixel(f,function(a){return a}),i=!1;g===r&&(i=!0,c=!0,k(p)||(q="pixel"===t.projection?t.coord:a.proj.transform([t.lon,t.lat],t.projection,v),p=n(h,q),angular.forEach(e.getOverlays(),function(a){e.removeOverlay(a)}),e.addOverlay(p)),e.getTarget().style.cursor="pointer"),!c&&p&&(i=!0,p=void 0,e.getTarget().style.cursor=""),i&&b.preventDefault()}},d.removeAllOverlays=function(a){angular.forEach(e.getOverlays(),function(a){e.removeOverlay(a)}),a.preventDefault()},k(r)){var f;if(f="pixel"===d.projection?d.coord:a.proj.transform([d.lon,d.lat],t.projection,e.getView().getProjection()),!angular.equals(r.getGeometry().getCoordinates(),f)){var g=new a.geom.Point(f);r.setGeometry(g)}}else t.projection=d.projection?d.projection:t.projection,t.coord=d.coord?d.coord:t.coord,t.lat=d.lat?d.lat:t.lat,t.lon=d.lon?d.lon:t.lon,k(d.style)?t.style=d.style:t.style=u.styles.marker,r=m(t,v),k(r)||b.error("[AngularJS - Openlayers] Received invalid data on the marker."),r.set("marker",d),s.getSource().addFeature(r);k(p)&&e.removeOverlay(p),k(d.label)&&(c.message=d.label.message,(o||k(c.message)&&0!==c.message.length)&&(d.label&&d.label.show===!0&&(q="pixel"===t.projection?t.coord:a.proj.transform([d.lon,d.lat],t.projection,v),p=n(h,q),e.addOverlay(p)),p&&d.label&&d.label.show===!1&&(e.removeOverlay(p),p=void 0),d.label&&d.label.show===!1&&d.label.showOnMouseOver&&e.getViewport().addEventListener("mousemove",d.handleInteraction),(d.label&&d.label.show===!1&&d.label.showOnMouseClick||i.hasOwnProperty("ngClick"))&&(e.getViewport().addEventListener("click",d.handleTapInteraction),e.getViewport().querySelector("canvas.ol-unselectable").addEventListener("touchend",d.handleTapInteraction)),d.label&&d.label.show===!1&&d.label.keepOneOverlayVisible&&(e.getViewport().addEventListener("mousemove",d.showAtLeastOneOverlay),e.getViewport().addEventListener("click",d.removeAllOverlays))))},!0)})}}}]),angular.module("openlayers-directive").service("olData",["$log","$q",function(a,b){function c(b,c){var d,e;if(angular.isDefined(c))d=c;else if(1===Object.keys(b).length)for(e in b)b.hasOwnProperty(e)&&(d=e);else 0===Object.keys(b).length?d="main":a.error("[AngularJS - Openlayers] - You have more than 1 map on the DOM, you must provide the map ID to the olData.getXXX call");return d}var d={},e=function(a,b){a[c(a,b)].resolvedDefer=!0},f=function(a,d){var e,f=c(a,d);return angular.isDefined(a[f])&&a[f].resolvedDefer!==!0?e=a[f].defer:(e=b.defer(),a[f]={defer:e,resolvedDefer:!1}),e},g=function(a,b){var d=c(a,b);return angular.isDefined(a[d])&&a[d].resolvedDefer!==!1?a[d].defer:f(a,b)};this.setMap=function(a,b){f(d,b).resolve(a),e(d,b)},this.getMap=function(a){return g(d,a).promise},this.resetMap=function(a){angular.isDefined(d[a])&&delete d[a]}}]),angular.module("openlayers-directive").factory("olHelpers",["$q","$log","$http",function(b,c,d){var e=function(a){return angular.isDefined(a)},f=function(a){return angular.isDefined(a)&&null!==a},g=function(a,b,c){a.on(b,function(d){var e=d.coordinate,f=a.getView().getProjection().getCode();"pixel"===f&&(e=e.map(function(a){return parseInt(a,10)})),c.$emit("openlayers.map."+b,{coord:e,projection:f,event:d})})},h=["Road","Aerial","AerialWithLabels","collinsBart","ordnanceSurvey"],i=function(){return{attribution:a.control.Attribution,fullscreen:a.control.FullScreen,mouseposition:a.control.MousePosition,overviewmap:a.control.OverviewMap,rotate:a.control.Rotate,scaleline:a.control.ScaleLine,zoom:a.control.Zoom,zoomslider:a.control.ZoomSlider,zoomtoextent:a.control.ZoomToExtent}},j=["osm","sat","hyb"],k=["World_Imagery","World_Street_Map","World_Topo_Map","World_Physical_Map","World_Terrain_Base","Ocean_Basemap","NatGeo_World_Map"],l={style:a.style.Style,fill:a.style.Fill,stroke:a.style.Stroke,circle:a.style.Circle,icon:a.style.Icon,image:a.style.Image,regularshape:a.style.RegularShape,text:a.style.Text},m=function(a,b){return b&&a instanceof b?a:b?new b(a):a},n=function a(b,c){var d;if(c?d=b[c]:(c="style",d=b),"style"===c&&b instanceof Function)return b;if(!(d instanceof Object))return d;var e;if("[object Object]"===Object.prototype.toString.call(d)){e={};var f=l[c];if(f&&d instanceof f)return d;Object.getOwnPropertyNames(d).forEach(function(b,g,h){var i=l[b];if(f&&i&&i.prototype instanceof l[c])return console.assert(1===h.length,"Extra parameters for "+c),e=a(d,b),m(e,i);e[b]=a(d,b),"text"!==b&&"string"!=typeof e[b]&&(e[b]=m(e[b],l[b]))})}else e=d;return m(e,l[c])},o=function(a){if(a.type)return a.type;switch(a.source.type){case"ImageWMS":return"Image";case"ImageStatic":return"Image";case"GeoJSON":case"JSONP":case"TopoJSON":case"KML":case"WKT":return"Vector";case"TileVector":case"MVT":return"TileVector";default:return"Tile"}},p=function(b){var d;switch(b.projection){case"pixel":if(!e(b.extent))return void c.error("[AngularJS - Openlayers] - You must provide the extent of the image if using pixel projection");d=new a.proj.Projection({code:"pixel",units:"pixels",extent:b.extent});break;default:d=new a.proj.get(b.projection)}return d},q=function(a){return["watercolor","terrain","toner"].indexOf(a)!==-1},r=function(b,f){var g,i,l,m=new a.format.GeoJSON;switch(b.type){case"MapBox":if(!b.mapId||!b.accessToken)return void c.error("[AngularJS - Openlayers] - MapBox layer requires the map id and the access token");l="https://api.tiles.mapbox.com/v4/"+b.mapId+"/{z}/{x}/{y}.png?access_token="+b.accessToken,i=window.devicePixelRatio,i>1&&(l=l.replace(".png","@2x.png")),g=new a.source.XYZ({url:l,tileLoadFunction:b.tileLoadFunction,attributions:t(b),tilePixelRatio:i>1?2:1,wrapX:void 0===b.wrapX||b.wrapX});break;case"MapBoxStudio":if(!b.mapId||!b.accessToken||!b.userId)return void c.error("[AngularJS - Openlayers] - MapBox Studio layer requires the map id, user id and the access token");l="https://api.mapbox.com/styles/v1/"+b.userId+"/"+b.mapId+"/tiles/{z}/{x}/{y}?access_token="+b.accessToken,i=window.devicePixelRatio,i>1&&(l=l.replace("{y}?access_token","{y}@2x?access_token")),g=new a.source.XYZ({url:l,tileLoadFunction:b.tileLoadFunction,attributions:t(b),tilePixelRatio:i>1?2:1,tileSize:b.tileSize||[512,512],wrapX:void 0===b.wrapX||b.wrapX});break;case"MVT":if(!b.url)return void c.error("[AngularJS - Openlayers] - MVT layer requires the source url");g=new a.source.VectorTile({attributions:b.attributions||"",format:new a.format.MVT,tileGrid:a.tilegrid.createXYZ({maxZoom:b.maxZoom||22}),tilePixelRatio:b.tilePixelRatio||16,url:b.url});break;case"ImageWMS":b.url&&b.params||c.error("[AngularJS - Openlayers] - ImageWMS Layer needs valid server url and params properties"),g=new a.source.ImageWMS({url:b.url,imageLoadFunction:b.imageLoadFunction,attributions:t(b),crossOrigin:void 0===b.crossOrigin?"anonymous":b.crossOrigin,params:s(b.params),ratio:b.ratio});break;case"TileWMS":(b.url||b.urls)&&b.params||c.error("[AngularJS - Openlayers] - TileWMS Layer needs valid url (or urls) and params properties");var n={tileLoadFunction:b.tileLoadFunction,crossOrigin:void 0===b.crossOrigin?"anonymous":b.crossOrigin,params:s(b.params),attributions:t(b),wrapX:void 0===b.wrapX||b.wrapX};b.serverType&&(n.serverType=b.serverType),b.url&&(n.url=b.url),b.urls&&(n.urls=b.urls),g=new a.source.TileWMS(n);break;case"WMTS":(b.url||b.urls)&&b.tileGrid||c.error("[AngularJS - Openlayers] - WMTS Layer needs valid url (or urls) and tileGrid properties");var o={tileLoadFunction:b.tileLoadFunction,projection:f,layer:b.layer,attributions:t(b),matrixSet:"undefined"===b.matrixSet?f:b.matrixSet,format:"undefined"===b.format?"image/jpeg":b.format,requestEncoding:"undefined"===b.requestEncoding?"KVP":b.requestEncoding,tileGrid:new a.tilegrid.WMTS({origin:b.tileGrid.origin,resolutions:b.tileGrid.resolutions,matrixIds:b.tileGrid.matrixIds}),style:"undefined"===b.style?"normal":b.style,wrapX:void 0===b.wrapX||b.wrapX};e(b.url)&&(o.url=b.url),e(b.urls)&&(o.urls=b.urls),g=new a.source.WMTS(o);break;case"OSM":g=new a.source.OSM({tileLoadFunction:b.tileLoadFunction,attributions:t(b),wrapX:void 0===b.wrapX||b.wrapX}),b.url&&g.setUrl(b.url);break;case"BingMaps":if(!b.key)return void c.error("[AngularJS - Openlayers] - You need an API key to show the Bing Maps.");var p={key:b.key,tileLoadFunction:b.tileLoadFunction,attributions:t(b),imagerySet:b.imagerySet?b.imagerySet:h[0],culture:b.culture,wrapX:void 0===b.wrapX||b.wrapX};b.maxZoom&&(p.maxZoom=b.maxZoom),g=new a.source.BingMaps(p);break;case"MapQuest":if(!b.layer||j.indexOf(b.layer)===-1)return void c.error("[AngularJS - Openlayers] - MapQuest layers needs a valid 'layer' property.");g=new a.source.MapQuest({attributions:t(b),layer:b.layer,wrapX:void 0===b.wrapX||b.wrapX});break;case"EsriBaseMaps":if(!b.layer||k.indexOf(b.layer)===-1)return void c.error("[AngularJS - Openlayers] - ESRI layers needs a valid 'layer' property.");var r="http://services.arcgisonline.com/ArcGIS/rest/services/",u=r+b.layer+"/MapServer/tile/{z}/{y}/{x}";g=new a.source.XYZ({attributions:t(b),tileLoadFunction:b.tileLoadFunction,url:u,wrapX:void 0===b.wrapX||b.wrapX});break;case"TileArcGISRest":b.url||c.error("[AngularJS - Openlayers] - TileArcGISRest Layer needs valid url"),g=new a.source.TileArcGISRest({attributions:t(b),tileLoadFunction:b.tileLoadFunction,url:b.url,wrapX:void 0===b.wrapX||b.wrapX});break;case"GeoJSON":if(!b.geojson&&!b.url)return void c.error("[AngularJS - Openlayers] - You need a geojson property to add a GeoJSON layer.");if(e(b.url))g=new a.source.Vector({format:new a.format.GeoJSON,url:b.url});else{g=new a.source.Vector;var v,w=f;v=e(b.geojson.projection)?new a.proj.get(b.geojson.projection):f;var x=m.readFeatures(b.geojson.object,{featureProjection:w.getCode(),dataProjection:v.getCode()});g.addFeatures(x)}break;case"WKT":if(!b.wkt&&!b.wkt.data)return void c.error("[AngularJS - Openlayers] - You need a WKT property to add a WKT format vector layer.");g=new a.source.Vector;var y,z=new a.format.WKT;y=e(b.wkt.projection)?new a.proj.get(b.wkt.projection):f;var A=z.readFeatures(b.wkt.data,{featureProjection:f.getCode(),dataProjection:y.getCode()});g.addFeatures(A);break;case"JSONP":if(!b.url)return void c.error("[AngularJS - Openlayers] - You need an url properly configured to add a JSONP layer.");e(b.url)&&(g=new a.source.ServerVector({format:m,loader:function(){var a=b.url+"&outputFormat=text/javascript&format_options=callback:JSON_CALLBACK";d.jsonp(a,{cache:b.cache}).success(function(a){g.addFeatures(m.readFeatures(a))}).error(function(a){c(a)})},projection:f}));break;case"TopoJSON":if(!b.topojson&&!b.url)return void c.error("[AngularJS - Openlayers] - You need a topojson property to add a TopoJSON layer.");g=b.url?new a.source.Vector({format:new a.format.TopoJSON,url:b.url}):new a.source.Vector(angular.extend(b.topojson,{format:new a.format.TopoJSON}));break;case"TileJSON":g=new a.source.TileJSON({url:b.url,attributions:t(b),tileLoadFunction:b.tileLoadFunction,crossOrigin:"anonymous",wrapX:void 0===b.wrapX||b.wrapX});break;case"TileVector":b.url&&b.format||c.error("[AngularJS - Openlayers] - TileVector Layer needs valid url and format properties"),g=new a.source.VectorTile({url:b.url,projection:f,attributions:t(b),tileLoadFunction:b.tileLoadFunction,format:b.format,tileGrid:new a.tilegrid.createXYZ({maxZoom:b.maxZoom||19}),wrapX:void 0===b.wrapX||b.wrapX});break;case"TileTMS":b.url&&b.tileGrid||c.error("[AngularJS - Openlayers] - TileTMS Layer needs valid url and tileGrid properties"),g=new a.source.TileImage({url:b.url,maxExtent:b.maxExtent,attributions:t(b),tileLoadFunction:b.tileLoadFunction,tileGrid:new a.tilegrid.TileGrid({origin:b.tileGrid.origin,resolutions:b.tileGrid.resolutions}),tileUrlFunction:function(a){var c=a[0],d=a[1],e=a[2];return d<0||e<0?"":b.url+c+"/"+d+"/"+e+".png"},wrapX:void 0===b.wrapX||b.wrapX});break;case"TileImage":g=new a.source.TileImage({url:b.url,attributions:t(b),tileLoadFunction:b.tileLoadFunction,tileGrid:new a.tilegrid.TileGrid({origin:b.tileGrid.origin,resolutions:b.tileGrid.resolutions}),tileUrlFunction:function(a){var c=a[0],d=a[1],e=-a[2]-1;return b.url.replace("{z}",c.toString()).replace("{x}",d.toString()).replace("{y}",e.toString())},wrapX:void 0===b.wrapX||b.wrapX});break;case"KML":var B=b.extractStyles||!1;g=new a.source.Vector({url:b.url,format:new a.format.KML,radius:b.radius,extractStyles:B});break;case"Stamen":if(!b.layer||!q(b.layer))return void c.error("[AngularJS - Openlayers] - You need a valid Stamen layer.");g=new a.source.Stamen({tileLoadFunction:b.tileLoadFunction,layer:b.layer,wrapX:void 0===b.wrapX||b.wrapX});break;case"ImageStatic":if(!b.url||!angular.isArray(b.imageSize)||2!==b.imageSize.length)return void c.error("[AngularJS - Openlayers] - You need a image URL to create a ImageStatic layer.");g=new a.source.ImageStatic({url:b.url,attributions:t(b),imageSize:b.imageSize,projection:f,imageExtent:b.imageExtent?b.imageExtent:f.getExtent(),imageLoadFunction:b.imageLoadFunction});break;case"XYZ":b.url||b.tileUrlFunction||c.error("[AngularJS - Openlayers] - XYZ Layer needs valid url or tileUrlFunction properties"),g=new a.source.XYZ({url:b.url,attributions:t(b),minZoom:b.minZoom,maxZoom:b.maxZoom,projection:b.projection,tileUrlFunction:b.tileUrlFunction,tileLoadFunction:b.tileLoadFunction,wrapX:void 0===b.wrapX||b.wrapX});break;case"Zoomify":b.url&&angular.isArray(b.imageSize)&&2===b.imageSize.length||c.error("[AngularJS - Openlayers] - Zoomify Layer needs valid url and imageSize properties"),g=new a.source.Zoomify({url:b.url,size:b.imageSize,wrapX:void 0===b.wrapX||b.wrapX})}return g||c.warn('[AngularJS - Openlayers] - No source could be found for type "'+b.type+'"'),g},s=function(a){var b=a;if(a&&"object"==typeof a){b="[object Array]"===Object.prototype.toString.call(a)?[]:{};for(var c in a)b[c]=s(a[c])}return b},t=function(b){var c=[];return e(b.attribution)&&c.unshift(new a.Attribution({html:b.attribution})),c},u=function(b){var c=new a.layer.Group;return c.set("name",b),c},v=function(b,c){var d;return angular.forEach(b,function(b){if(b instanceof a.layer.Group&&b.get("name")===c)return void(d=b)}),d},w=function(a,b){for(var c,d=0;d',controller:["$scope",function(a){var b=c.defer();a.getMap=function(){return b.promise},a.setMap=function(a){b.resolve(a)},this.getOpenlayersScope=function(){return a}}],link:function(b,c,d){var h=e.isDefined,i=e.createLayer,j=e.setMapEvents,k=e.setViewEvents,l=e.createView,m=f.setDefaults(b);h(d.width)&&(isNaN(d.width)?c.css("width",d.width):c.css("width",d.width+"px")),h(d.height)&&(isNaN(d.height)?c.css("height",d.height):c.css("height",d.height+"px")),h(d.lat)&&(m.center.lat=parseFloat(d.lat)),h(d.lon)&&(m.center.lon=parseFloat(d.lon)),h(d.zoom)&&(m.center.zoom=parseFloat(d.zoom));var n=a.control.defaults(m.controls),o=a.interaction.defaults(m.interactions),p=l(m.view),q=new a.Map({target:c[0],controls:n,interactions:o,renderer:m.renderer,view:p,loadTilesWhileAnimating:m.loadTilesWhileAnimating,loadTilesWhileInteracting:m.loadTilesWhileInteracting});if(b.$on("$destroy",function(){g.resetMap(d.id)}),!d.customLayers){var r={type:"Tile",source:{type:"OSM"}},s=i(r,p.getProjection(),"default");q.addLayer(s),q.set("default",!0)}if(!h(d.olCenter)){var t=a.proj.transform([m.center.lon,m.center.lat],m.center.projection,p.getProjection());p.setCenter(t),p.setZoom(m.center.zoom)}j(m.events,q,b),k(m.events,q,b),b.setMap(q),g.setMap(q,d.id)}}}]),angular.module("openlayers-directive").directive("olCenter",["$log","$location","olMapDefaults","olHelpers",function(b,c,d,e){return{restrict:"A",scope:!1,replace:!1,require:"openlayers",link:function(f,g,h,i){var j=e.safeApply,k=e.isValidCenter,l=e.isDefined,m=e.isArray,n=e.isNumber,o=e.isSameCenterOnMap,p=e.setCenter,q=e.setZoom,r=i.getOpenlayersScope();r.getMap().then(function(f){var g=d.getDefaults(r),i=f.getView(),s=r.center;if(-1!==h.olCenter.search("-"))return b.error('[AngularJS - Openlayers] The "center" variable can\'t use a "-" on his key name: "'+h.center+'".'),void p(i,g.view.projection,g.center,f);l(s)||(s={}),k(s)||(b.warn("[AngularJS - Openlayers] invalid 'center'"),s.lat=g.center.lat,s.lon=g.center.lon,s.zoom=g.center.zoom,s.projection=g.center.projection),s.projection||("pixel"!==g.view.projection?s.projection=g.center.projection:s.projection="pixel"),n(s.zoom)||(s.zoom=1),p(i,g.view.projection,s,f),i.setZoom(s.zoom);if(!0===s.centerUrlHash){var t=function(){var a,b=c.search();if(l(b.c)){var d=b.c.split(":");3===d.length&&(a={lat:parseFloat(d[0]),lon:parseFloat(d[1]),zoom:parseInt(d[2],10)})}return a};t(),r.$on("$locationChangeSuccess",function(){var a=t();a&&!o(a,f)&&j(r,function(b){b.center.lat=a.lat,b.center.lon=a.lon,b.center.zoom=a.zoom})})}var u;r.$watchCollection("center",function(c){if(c){if(c.projection||(c.projection=g.center.projection),c.autodiscover)return u||(u=new a.Geolocation({projection:a.proj.get(c.projection)}),u.on("change",function(){if(c.autodiscover){var a=u.getPosition();j(r,function(b){b.center.lat=a[1],b.center.lon=a[0],b.center.zoom=12,b.center.autodiscover=!1,u.setTracking(!1)})}})),void u.setTracking(!0);k(c)||(b.warn("[AngularJS - Openlayers] invalid 'center'"),c=g.center);var d=i.getCenter();if(d)if("pixel"===g.view.projection||"pixel"===c.projection)i.setCenter(c.coord);else{var e=a.proj.transform(d,g.view.projection,c.projection);e[1]===c.lat&&e[0]===c.lon||p(i,g.view.projection,c,f)}i.getZoom()!==c.zoom&&q(i,c.zoom,f)}});var v=f.on("moveend",function(){j(r,function(b){if(l(b.center)){var d=f.getView().getCenter();if(b.center.zoom=i.getZoom(),"pixel"===g.view.projection||"pixel"===b.center.projection)return void(b.center.coord=d);if(b.center){var h=a.proj.transform(d,g.view.projection,b.center.projection);if(b.center.lat=h[1],b.center.lon=h[0],e.notifyCenterUrlHashChanged(r,b.center,c.search()),m(b.center.bounds)){var j=i.calculateExtent(f.getSize()),k=b.center.projection,n=g.view.projection;b.center.bounds=a.proj.transformExtent(j,n,k)}}}})});r.$on("$destroy",function(){f.unByKey(v)})})}}}]),angular.module("openlayers-directive").directive("olLayer",["$log","$q","olMapDefaults","olHelpers",function(a,b,c,d){return{restrict:"E",scope:{properties:"=olLayerProperties",onLayerCreated:"&"},replace:!1,require:"^openlayers",link:function(a,b,e,f){var g=d.isDefined,h=d.equals,i=f.getOpenlayersScope(),j=d.createLayer,k=d.setVectorLayerEvents,l=d.detectLayerType,m=d.createStyle,n=d.isBoolean,o=d.addLayerBeforeMarkers,p=d.isNumber,q=d.insertLayer,r=d.removeLayer,s=d.addLayerToGroup,t=d.removeLayerFromGroup,u=d.getGroup;i.getMap().then(function(b){var d,f=b.getView().getProjection(),v=c.setDefaults(i),w=b.getLayers();if(a.$on("$destroy",function(){a.properties.group?t(w,d,a.properties.group):r(w,d.index),b.removeLayer(d)}),g(a.properties))a.$watch("properties",function(c,e){if(g(c.source)&&g(c.source.type)){if(!g(c.visible))return void(c.visible=!0);if(!g(c.opacity))return void(c.opacity=1);var i,x,y;if(g(d)){var z=function(a){return function(b){return b!==a}}(d);if(g(e)&&!h(c.source,e.source)){var A=d.index;y=w,x=d.get("group"),x&&(y=u(w,x).getLayers()),y.removeAt(A),d=j(c,f,a.onLayerCreated),d.set("group",x),g(d)&&(q(y,A,d),"Vector"===l(c)&&k(v.events,b,a,c.name))}(g(e)&&c.opacity!==e.opacity||z(d))&&(p(c.opacity)||p(parseFloat(c.opacity)))&&d.setOpacity(c.opacity),g(c.index)&&c.index!==d.index&&(y=w,x=d.get("group"),x&&(y=u(w,x).getLayers()),r(y,d.index),q(y,c.index,d)),g(c.group)&&c.group!==e.group&&(t(w,d,e.group),s(w,d,c.group)),g(e)&&n(c.visible)&&(c.visible!==e.visible||z(d)||d.getVisible()!==c.visible)&&d.setVisible(c.visible),(g(c.style)&&!h(c.style,e.style)||z(d))&&(i=angular.isFunction(c.style)?c.style:m(c.style),d.setStyle&&angular.isFunction(d.setStyle)&&d.setStyle(i)),h(c.minResolution,e.minResolution)&&!z(d)||g(c.minResolution)&&d.setMinResolution(c.minResolution),h(c.maxResolution,e.maxResolution)&&!z(d)||g(c.maxResolution)&&d.setMaxResolution(c.maxResolution)}else d=j(c,f,a.onLayerCreated),g(c.group)?s(w,d,c.group):g(c.index)?q(w,c.index,d):o(w,d),"Vector"===l(c)&&k(v.events,b,a,c.name),n(c.visible)&&d.setVisible(c.visible),c.opacity&&d.setOpacity(c.opacity),angular.isArray(c.extent)&&d.setExtent(c.extent),c.style&&(i=angular.isFunction(c.style)?c.style:m(c.style),d.setStyle&&angular.isFunction(d.setStyle)&&d.setStyle(i)),c.minResolution&&d.setMinResolution(c.minResolution),c.maxResolution&&d.setMaxResolution(c.maxResolution)}},!0);else if(g(e.sourceType)&&g(e.sourceUrl)){var x={source:{url:e.sourceUrl,type:e.sourceType}};d=j(x,f,e.layerName,a.onLayerCreated),"Vector"===l(x)&&k(v.events,b,a,e.name),o(w,d)}})}}}]),angular.module("openlayers-directive").directive("olPath",["$log","$q","olMapDefaults","olHelpers",function(a,b,c,d){return{restrict:"E",scope:{properties:"=olGeomProperties",style:"=olStyle"},require:"^openlayers",replace:!0,template:'',link:function(a,b,e,f){var g=d.isDefined,h=d.createFeature,i=d.createOverlay,j=d.createVectorLayer,k=d.insertLayer,l=d.removeLayer,m=f.getOpenlayersScope();m.getMap().then(function(d){var f=c.getDefaults(m),n=f.view.projection,o=j(),p=d.getLayers();if(k(p,p.getLength(),o),a.$on("$destroy",function(){l(p,o.index)}),g(e.coords)){var q=e.proj||"EPSG:4326",r=JSON.parse(e.coords),s={type:"Polygon",coords:r,projection:q,style:a.style?a.style:f.styles.path},t=h(s,n);if(o.getSource().addFeature(t),e.message){a.message=e.message;var u=t.getGeometry().getExtent(),v=i(b,u);d.addOverlay(v)}}else;})}}}]),angular.module("openlayers-directive").directive("olView",["$log","$q","olData","olMapDefaults","olHelpers",function(a,b,c,d,e){return{restrict:"A",scope:!1,replace:!1,require:"openlayers",link:function(a,b,c,f){var g=f.getOpenlayersScope(),h=e.isNumber,i=e.safeApply,j=e.createView;g.getMap().then(function(a){var b=d.getDefaults(g),c=g.view;c.projection||(c.projection=b.view.projection),c.maxZoom||(c.maxZoom=b.view.maxZoom),c.minZoom||(c.minZoom=b.view.minZoom),c.rotation||(c.rotation=b.view.rotation);var e=j(c);a.setView(e),g.$watchCollection("view",function(a){h(a.rotation)&&e.setRotation(a.rotation)});var f=e.on("change:rotation",function(){i(g,function(b){b.view.rotation=a.getView().getRotation()})});g.$on("$destroy",function(){a.unByKey(f)})})}}}]),angular.module("openlayers-directive").directive("olControl",["$log","$q","olData","olMapDefaults","olHelpers",function(a,b,c,d,e){return{restrict:"E",scope:{properties:"=olControlProperties"},replace:!1,require:"^openlayers",link:function(a,b,c,d){var f,g,h=e.isDefined,i=d.getOpenlayersScope(),j=e.getControlClasses,k=j();i.getMap().then(function(b){function d(a){a&&a.control?(f&&b.removeControl(f),f=a.control,b.addControl(f)):c.name&&(h(a)&&(g=a),f&&b.removeControl(f),f=new k[c.name](g),b.addControl(f))}a.$on("$destroy",function(){b.removeControl(f)}),a.$watch("properties",function(a){h(a)&&d(a)}),d(a.properties)})}}}]),angular.module("openlayers-directive").directive("olMarker",["$log","$q","olMapDefaults","olHelpers",function(b,c,d,e){var f=function(){return{projection:"EPSG:4326",lat:0,lon:0,coord:[],show:!0,showOnMouseOver:!1,showOnMouseClick:!1,keepOneOverlayVisible:!1}},g=function(){function a(a){return b.map(function(a){return a.map}).indexOf(a)}var b=[];return{getInst:function(c,d){var f=a(d);if(-1===f){var g=e.createVectorLayer();g.set("markers",!0),d.addLayer(g),b.push({map:d,markerLayer:g,instScopes:[]}),f=b.length-1}return b[f].instScopes.push(c),b[f].markerLayer},deregisterScope:function(c,d){var e=a(d);if(-1===e)throw Error("This map has no markers");var f=b[e].instScopes,g=f.indexOf(c);if(-1===g)throw Error("Scope wan't registered");f.splice(g,1),f.length||(d.removeLayer(b[e].markerLayer),delete b[e].markerLayer,delete b[e])}}}();return{restrict:"E",scope:{lat:"=lat",lon:"=lon",label:"=label",properties:"=olMarkerProperties",style:"=olStyle"},transclude:!0,require:"^openlayers",replace:!0,template:'',link:function(c,h,i,j){var k=e.isDefined,l=j.getOpenlayersScope(),m=e.createFeature,n=e.createOverlay,o=h.find("ng-transclude").children().length>0;l.getMap().then(function(e){function j(){c.properties&&(e.getViewport().removeEventListener("mousemove",c.properties.handleInteraction),e.getViewport().removeEventListener("click",c.properties.handleTapInteraction),e.getViewport().querySelector("canvas.ol-unselectable").removeEventListener("touchend",c.properties.handleTapInteraction),e.getViewport().removeEventListener("mousemove",c.properties.showAtLeastOneOverlay),e.getViewport().removeEventListener("click",c.properties.removeAllOverlays),e.getViewport().querySelector("canvas.ol-unselectable").removeEventListener("touchmove",c.properties.activateCooldown))}var p,q,r,s=g.getInst(c,e),t=f(),u=d.getDefaults(l),v=u.view.projection,w=null,x=null;if(c.handleDrag=function(b){var d=b.coordinate,f=e.getView().getProjection().getCode();if(d="pixel"===f?d.map(function(a){return parseInt(a,10)}):a.proj.transform(d,f,"EPSG:4326"),"pointerdown"===b.type){var g=e.forEachFeatureAtPixel(b.pixel,function(a){return a});if(!(x=g?g.get("marker"):null)||!x.draggable)return void(x=null);e.getTarget().style.cursor="pointer",w="pixel"===f?[d[0]-x.coord[0],d[1]-x.coord[1]]:[d[0]-x.lon,d[1]-x.lat],b.preventDefault()}else w&&x&&("pointerup"===b.type?(e.getTarget().style.cursor="",w=null,x=null,b.preventDefault()):"pointerdrag"===b.type&&(b.preventDefault(),c.$apply(function(){"pixel"===f?(x.coord[0]=d[0]-w[0],x.coord[1]=d[1]-w[1]):(x.lon=d[0]-w[0],x.lat=d[1]-w[1])})))},e.on("pointerdown",c.handleDrag),e.on("pointerup",c.handleDrag),e.on("pointerdrag",c.handleDrag),c.$on("$destroy",function(){s.getSource().removeFeature(r),k(p)&&e.removeOverlay(p),g.deregisterScope(c,e),e.un("pointerdown",c.handleDrag),e.un("pointerup",c.handleDrag),e.un("pointerdrag",c.handleDrag),j()}),!k(c.properties))return t.lat=c.lat?c.lat:t.lat,t.lon=c.lon?c.lon:t.lon,t.message=i.message,t.style=c.style?c.style:u.styles.marker,r=m(t,v),k(r)||b.error("[AngularJS - Openlayers] Received invalid data on the marker."),r.set("marker",c),s.getSource().addFeature(r),void((t.message||o)&&(c.message=i.message,q=a.proj.transform([t.lon,t.lat],t.projection,v),p=n(h,q),e.addOverlay(p)));c.$watch("properties",function(d){if(j(),d.handleInteraction=function(b){var c=!1;if(i.hasOwnProperty("ngClick")&&(c=!0),!d.label.show||c){var f=!1,g=e.getEventPixel(b),j=e.forEachFeatureAtPixel(g,function(a){return a}),l=!1;if(j===r){if(l=!0,f=!0,c&&("click"===b.type||"touchend"===b.type))return h.triggerHandler("click"),b.preventDefault(),void b.stopPropagation();k(p)||(q="pixel"===t.projection?d.coord:a.proj.transform([d.lon,d.lat],t.projection,v),p=n(h,q),e.addOverlay(p)),e.getTarget().style.cursor="pointer"}!f&&p&&(l=!0,e.removeOverlay(p),p=void 0,e.getTarget().style.cursor=""),l&&b.preventDefault()}},d.handleTapInteraction=function(){var a,b=!1;return d.activateCooldown=function(){b=!0,a&&clearTimeout(a),a=setTimeout(function(){b=!1,a=null},500)},d.activateCooldown&&e.getViewport().querySelector("canvas.ol-unselectable").removeEventListener("touchmove",d.activateCooldown),e.getViewport().querySelector("canvas.ol-unselectable").addEventListener("touchmove",d.activateCooldown),function(){b||(d.handleInteraction.apply(null,arguments),d.activateCooldown())}}(),d.showAtLeastOneOverlay=function(b){if(!d.label.show){var c=!1,f=e.getEventPixel(b),g=e.forEachFeatureAtPixel(f,function(a){return a}),i=!1;g===r&&(i=!0,c=!0,k(p)||(q="pixel"===t.projection?t.coord:a.proj.transform([t.lon,t.lat],t.projection,v),p=n(h,q),angular.forEach(e.getOverlays(),function(a){e.removeOverlay(a)}),e.addOverlay(p)),e.getTarget().style.cursor="pointer"),!c&&p&&(i=!0,p=void 0,e.getTarget().style.cursor=""),i&&b.preventDefault()}},d.removeAllOverlays=function(a){angular.forEach(e.getOverlays(),function(a){e.removeOverlay(a)}),a.preventDefault()},k(r)){var f;if(f="pixel"===d.projection?d.coord:a.proj.transform([d.lon,d.lat],t.projection,e.getView().getProjection()),!angular.equals(r.getGeometry().getCoordinates(),f)){var g=new a.geom.Point(f);r.setGeometry(g)}}else t.projection=d.projection?d.projection:t.projection,t.coord=d.coord?d.coord:t.coord,t.lat=d.lat?d.lat:t.lat,t.lon=d.lon?d.lon:t.lon,k(d.style)?t.style=d.style:t.style=u.styles.marker,r=m(t,v),k(r)||b.error("[AngularJS - Openlayers] Received invalid data on the marker."),r.set("marker",d),s.getSource().addFeature(r);k(p)&&e.removeOverlay(p),k(d.label)&&(c.message=d.label.message,(o||k(c.message)&&0!==c.message.length)&&(d.label&&!0===d.label.show&&(q="pixel"===t.projection?t.coord:a.proj.transform([d.lon,d.lat],t.projection,v),p=n(h,q),e.addOverlay(p)),p&&d.label&&!1===d.label.show&&(e.removeOverlay(p),p=void 0),d.label&&!1===d.label.show&&d.label.showOnMouseOver&&e.getViewport().addEventListener("mousemove",d.handleInteraction),(d.label&&!1===d.label.show&&d.label.showOnMouseClick||i.hasOwnProperty("ngClick"))&&(e.getViewport().addEventListener("click",d.handleTapInteraction),e.getViewport().querySelector("canvas.ol-unselectable").addEventListener("touchend",d.handleTapInteraction)),d.label&&!1===d.label.show&&d.label.keepOneOverlayVisible&&(e.getViewport().addEventListener("mousemove",d.showAtLeastOneOverlay),e.getViewport().addEventListener("click",d.removeAllOverlays))))},!0)})}}}]),angular.module("openlayers-directive").service("olData",["$log","$q",function(a,b){function c(b,c){var d,e;if(angular.isDefined(c))d=c;else if(1===Object.keys(b).length)for(e in b)b.hasOwnProperty(e)&&(d=e);else 0===Object.keys(b).length?d="main":a.error("[AngularJS - Openlayers] - You have more than 1 map on the DOM, you must provide the map ID to the olData.getXXX call");return d}var d={},e=function(a,b){a[c(a,b)].resolvedDefer=!0},f=function(a,d){var e,f=c(a,d);return angular.isDefined(a[f])&&!0!==a[f].resolvedDefer?e=a[f].defer:(e=b.defer(),a[f]={defer:e,resolvedDefer:!1}),e},g=function(a,b){var d=c(a,b);return angular.isDefined(a[d])&&!1!==a[d].resolvedDefer?a[d].defer:f(a,b)};this.setMap=function(a,b){f(d,b).resolve(a),e(d,b)},this.getMap=function(a){return g(d,a).promise},this.resetMap=function(a){angular.isDefined(d[a])&&delete d[a]}}]),angular.module("openlayers-directive").factory("olHelpers",["$q","$log","$http",function(b,c,d){var e=function(a){return angular.isDefined(a)},f=function(a){return angular.isDefined(a)&&null!==a},g=function(a,b,c){a.on(b,function(d){var e=d.coordinate,f=a.getView().getProjection().getCode();"pixel"===f&&(e=e.map(function(a){return parseInt(a,10)})),c.$emit("openlayers.map."+b,{coord:e,projection:f,event:d})})},h=["Road","Aerial","AerialWithLabels","collinsBart","ordnanceSurvey"],i=function(){return{attribution:a.control.Attribution,fullscreen:a.control.FullScreen,mouseposition:a.control.MousePosition,overviewmap:a.control.OverviewMap,rotate:a.control.Rotate,scaleline:a.control.ScaleLine,zoom:a.control.Zoom,zoomslider:a.control.ZoomSlider,zoomtoextent:a.control.ZoomToExtent}},j=["osm","sat","hyb"],k=["World_Imagery","World_Street_Map","World_Topo_Map","World_Physical_Map","World_Terrain_Base","Ocean_Basemap","NatGeo_World_Map"],l={style:a.style.Style,fill:a.style.Fill,stroke:a.style.Stroke,circle:a.style.Circle,icon:a.style.Icon,image:a.style.Image,regularshape:a.style.RegularShape,text:a.style.Text},m=function(a,b){return b&&a instanceof b?a:b?new b(a):a},n=function a(b,c){var d;if(c?d=b[c]:(c="style",d=b),"style"===c&&b instanceof Function)return b;if(!(d instanceof Object))return d;var e;if("[object Object]"===Object.prototype.toString.call(d)){e={};var f=l[c];if(f&&d instanceof f)return d;Object.getOwnPropertyNames(d).forEach(function(b,g,h){var i=l[b];if(f&&i&&i.prototype instanceof l[c])return console.assert(1===h.length,"Extra parameters for "+c),e=a(d,b),m(e,i);e[b]=a(d,b),"text"!==b&&"string"!=typeof e[b]&&(e[b]=m(e[b],l[b]))})}else e=d;return m(e,l[c])},o=function(a){if(a.type)return a.type;switch(a.source.type){case"ImageWMS":case"ImageStatic":return"Image";case"GeoJSON":case"JSONP":case"TopoJSON":case"KML":case"WKT":return"Vector";case"TileVector":case"MVT":return"TileVector";default:return"Tile"}},p=function(b){var d;switch(b.projection){case"pixel":if(!e(b.extent))return void c.error("[AngularJS - Openlayers] - You must provide the extent of the image if using pixel projection");d=new a.proj.Projection({code:"pixel",units:"pixels",extent:b.extent});break;default:d=new a.proj.get(b.projection)}return d},q=function(a){return-1!==["watercolor","terrain","toner"].indexOf(a)},r=function(b,f){var g,i,l,m=new a.format.GeoJSON;switch(b.type){case"MapBox":if(!b.mapId||!b.accessToken)return void c.error("[AngularJS - Openlayers] - MapBox layer requires the map id and the access token");l="https://api.tiles.mapbox.com/v4/"+b.mapId+"/{z}/{x}/{y}.png?access_token="+b.accessToken,i=window.devicePixelRatio,i>1&&(l=l.replace(".png","@2x.png")),g=new a.source.XYZ({url:l,tileLoadFunction:b.tileLoadFunction,attributions:t(b),tilePixelRatio:i>1?2:1,wrapX:void 0===b.wrapX||b.wrapX});break;case"MapBoxStudio":if(!b.mapId||!b.accessToken||!b.userId)return void c.error("[AngularJS - Openlayers] - MapBox Studio layer requires the map id, user id and the access token");l="https://api.mapbox.com/styles/v1/"+b.userId+"/"+b.mapId+"/tiles/{z}/{x}/{y}?access_token="+b.accessToken,i=window.devicePixelRatio,i>1&&(l=l.replace("{y}?access_token","{y}@2x?access_token")),g=new a.source.XYZ({url:l,tileLoadFunction:b.tileLoadFunction,attributions:t(b),tilePixelRatio:i>1?2:1,tileSize:b.tileSize||[512,512],wrapX:void 0===b.wrapX||b.wrapX});break;case"MVT":if(!b.url)return void c.error("[AngularJS - Openlayers] - MVT layer requires the source url");g=new a.source.VectorTile({attributions:b.attributions||"",format:new a.format.MVT,tileGrid:a.tilegrid.createXYZ({maxZoom:b.maxZoom||22}),tilePixelRatio:b.tilePixelRatio||16,url:b.url});break;case"ImageWMS":b.url&&b.params||c.error("[AngularJS - Openlayers] - ImageWMS Layer needs valid server url and params properties"),g=new a.source.ImageWMS({url:b.url,imageLoadFunction:b.imageLoadFunction,attributions:t(b),crossOrigin:void 0===b.crossOrigin?"anonymous":b.crossOrigin,params:s(b.params),ratio:b.ratio});break;case"TileWMS":(b.url||b.urls)&&b.params||c.error("[AngularJS - Openlayers] - TileWMS Layer needs valid url (or urls) and params properties");var n={tileLoadFunction:b.tileLoadFunction,crossOrigin:void 0===b.crossOrigin?"anonymous":b.crossOrigin,params:s(b.params),attributions:t(b),wrapX:void 0===b.wrapX||b.wrapX};b.serverType&&(n.serverType=b.serverType),b.url&&(n.url=b.url),b.urls&&(n.urls=b.urls),g=new a.source.TileWMS(n);break;case"WMTS":(b.url||b.urls)&&b.tileGrid||c.error("[AngularJS - Openlayers] - WMTS Layer needs valid url (or urls) and tileGrid properties");var o={tileLoadFunction:b.tileLoadFunction,projection:f,layer:b.layer,attributions:t(b),matrixSet:"undefined"===b.matrixSet?f:b.matrixSet,format:"undefined"===b.format?"image/jpeg":b.format,requestEncoding:"undefined"===b.requestEncoding?"KVP":b.requestEncoding,tileGrid:new a.tilegrid.WMTS({origin:b.tileGrid.origin,resolutions:b.tileGrid.resolutions,matrixIds:b.tileGrid.matrixIds}),style:"undefined"===b.style?"normal":b.style,wrapX:void 0===b.wrapX||b.wrapX};e(b.url)&&(o.url=b.url),e(b.urls)&&(o.urls=b.urls),g=new a.source.WMTS(o);break;case"OSM":g=new a.source.OSM({tileLoadFunction:b.tileLoadFunction,attributions:t(b),wrapX:void 0===b.wrapX||b.wrapX}),b.url&&g.setUrl(b.url);break;case"BingMaps":if(!b.key)return void c.error("[AngularJS - Openlayers] - You need an API key to show the Bing Maps.");var p={key:b.key,tileLoadFunction:b.tileLoadFunction,attributions:t(b),imagerySet:b.imagerySet?b.imagerySet:h[0],culture:b.culture,wrapX:void 0===b.wrapX||b.wrapX};b.maxZoom&&(p.maxZoom=b.maxZoom),g=new a.source.BingMaps(p);break;case"MapQuest":if(!b.layer||-1===j.indexOf(b.layer))return void c.error("[AngularJS - Openlayers] - MapQuest layers needs a valid 'layer' property.");g=new a.source.MapQuest({attributions:t(b),layer:b.layer,wrapX:void 0===b.wrapX||b.wrapX});break;case"EsriBaseMaps":if(!b.layer||-1===k.indexOf(b.layer))return void c.error("[AngularJS - Openlayers] - ESRI layers needs a valid 'layer' property.");var r="http://services.arcgisonline.com/ArcGIS/rest/services/",u=r+b.layer+"/MapServer/tile/{z}/{y}/{x}";g=new a.source.XYZ({attributions:t(b),tileLoadFunction:b.tileLoadFunction,url:u,wrapX:void 0===b.wrapX||b.wrapX});break;case"TileArcGISRest":b.url||c.error("[AngularJS - Openlayers] - TileArcGISRest Layer needs valid url"),g=new a.source.TileArcGISRest({attributions:t(b),tileLoadFunction:b.tileLoadFunction,url:b.url,wrapX:void 0===b.wrapX||b.wrapX});break;case"GeoJSON":if(!b.geojson&&!b.url)return void c.error("[AngularJS - Openlayers] - You need a geojson property to add a GeoJSON layer.");if(e(b.url))g=new a.source.Vector({format:new a.format.GeoJSON,url:b.url});else{g=new a.source.Vector;var v,w=f;v=e(b.geojson.projection)?new a.proj.get(b.geojson.projection):f;var x=m.readFeatures(b.geojson.object,{featureProjection:w.getCode(),dataProjection:v.getCode()});g.addFeatures(x)}break;case"WKT":if(!b.wkt&&!b.wkt.data)return void c.error("[AngularJS - Openlayers] - You need a WKT property to add a WKT format vector layer.");g=new a.source.Vector;var y,z=new a.format.WKT;y=e(b.wkt.projection)?new a.proj.get(b.wkt.projection):f;var A=z.readFeatures(b.wkt.data,{featureProjection:f.getCode(),dataProjection:y.getCode()});g.addFeatures(A);break;case"JSONP":if(!b.url)return void c.error("[AngularJS - Openlayers] - You need an url properly configured to add a JSONP layer.");e(b.url)&&(g=new a.source.ServerVector({format:m,loader:function(){var a=b.url+"&outputFormat=text/javascript&format_options=callback:JSON_CALLBACK";d.jsonp(a,{cache:b.cache}).success(function(a){g.addFeatures(m.readFeatures(a))}).error(function(a){c(a)})},projection:f}));break;case"TopoJSON":if(!b.topojson&&!b.url)return void c.error("[AngularJS - Openlayers] - You need a topojson property to add a TopoJSON layer.");g=b.url?new a.source.Vector({format:new a.format.TopoJSON,url:b.url}):new a.source.Vector(angular.extend(b.topojson,{format:new a.format.TopoJSON}));break;case"TileJSON":g=new a.source.TileJSON({url:b.url,attributions:t(b),tileLoadFunction:b.tileLoadFunction,crossOrigin:"anonymous",wrapX:void 0===b.wrapX||b.wrapX});break;case"TileVector":b.url&&b.format||c.error("[AngularJS - Openlayers] - TileVector Layer needs valid url and format properties"),g=new a.source.VectorTile({url:b.url,projection:f,attributions:t(b),tileLoadFunction:b.tileLoadFunction,format:b.format,tileGrid:new a.tilegrid.createXYZ({maxZoom:b.maxZoom||19}),wrapX:void 0===b.wrapX||b.wrapX});break;case"TileTMS":b.url&&b.tileGrid||c.error("[AngularJS - Openlayers] - TileTMS Layer needs valid url and tileGrid properties"),g=new a.source.TileImage({url:b.url,maxExtent:b.maxExtent,attributions:t(b),tileLoadFunction:b.tileLoadFunction,tileGrid:new a.tilegrid.TileGrid({origin:b.tileGrid.origin,resolutions:b.tileGrid.resolutions}),tileUrlFunction:function(a){var c=a[0],d=a[1],e=a[2];return d<0||e<0?"":b.url+c+"/"+d+"/"+e+".png"},wrapX:void 0===b.wrapX||b.wrapX});break;case"TileImage":g=new a.source.TileImage({url:b.url,attributions:t(b),tileLoadFunction:b.tileLoadFunction,tileGrid:new a.tilegrid.TileGrid({origin:b.tileGrid.origin,resolutions:b.tileGrid.resolutions}),tileUrlFunction:function(a){var c=a[0],d=a[1],e=-a[2]-1;return b.url.replace("{z}",c.toString()).replace("{x}",d.toString()).replace("{y}",e.toString())},wrapX:void 0===b.wrapX||b.wrapX});break;case"KML":var B=b.extractStyles||!1;g=new a.source.Vector({url:b.url,format:new a.format.KML,radius:b.radius,extractStyles:B});break;case"Stamen":if(!b.layer||!q(b.layer))return void c.error("[AngularJS - Openlayers] - You need a valid Stamen layer.");g=new a.source.Stamen({tileLoadFunction:b.tileLoadFunction,layer:b.layer,wrapX:void 0===b.wrapX||b.wrapX});break;case"ImageStatic":if(!b.url||!angular.isArray(b.imageSize)||2!==b.imageSize.length)return void c.error("[AngularJS - Openlayers] - You need a image URL to create a ImageStatic layer.");g=new a.source.ImageStatic({url:b.url,attributions:t(b),imageSize:b.imageSize,projection:f,imageExtent:b.imageExtent?b.imageExtent:f.getExtent(),imageLoadFunction:b.imageLoadFunction});break;case"XYZ":b.url||b.tileUrlFunction||c.error("[AngularJS - Openlayers] - XYZ Layer needs valid url or tileUrlFunction properties"),g=new a.source.XYZ({url:b.url,attributions:t(b),minZoom:b.minZoom,maxZoom:b.maxZoom,projection:b.projection,tileUrlFunction:b.tileUrlFunction,tileLoadFunction:b.tileLoadFunction,wrapX:void 0===b.wrapX||b.wrapX});break;case"Zoomify":b.url&&angular.isArray(b.imageSize)&&2===b.imageSize.length||c.error("[AngularJS - Openlayers] - Zoomify Layer needs valid url and imageSize properties"),g=new a.source.Zoomify({url:b.url,size:b.imageSize,wrapX:void 0===b.wrapX||b.wrapX})}return g||c.warn('[AngularJS - Openlayers] - No source could be found for type "'+b.type+'"'),g},s=function(a){var b=a;if(a&&"object"==typeof a){b="[object Array]"===Object.prototype.toString.call(a)?[]:{};for(var c in a)b[c]=s(a[c])}return b},t=function(b){var c=[];if(e(b.attribution))!1!==b.attribution&&c.unshift(new a.Attribution({html:b.attribution}));else{var d=u(b);d&&c.unshift(d)}return c},u=function(b){if(b&&b.type){var c=a.source[b.type];if(c)for(var d in c)if(c.hasOwnProperty(d)&&d.toLowerCase().indexOf("attribution")>-1)return a.source[b.type][d]}return null},v=function(b){var c=new a.layer.Group;return c.set("name",b),c},w=function(b,c){var d;return angular.forEach(b,function(b){if(b instanceof a.layer.Group&&b.get("name")===c)return void(d=b)}),d},x=function(a,b){for(var c,d=0;d default tries to show an attribution + if (!(source.attribution === false)) { // jshint ignore:line + // we got some HTML so display that as the attribution + attributions.unshift(new ol.Attribution({html: source.attribution})); + } + } else { + // try to infer automatically + var attrib = extractAttributionFromSource(source); + if (attrib) { + attributions.unshift(attrib); + } } + return attributions; }; + var extractAttributionFromSource = function(source) { + if (source && source.type) { + var ol3SourceInstance = ol.source[source.type]; + if (ol3SourceInstance) { + // iterate over the object's props and try + // to find the attribution one as it differs + for (var prop in ol3SourceInstance) { + if (ol3SourceInstance.hasOwnProperty(prop)) { + if (prop.toLowerCase().indexOf('attribution') > -1) { + return ol.source[source.type][prop]; + } + } + } + } + } + + return null; + }; + var createGroup = function(name) { var olGroup = new ol.layer.Group(); olGroup.set('name', name); diff --git a/package.json b/package.json index dfa09813..68e55764 100644 --- a/package.json +++ b/package.json @@ -66,5 +66,5 @@ "semantic-release": "semantic-release pre && npm publish && semantic-release post" }, "main": "dist/angular-openlayers-directive", - "version": "1.19.3" + "version": "1.20.0" } \ No newline at end of file diff --git a/src/services/olHelpers.js b/src/services/olHelpers.js index b290eca9..a6bca395 100644 --- a/src/services/olHelpers.js +++ b/src/services/olHelpers.js @@ -685,11 +685,41 @@ angular.module('openlayers-directive').factory('olHelpers', function($q, $log, $ var createAttribution = function(source) { var attributions = []; if (isDefined(source.attribution)) { - attributions.unshift(new ol.Attribution({html: source.attribution})); + // opt-out -> default tries to show an attribution + if (!(source.attribution === false)) { // jshint ignore:line + // we got some HTML so display that as the attribution + attributions.unshift(new ol.Attribution({html: source.attribution})); + } + } else { + // try to infer automatically + var attrib = extractAttributionFromSource(source); + if (attrib) { + attributions.unshift(attrib); + } } + return attributions; }; + var extractAttributionFromSource = function(source) { + if (source && source.type) { + var ol3SourceInstance = ol.source[source.type]; + if (ol3SourceInstance) { + // iterate over the object's props and try + // to find the attribution one as it differs + for (var prop in ol3SourceInstance) { + if (ol3SourceInstance.hasOwnProperty(prop)) { + if (prop.toLowerCase().indexOf('attribution') > -1) { + return ol.source[source.type][prop]; + } + } + } + } + } + + return null; + }; + var createGroup = function(name) { var olGroup = new ol.layer.Group(); olGroup.set('name', name);