From 90b5bc458a3fad1e7e118ffb35ecb3c85ea835ab Mon Sep 17 00:00:00 2001 From: Dominik Hebeler <dominik@suma-ev.de> Date: Wed, 6 Dec 2023 13:19:55 +0100 Subject: [PATCH] prepare update for tileserver --- app/app/Http/Controllers/SearchController.php | 107 +- app/config/maps.php | 5 +- app/public/mix-manifest.json | 5 +- app/resources/css/_ol.css | 1 - app/resources/js/ReversePositionManager.js | 2 +- app/resources/js/_ol.js | 1020 - app/resources/js/findRoute.js | 2 +- app/resources/js/map.js | 8 +- app/resources/js/ol-debug.js | 95334 ---------------- app/resources/js/ol.js | 2 - app/resources/views/map.blade.php | 25 +- app/routes/web.php | 59 +- app/webpack.mix.js | 10 +- build/fpm/Dockerfile | 3 +- docker-compose.yml | 5 +- 15 files changed, 114 insertions(+), 96474 deletions(-) delete mode 100644 app/resources/css/_ol.css delete mode 100644 app/resources/js/_ol.js delete mode 100644 app/resources/js/ol-debug.js delete mode 100644 app/resources/js/ol.js diff --git a/app/app/Http/Controllers/SearchController.php b/app/app/Http/Controllers/SearchController.php index 1d4c26f..01b20d4 100644 --- a/app/app/Http/Controllers/SearchController.php +++ b/app/app/Http/Controllers/SearchController.php @@ -7,43 +7,40 @@ use Response; use \Illuminate\Http\Request; -class SearchController extends Controller -{ +class SearchController extends Controller { - public function search($search) - { - $link = config("maps.nominatim.host") . "/search.php?q=" . urlencode($search) . "&limit=10&polygon_geojson=1&format=json&extratags=1&addressdetails=1&namedetails=1"; + public function search($search) { + $link = config("maps.nominatim.host")."/search.php?q=".urlencode($search)."&limit=10&polygon_geojson=1&format=json&extratags=1&addressdetails=1&namedetails=1"; $searchResults = $this->makeSearch($link, $search, true); return $searchResults; } - public function boundingBoxSearch(Request $request, $search, $latMin, $lonMin, $latMax, $lonMax, $adjustView = true, $limit = 10) - { - $exactSearch = filter_var($request->input('exactSearch', 'false'), FILTER_VALIDATE_BOOLEAN); - $adjustLink = filter_var($request->input('adjustLink', 'true'), FILTER_VALIDATE_BOOLEAN); - $search = urldecode($search); - $adjustView = filter_var($adjustView, FILTER_VALIDATE_BOOLEAN); - $search = urldecode($search); + public function boundingBoxSearch(Request $request, $search, $latMin, $lonMin, $latMax, $lonMax, $adjustView = true, $limit = 10) { + $exactSearch = filter_var($request->input('exactSearch', 'false'), FILTER_VALIDATE_BOOLEAN); + $adjustLink = filter_var($request->input('adjustLink', 'true'), FILTER_VALIDATE_BOOLEAN); + $search = urldecode($search); + $adjustView = filter_var($adjustView, FILTER_VALIDATE_BOOLEAN); + $search = urldecode($search); $exactMatches = 0; - $results = []; + $results = []; # Eine Suche in den gesamten Kartendaten führen wir nur durch, wenn keine View-Spezifische Suche durchgeführt werden soll - if ($adjustView) { + if($adjustView) { # Wir werden zunächst eine Suche ohne das übergebene Gebiet als Begrenzung durchführen. - $link = config("maps.nominatim.host") . "/search.php?q=" . urlencode($search) . "&limit=$limit&polygon_geojson=1&format=json&dedupe=1&extratags=1&addressdetails=1&namedetails=1"; - $results = $this->makeSearch($link, $search, false); + $link = config("maps.nominatim.host")."/search.php?q=".urlencode($search)."&limit=$limit&polygon_geojson=1&format=json&dedupe=1&extratags=1&addressdetails=1&namedetails=1"; + $results = $this->makeSearch($link, $search, false); $exactMatches = $this->getExactMatchesCount($search, $results); } # Wir wollen nun wissen, wie viele von den Ergebnissen genau auf die Suchanfrage passen - if ($exactMatches >= 10) { + if($exactMatches >= 10) { # Okay, das sind ganz schön viele Ergebnisse # Es würde sich wohl lohnen die Suche doch auf das angegebene Gebiet zu begrenzen - $link = config("maps.nominatim.host") . "/search.php?q=" . urlencode($search) . "&limit=$limit&dedupe=1&bounded=1&polygon_geojson=1&viewbox=$latMin,$lonMin,$latMax,$lonMax&format=json&extratags=1&addressdetails=1&namedetails=1"; + $link = config("maps.nominatim.host")."/search.php?q=".urlencode($search)."&limit=$limit&dedupe=1&bounded=1&polygon_geojson=1&viewbox=$latMin,$lonMin,$latMax,$lonMax&format=json&extratags=1&addressdetails=1&namedetails=1"; $tmpResults = $this->makeSearch($link, $search, false); # Wenn In diesem Bereich Ergebnisse gefunden wurden, nehmen wir diese an Stelle der anderen: - if (sizeof($tmpResults) > 0) { - $results = $tmpResults; + if(sizeof($tmpResults) > 0) { + $results = $tmpResults; $exactMatches = $this->getExactMatchesCount($search, $results); } } @@ -56,7 +53,7 @@ public function boundingBoxSearch(Request $request, $search, $latMin, $lonMin, $ return $response; # Wenn wir keine Ergebnisse haben, müssen wir auch nichts anzeigen: - if (sizeof($results) === 0) { + if(sizeof($results) === 0) { $response = Response::make('', 200); $response->header("Content-Type", "application/javascript"); return $response; @@ -68,12 +65,19 @@ public function boundingBoxSearch(Request $request, $search, $latMin, $lonMin, $ } } - private function makeSearch($link, $search, $exactSearch = false) - { + public function reverse(Request $request) { + $path = $request->getRequestUri(); + $url = config("maps.nominatim.host").$path; + $url = str_replace("/search/reverse.php", "/reverse.php", $url); + $result = file_get_contents($url); + return response($result, 200, ["Content-Type" => "application/json"]); + } + + private function makeSearch($link, $search, $exactSearch = false) { $results = []; - if ($this->canCache()) { + if($this->canCache()) { $hash = md5($link); - if (Cache::has($hash)) { + if(Cache::has($hash)) { $results = unserialize(base64_decode(Cache::get($hash))); } else { $results = json_decode(file_get_contents($link), true); @@ -84,25 +88,25 @@ private function makeSearch($link, $search, $exactSearch = false) $results = json_decode(file_get_contents($link), true); } $searchResults = []; - if ($results) { - foreach ($results as $result) { - if ($exactSearch) { + if($results) { + foreach($results as $result) { + if($exactSearch) { $searchWords = explode(" ", $search); - $match = false; - foreach ($searchWords as $word) { - foreach ($result["address"] as $key => $value) { - if (($key === "hamlet" || $key === "village" || $key === "suburb" || $key === "subdistrict" || $key === "district" || $key === "province" || $key === "state" || $key === "city" || $key === "place" || $key === "street" || $key === "country" || $key === "housename") && stripos($value, $word) !== false) { + $match = false; + foreach($searchWords as $word) { + foreach($result["address"] as $key => $value) { + if(($key === "hamlet" || $key === "village" || $key === "suburb" || $key === "subdistrict" || $key === "district" || $key === "province" || $key === "state" || $key === "city" || $key === "place" || $key === "street" || $key === "country" || $key === "housename") && stripos($value, $word) !== false) { $match = true; break 2; } } } - if (!$match) { + if(!$match) { continue; } } # Marker - $result["title"] = substr($result["display_name"], 0, strpos($result["display_name"], ",")); + $result["title"] = substr($result["display_name"], 0, strpos($result["display_name"], ",")); $result["huerotate"] = hexdec(substr(md5(serialize($result)), 0, 5)) % 360; $searchResults[] = $result; @@ -111,37 +115,36 @@ private function makeSearch($link, $search, $exactSearch = false) return $searchResults; } - private function getExactMatchesCount($search, $results) - { - $exactMatches = 0; + private function getExactMatchesCount($search, $results) { + $exactMatches = 0; $wordsInSearch = []; - if (preg_match_all('/([a-zA-Z]|\xC3[\x80-\x96\x98-\xB6\xB8-\xBF]|\xC5[\x92\x93\xA0\xA1\xB8\xBD\xBE]){4,}/', $search, $match_arr)) { + if(preg_match_all('/([a-zA-Z]|\xC3[\x80-\x96\x98-\xB6\xB8-\xBF]|\xC5[\x92\x93\xA0\xA1\xB8\xBD\xBE]){4,}/', $search, $match_arr)) { $wordsInSearch = $match_arr[0]; - $result = []; - foreach ($wordsInSearch as $word) { + $result = []; + foreach($wordsInSearch as $word) { $result[] = preg_quote($word, "/"); } $wordsInSearch = $result; } - foreach ($results as $result) { + foreach($results as $result) { $n_words = preg_match_all('/([a-zA-Z]|\xC3[\x80-\x96\x98-\xB6\xB8-\xBF]|\xC5[\x92\x93\xA0\xA1\xB8\xBD\xBE]){4,}/', $result["display_name"], $match_arr); - if ($n_words) { + if($n_words) { $hasEveryWord = true; - foreach ($wordsInSearch as $word) { + foreach($wordsInSearch as $word) { $hasThisWord = false; - foreach ($match_arr[0] as $wordInResult) { - if (stripos($wordInResult, $word) !== false) { + foreach($match_arr[0] as $wordInResult) { + if(stripos($wordInResult, $word) !== false) { $hasThisWord = true; break; } } - if (!$hasThisWord) { + if(!$hasThisWord) { $hasEveryWord = false; break; } } - if ($hasEveryWord) { + if($hasEveryWord) { $exactMatches++; } else { break; @@ -153,8 +156,7 @@ private function getExactMatchesCount($search, $results) return $exactMatches; } - private function canCache() - { + private function canCache() { # Cachebarkeit testen try { Cache::has('test'); @@ -164,13 +166,12 @@ private function canCache() } } - public function iframeSearch($search) - { + public function iframeSearch($search) { # Let's get some Searchresults if existent $searchResults = app('\App\Http\Controllers\SearchController')->search($search); - if (sizeof($searchResults) > 0) { + if(sizeof($searchResults) > 0) { $exactMatches = $this->getExactMatchesCount($search, $searchResults); - $javaScript = view('searchResults')->with("results", json_encode($searchResults))->with('adjustView', true)->with('boundingSuccess', true)->with('search', $search)->with('adjustLink', false)->with("exactMatches", $exactMatches); + $javaScript = view('searchResults')->with("results", json_encode($searchResults))->with('adjustView', true)->with('boundingSuccess', true)->with('search', $search)->with('adjustLink', false)->with("exactMatches", $exactMatches); # Wir erstellen die Ergebnisseite (JavaScipt) return view('mapIframe')->with('search', $search)->with('script', $javaScript); diff --git a/app/config/maps.php b/app/config/maps.php index 850d36c..920e73f 100644 --- a/app/config/maps.php +++ b/app/config/maps.php @@ -1,7 +1,10 @@ <?php return [ - "nominatim" => [ + "nominatim" => [ "host" => env("NOMINATIM_HOST", ""), ], + "tileserver" => [ + "host" => env("TILESERVER_HOST", ""), + ], ]; \ No newline at end of file diff --git a/app/public/mix-manifest.json b/app/public/mix-manifest.json index 9ac80da..5e06f68 100644 --- a/app/public/mix-manifest.json +++ b/app/public/mix-manifest.json @@ -2,12 +2,11 @@ "/js/modules.js": "/js/modules.js?id=6e01750e4a5262f0aa6b58c1102448f2", "/resources/css/offline-module.css": "/resources/css/offline-module.css?id=9de68a717293298cc813e57caf5dc970", "/js/lib.js": "/js/lib.js?id=5e13e04914a8734ddea7a01a64d8a3ba", - "/js/map-normal.js": "/js/map-normal.js?id=66c668920230437ad8cf60f6d0dae7d6", - "/js/map.js": "/js/map.js?id=43049f3d0d0441f15246d96ba4f30390", + "/js/map.js": "/js/map.js?id=d21a6fab1a8538dce3785463f20342cb", "/js/turf.min.js": "/js/turf.min.js?id=859561c2951cc6bd635ac2b0e8813256", "/css/staticPages.css": "/css/staticPages.css?id=74737c858d58797108ca9ac733c7fa59", "/css/general.css": "/css/general.css?id=787dbb34eea9bbfaa241777238c92e72", "/css/mapSearch.css": "/css/mapSearch.css?id=ae0023b9d1214e22f2f22774282a213c", - "/css/iframeSearch.css": "/css/iframeSearch.css?id=2ae301fe29e809c1cf6b4fbd07cf9e4b", + "/css/iframeSearch.css": "/css/iframeSearch.css?id=acc6e5e3c58d12f4b6516fc1790bf2e5", "/css/routing.css": "/css/routing.css?id=014b091b4366ad8570c8aa53c8b05d8a" } diff --git a/app/resources/css/_ol.css b/app/resources/css/_ol.css deleted file mode 100644 index 019b146..0000000 --- a/app/resources/css/_ol.css +++ /dev/null @@ -1 +0,0 @@ -.ol-box{box-sizing:border-box;border-radius:2px;border:2px solid #00f}.ol-mouse-position{top:8px;right:8px;position:absolute}.ol-scale-line{background:rgba(0,60,136,.3);border-radius:4px;bottom:8px;left:8px;padding:2px;position:absolute}.ol-scale-line-inner{border:1px solid #eee;border-top:none;color:#eee;font-size:10px;text-align:center;margin:1px;will-change:contents,width}.ol-overlay-container{will-change:left,right,top,bottom}.ol-unsupported{display:none}.ol-unselectable,.ol-viewport{-webkit-touch-callout:none;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;-webkit-tap-highlight-color:transparent}.ol-selectable{-webkit-touch-callout:default;-webkit-user-select:auto;-moz-user-select:auto;-ms-user-select:auto;user-select:auto}.ol-control{position:absolute;background-color:rgba(255,255,255,.4);border-radius:4px;padding:2px}.ol-control:hover{background-color:rgba(255,255,255,.6)}.ol-zoom{top:.5em;left:.5em}.ol-rotate{top:.5em;right:.5em;transition:opacity .25s linear,visibility 0s linear}.ol-rotate.ol-hidden{opacity:0;visibility:hidden;transition:opacity .25s linear,visibility 0s linear .25s}.ol-zoom-extent{top:4.643em;left:.5em}.ol-full-screen{right:.5em;top:.5em}@media print{.ol-control{display:none}}.ol-control button{display:block;margin:1px;padding:0;color:#fff;font-size:1.14em;font-weight:700;text-decoration:none;text-align:center;height:1.375em;width:1.375em;line-height:.4em;background-color:rgba(0,60,136,.5);border:none;border-radius:2px}.ol-control button::-moz-focus-inner{border:none;padding:0}.ol-zoom-extent button{line-height:1.4em}.ol-compass{display:block;font-weight:400;font-size:1.2em;will-change:transform}.ol-touch .ol-control button{font-size:1.5em}.ol-touch .ol-zoom-extent{top:5.5em}.ol-control button:focus,.ol-control button:hover{text-decoration:none;background-color:rgba(0,60,136,.7)}.ol-zoom .ol-zoom-in{border-radius:2px 2px 0 0}.ol-zoom .ol-zoom-out{border-radius:0 0 2px 2px}.ol-attribution{text-align:right;bottom:.5em;right:.5em;max-width:calc(100% - 1.3em)}.ol-attribution ul{margin:0;padding:0 .5em;font-size:.7rem;line-height:1.375em;color:#000;text-shadow:0 0 2px #fff}.ol-attribution li{display:inline;list-style:none;line-height:inherit}.ol-attribution li:not(:last-child):after{content:" "}.ol-attribution img{max-height:2em;max-width:inherit;vertical-align:middle}.ol-attribution button,.ol-attribution ul{display:inline-block}.ol-attribution.ol-collapsed ul{display:none}.ol-attribution.ol-logo-only ul{display:block}.ol-attribution:not(.ol-collapsed){background:rgba(255,255,255,.8)}.ol-attribution.ol-uncollapsible{bottom:0;right:0;border-radius:4px 0 0;height:1.1em;line-height:1em}.ol-attribution.ol-logo-only{background:0 0;bottom:.4em;height:1.1em;line-height:1em}.ol-attribution.ol-uncollapsible img{margin-top:-.2em;max-height:1.6em}.ol-attribution.ol-logo-only button,.ol-attribution.ol-uncollapsible button{display:none}.ol-zoomslider{top:4.5em;left:.5em;height:200px}.ol-zoomslider button{position:relative;height:10px}.ol-touch .ol-zoomslider{top:5.5em}.ol-overviewmap{left:.5em;bottom:.5em}.ol-overviewmap.ol-uncollapsible{bottom:0;left:0;border-radius:0 4px 0 0}.ol-overviewmap .ol-overviewmap-map,.ol-overviewmap button{display:inline-block}.ol-overviewmap .ol-overviewmap-map{border:1px solid #7b98bc;height:150px;margin:2px;width:150px}.ol-overviewmap:not(.ol-collapsed) button{bottom:1px;left:2px;position:absolute}.ol-overviewmap.ol-collapsed .ol-overviewmap-map,.ol-overviewmap.ol-uncollapsible button{display:none}.ol-overviewmap:not(.ol-collapsed){background:rgba(255,255,255,.8)}.ol-overviewmap-box{border:2px dotted rgba(0,60,136,.7)}.ol-overviewmap .ol-overviewmap-box:hover{cursor:move} \ No newline at end of file diff --git a/app/resources/js/ReversePositionManager.js b/app/resources/js/ReversePositionManager.js index d758528..1f1c1f5 100644 --- a/app/resources/js/ReversePositionManager.js +++ b/app/resources/js/ReversePositionManager.js @@ -19,7 +19,7 @@ ReversePositionManager.prototype.constructor = ReversePositionManager; ReversePositionManager.prototype.getNearest = function(evt) { var pos = evt.lngLat; var url = - "https://maps.metager.de/nominatim/reverse.php?format=json&lat=" + + "/search/reverse.php?format=json&lat=" + pos.lat + "&lon=" + pos.lng + diff --git a/app/resources/js/_ol.js b/app/resources/js/_ol.js deleted file mode 100644 index ed987c2..0000000 --- a/app/resources/js/_ol.js +++ /dev/null @@ -1,1020 +0,0 @@ -// OpenLayers. See https://openlayers.org/ -// License: https://raw.githubusercontent.com/openlayers/openlayers/master/LICENSE.md -// Version: v4.1.1 -;(function (root, factory) { - if (typeof exports === "object") { - module.exports = factory(); - } else if (typeof define === "function" && define.amd) { - define([], factory); - } else { - root.ol = factory(); - } -}(this, function () { - var OPENLAYERS = {}; - var k,ba=this;function t(a,b){var c=OPENLAYERS,d=a.split("."),c=c||ba;d[0]in c||!c.execScript||c.execScript("var "+d[0]);for(var e;d.length&&(e=d.shift());)d.length||void 0===b?c[e]&&Object.prototype.hasOwnProperty.call(c,e)?c=c[e]:c=c[e]={}:c[e]=b};var ca,da;function ea(a,b){return a>b?1:a<b?-1:0}function fa(a,b){return 0<=a.indexOf(b)}function ga(a,b,c){var d=a.length;if(a[0]<=b)return 0;if(!(b<=a[d-1]))if(0<c)for(c=1;c<d;++c){if(a[c]<b)return c-1}else if(0>c)for(c=1;c<d;++c){if(a[c]<=b)return c}else for(c=1;c<d;++c){if(a[c]==b)return c;if(a[c]<b)return a[c-1]-b<b-a[c]?c-1:c}return d-1}function ha(a,b){var c,d=Array.isArray(b)?b:[b],e=d.length;for(c=0;c<e;c++)a[a.length]=d[c]} -function ia(a,b){for(var c=a.length>>>0,d,e=0;e<c;e++)if(d=a[e],b(d,e,a))return d;return null}function ja(a,b){var c=a.length;if(c!==b.length)return!1;for(var d=0;d<c;d++)if(a[d]!==b[d])return!1;return!0}function ka(a){var b=la,c=a.length,d=Array(a.length),e;for(e=0;e<c;e++)d[e]={index:e,value:a[e]};d.sort(function(a,c){return b(a.value,c.value)||a.index-c.index});for(e=0;e<a.length;e++)a[e]=d[e].value}function ma(a,b){var c;return a.every(function(d,e){c=e;return!b(d,e,a)})?-1:c} -function na(a,b){var c=b||ea;return a.every(function(b,e){if(!e)return!0;var d=c(a[e-1],b);return!(0<d||0===d)})};function u(a,b){a.prototype=Object.create(b.prototype);a.prototype.constructor=a}function oa(){}function w(a){return a.Lo||(a.Lo=++pa)}var pa=0;function qa(a){this.message="Assertion failed. See https://openlayers.org/en/v4.1.1/doc/errors/#"+a+" for details.";this.code=a;this.name="AssertionError"}u(qa,Error);function sa(a,b){if(!a)throw new qa(b);};function ta(a,b,c,d){this.da=a;this.ba=b;this.ga=c;this.ja=d}function ua(a,b,c){return a.da<=b&&b<=a.ba&&a.ga<=c&&c<=a.ja}function va(a,b){return a.da==b.da&&a.ga==b.ga&&a.ba==b.ba&&a.ja==b.ja}function wa(a,b){return a.da<=b.ba&&a.ba>=b.da&&a.ga<=b.ja&&a.ja>=b.ga};function xa(a,b,c){return Math.min(Math.max(a,b),c)}var ya=function(){var a;"cosh"in Math?a=Math.cosh:a=function(a){a=Math.exp(a);return(a+1/a)/2};return a}();function za(a){sa(0<a,29);return Math.pow(2,Math.ceil(Math.log(a)/Math.LN2))}function Aa(a,b,c,d,e,f){var g=e-c,h=f-d;if(g||h){var l=((a-c)*g+(b-d)*h)/(g*g+h*h);1<l?(c=e,d=f):0<l&&(c+=g*l,d+=h*l)}return Ba(a,b,c,d)}function Ba(a,b,c,d){a=c-a;b=d-b;return a*a+b*b}function Ca(a){return a*Math.PI/180} -function Da(a,b){var c=a%b;return 0>c*b?c+b:c}function Ea(a,b,c){return a+c*(b-a)};function Fa(a,b,c){void 0===c&&(c=[0,0]);c[0]=a[0]+2*b;c[1]=a[1]+2*b;return c}function Ga(a,b,c){void 0===c&&(c=[0,0]);c[0]=a[0]*b+.5|0;c[1]=a[1]*b+.5|0;return c}function Ha(a,b){if(Array.isArray(a))return a;void 0===b?b=[a,a]:b[0]=b[1]=a;return b};function Ia(a){for(var b=Ja(),c=0,d=a.length;c<d;++c)La(b,a[c]);return b}function Ma(a,b,c){return c?(c[0]=a[0]-b,c[1]=a[1]-b,c[2]=a[2]+b,c[3]=a[3]+b,c):[a[0]-b,a[1]-b,a[2]+b,a[3]+b]}function Oa(a,b){return b?(b[0]=a[0],b[1]=a[1],b[2]=a[2],b[3]=a[3],b):a.slice()}function Pa(a,b,c){b=b<a[0]?a[0]-b:a[2]<b?b-a[2]:0;a=c<a[1]?a[1]-c:a[3]<c?c-a[3]:0;return b*b+a*a}function Qa(a,b){return Sa(a,b[0],b[1])}function Ua(a,b){return a[0]<=b[0]&&b[2]<=a[2]&&a[1]<=b[1]&&b[3]<=a[3]} -function Sa(a,b,c){return a[0]<=b&&b<=a[2]&&a[1]<=c&&c<=a[3]}function Va(a,b){var c=a[1],d=a[2],e=a[3],f=b[0],g=b[1],h=0;f<a[0]?h|=16:f>d&&(h|=4);g<c?h|=8:g>e&&(h|=2);h||(h=1);return h}function Ja(){return[Infinity,Infinity,-Infinity,-Infinity]}function Wa(a,b,c,d,e){return e?(e[0]=a,e[1]=b,e[2]=c,e[3]=d,e):[a,b,c,d]}function Xa(a,b){var c=a[0],d=a[1];return Wa(c,d,c,d,b)}function Ya(a,b,c,d,e){e=Wa(Infinity,Infinity,-Infinity,-Infinity,e);return Za(e,a,b,c,d)} -function $a(a,b){return a[0]==b[0]&&a[2]==b[2]&&a[1]==b[1]&&a[3]==b[3]}function ab(a,b){b[0]<a[0]&&(a[0]=b[0]);b[2]>a[2]&&(a[2]=b[2]);b[1]<a[1]&&(a[1]=b[1]);b[3]>a[3]&&(a[3]=b[3]);return a}function La(a,b){b[0]<a[0]&&(a[0]=b[0]);b[0]>a[2]&&(a[2]=b[0]);b[1]<a[1]&&(a[1]=b[1]);b[1]>a[3]&&(a[3]=b[1])}function Za(a,b,c,d,e){for(;c<d;c+=e){var f=a,g=b[c],h=b[c+1];f[0]=Math.min(f[0],g);f[1]=Math.min(f[1],h);f[2]=Math.max(f[2],g);f[3]=Math.max(f[3],h)}return a} -function bb(a,b,c){var d;return(d=b.call(c,cb(a)))||(d=b.call(c,db(a)))||(d=b.call(c,eb(a)))?d:(d=b.call(c,fb(a)))?d:!1}function gb(a){var b=0;hb(a)||(b=ib(a)*jb(a));return b}function cb(a){return[a[0],a[1]]}function db(a){return[a[2],a[1]]}function kb(a){return[(a[0]+a[2])/2,(a[1]+a[3])/2]} -function lb(a,b,c,d,e){var f=b*d[0]/2;d=b*d[1]/2;b=Math.cos(c);var g=Math.sin(c);c=f*b;f*=g;b*=d;var h=d*g,l=a[0],m=a[1];a=l-c+h;d=l-c-h;g=l+c-h;c=l+c+h;var h=m-f-b,l=m-f+b,n=m+f+b,f=m+f-b;return Wa(Math.min(a,d,g,c),Math.min(h,l,n,f),Math.max(a,d,g,c),Math.max(h,l,n,f),e)}function jb(a){return a[3]-a[1]}function mb(a,b,c){c=c?c:Ja();nb(a,b)&&(c[0]=a[0]>b[0]?a[0]:b[0],c[1]=a[1]>b[1]?a[1]:b[1],c[2]=a[2]<b[2]?a[2]:b[2],c[3]=a[3]<b[3]?a[3]:b[3]);return c}function fb(a){return[a[0],a[3]]} -function eb(a){return[a[2],a[3]]}function ib(a){return a[2]-a[0]}function nb(a,b){return a[0]<=b[2]&&a[2]>=b[0]&&a[1]<=b[3]&&a[3]>=b[1]}function hb(a){return a[2]<a[0]||a[3]<a[1]}function ob(a,b){var c=(a[2]-a[0])/2*(b-1),d=(a[3]-a[1])/2*(b-1);a[0]-=c;a[2]+=c;a[1]-=d;a[3]+=d} -function pb(a,b,c){a=[a[0],a[1],a[0],a[3],a[2],a[1],a[2],a[3]];b(a,a,2);var d=[a[0],a[2],a[4],a[6]],e=[a[1],a[3],a[5],a[7]];b=Math.min.apply(null,d);a=Math.min.apply(null,e);d=Math.max.apply(null,d);e=Math.max.apply(null,e);return Wa(b,a,d,e,c)};var qb="function"===typeof Object.assign?Object.assign:function(a,b){if(!a||null===a)throw new TypeError("Cannot convert undefined or null to object");for(var c=Object(a),d=1,e=arguments.length;d<e;++d){var f=arguments[d];if(void 0!==f&&null!==f)for(var g in f)f.hasOwnProperty(g)&&(c[g]=f[g])}return c};function rb(a){for(var b in a)delete a[b]}function sb(a){var b=[],c;for(c in a)b.push(a[c]);return b}function tb(a){for(var b in a)return!1;return!b};/* - - Latitude/longitude spherical geodesy formulae taken from - http://www.movable-type.co.uk/scripts/latlong.html - Licensed under CC-BY-3.0. -*/ -function ub(a){this.radius=a}ub.prototype.a=function(a){for(var b=0,c=a.length,d=a[c-1][0],e=a[c-1][1],f=0;f<c;f++)var g=a[f][0],h=a[f][1],b=b+Ca(g-d)*(2+Math.sin(Ca(e))+Math.sin(Ca(h))),d=g,e=h;return b*this.radius*this.radius/2};ub.prototype.b=function(a,b){var c=Ca(a[1]),d=Ca(b[1]),e=(d-c)/2,f=Ca(b[0]-a[0])/2,c=Math.sin(e)*Math.sin(e)+Math.sin(f)*Math.sin(f)*Math.cos(c)*Math.cos(d);return 2*this.radius*Math.atan2(Math.sqrt(c),Math.sqrt(1-c))}; -ub.prototype.offset=function(a,b,c){var d=Ca(a[1]);b/=this.radius;var e=Math.asin(Math.sin(d)*Math.cos(b)+Math.cos(d)*Math.sin(b)*Math.cos(c));return[180*(Ca(a[0])+Math.atan2(Math.sin(c)*Math.sin(b)*Math.cos(d),Math.cos(b)-Math.sin(d)*Math.sin(e)))/Math.PI,180*e/Math.PI]};var vb=new ub(6370997);var xb={};xb.degrees=2*Math.PI*vb.radius/360;xb.ft=.3048;xb.m=1;xb["us-ft"]=1200/3937;var yb=null;function zb(a){this.nb=a.code;this.i=a.units;this.c=void 0!==a.extent?a.extent:null;this.f=void 0!==a.worldExtent?a.worldExtent:null;this.b=void 0!==a.axisOrientation?a.axisOrientation:"enu";this.g=void 0!==a.global?a.global:!1;this.a=!(!this.g||!this.c);this.l=a.getPointResolution;this.j=null;this.o=a.metersPerUnit;var b=a.code,c=yb||window.proj4;"function"==typeof c&&(b=c.defs(b),void 0!==b&&(void 0!==b.axis&&void 0===a.axisOrientation&&(this.b=b.axis),void 0===a.metersPerUnit&&(this.o=b.to_meter), -void 0===a.units&&(this.i=b.units)))}k=zb.prototype;k.Fk=function(){return this.nb};k.D=function(){return this.c};k.Kb=function(){return this.i};k.uc=function(){return this.o||xb[this.i]};k.ol=function(){return this.f};k.Zl=function(){return this.g};k.Qp=function(a){this.g=a;this.a=!(!a||!this.c)};k.Mn=function(a){this.c=a;this.a=!(!this.g||!a)};k.$p=function(a){this.f=a};k.Pp=function(a){this.l=a};function Ab(a){zb.call(this,{code:a,units:"m",extent:Bb,global:!0,worldExtent:Cb,getPointResolution:function(a,c){return a/ya(c[1]/6378137)}})}u(Ab,zb);var Db=6378137*Math.PI,Bb=[-Db,-Db,Db,Db],Cb=[-180,-85,180,85],Eb="EPSG:3857 EPSG:102100 EPSG:102113 EPSG:900913 urn:ogc:def:crs:EPSG:6.18:3:3857 urn:ogc:def:crs:EPSG::3857 http://www.opengis.net/gml/srs/epsg.xml#3857".split(" ").map(function(a){return new Ab(a)}); -function Fb(a,b,c){var d=a.length;c=1<c?c:2;void 0===b&&(2<c?b=a.slice():b=Array(d));for(var e=0;e<d;e+=c){b[e]=Db*a[e]/180;var f=6378137*Math.log(Math.tan(Math.PI*(a[e+1]+90)/360));f>Db?f=Db:f<-Db&&(f=-Db);b[e+1]=f}return b}function Gb(a,b,c){var d=a.length;c=1<c?c:2;void 0===b&&(2<c?b=a.slice():b=Array(d));for(var e=0;e<d;e+=c)b[e]=180*a[e]/Db,b[e+1]=360*Math.atan(Math.exp(a[e+1]/6378137))/Math.PI-90;return b};var Hb=new ub(6378137);function Ib(a,b){zb.call(this,{code:a,units:"degrees",extent:Jb,axisOrientation:b,global:!0,metersPerUnit:Kb,worldExtent:Jb})}u(Ib,zb);var Jb=[-180,-90,180,90],Kb=Math.PI*Hb.radius/180,Lb=[new Ib("CRS:84"),new Ib("EPSG:4326","neu"),new Ib("urn:ogc:def:crs:EPSG::4326","neu"),new Ib("urn:ogc:def:crs:EPSG:6.6:4326","neu"),new Ib("urn:ogc:def:crs:OGC:1.3:CRS84"),new Ib("urn:ogc:def:crs:OGC:2:84"),new Ib("http://www.opengis.net/gml/srs/epsg.xml#4326","neu"),new Ib("urn:x-ogc:def:crs:EPSG:4326","neu")];var Mb={};var Nb={};function Ob(a,b,c){a=a.nb;b=b.nb;a in Nb||(Nb[a]={});Nb[a][b]=c}function Qb(a,b){var c;a in Nb&&b in Nb[a]&&(c=Nb[a][b]);return c};function Rb(a,b,c){var d=a.l;d?b=d(b,c):"degrees"!=a.Kb()&&(d=Sb(a,Tb("EPSG:4326")),b=[c[0]-b/2,c[1],c[0]+b/2,c[1],c[0],c[1]-b/2,c[0],c[1]+b/2],b=d(b,b,2),b=(vb.b(b.slice(0,2),b.slice(2,4))+vb.b(b.slice(4,6),b.slice(6,8)))/2,a=a.uc(),void 0!==a&&(b/=a));return b}function Ub(a){Vb(a);a.forEach(function(b){a.forEach(function(a){b!==a&&Ob(b,a,Wb)})})}function Xb(){Lb.forEach(function(a){Eb.forEach(function(b){Ob(a,b,Fb);Ob(b,a,Gb)})})}function Yb(a){Mb[a.nb]=a;Ob(a,a,Wb)} -function Vb(a){var b=[];a.forEach(function(a){b.push(Yb(a))})}function Zb(a){return a?"string"===typeof a?Tb(a):a:Tb("EPSG:3857")}function $b(a,b,c,d){a=Tb(a);b=Tb(b);Ob(a,b,ac(c));Ob(b,a,ac(d))}function ac(a){return function(b,c,d){var e=b.length;d=void 0!==d?d:2;c=void 0!==c?c:Array(e);var f,g;for(g=0;g<e;g+=d)for(f=a([b[g],b[g+1]]),c[g]=f[0],c[g+1]=f[1],f=d-1;2<=f;--f)c[g+f]=b[g+f];return c}} -function Tb(a){var b=null;if(a instanceof zb)b=a;else if("string"===typeof a){var b=Mb[a]||null,c=yb||window.proj4;b||"function"!=typeof c||void 0===c.defs(a)||(b=new zb({code:a}),Yb(b))}return b}function bc(a,b){if(a===b)return!0;var c=a.Kb()===b.Kb();return a.nb===b.nb?c:Sb(a,b)===Wb&&c}function dc(a,b){var c=Tb(a),d=Tb(b);return Sb(c,d)} -function Sb(a,b){var c=a.nb,d=b.nb,e=Qb(c,d);if(!e){var f=yb||window.proj4;if("function"==typeof f){var g=f.defs(c),h=f.defs(d);void 0!==g&&void 0!==h&&(g===h?Ub([b,a]):(e=f(d,c),$b(b,a,e.forward,e.inverse)),e=Qb(c,d))}}e||(e=ec);return e}function ec(a,b){if(void 0!==b&&a!==b){for(var c=0,d=a.length;c<d;++c)b[c]=a[c];a=b}return a}function Wb(a,b){var c;if(void 0!==b){c=0;for(var d=a.length;c<d;++c)b[c]=a[c];c=b}else c=a.slice();return c}function fc(a,b,c){return dc(b,c)(a,void 0,a.length)} -function gc(a,b,c){b=dc(b,c);return pb(a,b)}function hc(){Ub(Eb);Ub(Lb);Xb()}hc();function ic(a,b,c,d){return void 0!==d?(d[0]=a,d[1]=b,d[2]=c,d):[a,b,c]}function jc(a){var b=a[0],c=Array(b),d=1<<b-1,e,f;for(e=0;e<b;++e)f=48,a[1]&d&&(f+=1),a[2]&d&&(f+=2),c[e]=String.fromCharCode(f),d>>=1;return c.join("")};function kc(a){this.minZoom=void 0!==a.minZoom?a.minZoom:0;this.b=a.resolutions;sa(na(this.b,function(a,b){return b-a}),17);this.maxZoom=this.b.length-1;this.g=void 0!==a.origin?a.origin:null;this.c=null;void 0!==a.origins&&(this.c=a.origins,sa(this.c.length==this.b.length,20));var b=a.extent;void 0===b||this.g||this.c||(this.g=fb(b));sa(!this.g&&this.c||this.g&&!this.c,18);this.i=null;void 0!==a.tileSizes&&(this.i=a.tileSizes,sa(this.i.length==this.b.length,19));this.f=void 0!==a.tileSize?a.tileSize: -this.i?null:256;sa(!this.f&&this.i||this.f&&!this.i,22);this.u=void 0!==b?b:null;this.a=null;this.j=[0,0];void 0!==a.sizes?this.a=a.sizes.map(function(a){return new ta(Math.min(0,a[0]),Math.max(a[0]-1,-1),Math.min(0,a[1]),Math.max(a[1]-1,-1))},this):b&&lc(this,b)}var mc=[0,0,0];k=kc.prototype;k.mh=function(a,b,c){a=nc(this,a,b);for(var d=a.da,e=a.ba;d<=e;++d)for(var f=a.ga,g=a.ja;f<=g;++f)c([b,d,f])}; -function oc(a,b,c,d,e){e=a.Ua(b,e);for(b=b[0]-1;b>=a.minZoom;){if(c.call(null,b,nc(a,e,b,d)))return!0;--b}return!1}k.D=function(){return this.u};k.Ni=function(){return this.maxZoom};k.Oi=function(){return this.minZoom};k.Uc=function(a){return this.g?this.g:this.c[a]};k.La=function(a){return this.b[a]};k.Pi=function(){return this.b};function pc(a,b,c,d){return b[0]<a.maxZoom?(d=a.Ua(b,d),nc(a,d,b[0]+1,c)):null} -function qc(a,b,c,d){rc(a,b[0],b[1],c,!1,mc);var e=mc[1],f=mc[2];rc(a,b[2],b[3],c,!0,mc);a=mc[1];b=mc[2];void 0!==d?(d.da=e,d.ba=a,d.ga=f,d.ja=b):d=new ta(e,a,f,b);return d}function nc(a,b,c,d){return qc(a,b,a.La(c),d)}function sc(a,b){var c=a.Uc(b[0]),d=a.La(b[0]),e=Ha(a.eb(b[0]),a.j);return[c[0]+(b[1]+.5)*e[0]*d,c[1]+(b[2]+.5)*e[1]*d]}k.Ua=function(a,b){var c=this.Uc(a[0]),d=this.La(a[0]),e=Ha(this.eb(a[0]),this.j),f=c[0]+a[1]*e[0]*d,c=c[1]+a[2]*e[1]*d;return Wa(f,c,f+e[0]*d,c+e[1]*d,b)}; -k.Ae=function(a,b,c){return rc(this,a[0],a[1],b,!1,c)};function rc(a,b,c,d,e,f){var g=a.Qc(d),h=d/a.La(g),l=a.Uc(g);a=Ha(a.eb(g),a.j);b=h*Math.floor((b-l[0])/d+(e?.5:0))/a[0];c=h*Math.floor((c-l[1])/d+(e?0:.5))/a[1];e?(b=Math.ceil(b)-1,c=Math.ceil(c)-1):(b=Math.floor(b),c=Math.floor(c));return ic(g,b,c,f)}k.Xf=function(a,b,c){return rc(this,a[0],a[1],this.La(b),!1,c)};k.eb=function(a){return this.f?this.f:this.i[a]};k.Qc=function(a,b){return xa(ga(this.b,a,b||0),this.minZoom,this.maxZoom)}; -function lc(a,b){for(var c=a.b.length,d=Array(c),e=a.minZoom;e<c;++e)d[e]=nc(a,b,e);a.a=d};function tc(a){var b=a.j;if(!b){var b=uc(a),c=vc(b,void 0,void 0),b=new kc({extent:b,origin:fb(b),resolutions:c,tileSize:void 0});a.j=b}return b}function wc(a){var b={};qb(b,a?a:{});void 0===b.extent&&(b.extent=Tb("EPSG:3857").D());b.resolutions=vc(b.extent,b.maxZoom,b.tileSize);delete b.maxZoom;return new kc(b)}function vc(a,b,c){b=void 0!==b?b:42;var d=jb(a);a=ib(a);c=Ha(void 0!==c?c:256);c=Math.max(a/c[0],d/c[1]);b+=1;d=Array(b);for(a=0;a<b;++a)d[a]=c/Math.pow(2,a);return d} -function uc(a){a=Tb(a);var b=a.D();b||(a=180*xb.degrees/a.uc(),b=Wa(-a,-a,a,a));return b};function xc(a){this.b=a.html;this.a=a.tileRanges?a.tileRanges:null}xc.prototype.g=function(){return this.b};function yc(a){return function(b){if(b)return[xa(b[0],a[0],a[2]),xa(b[1],a[1],a[3])]}}function zc(a){return a};function Ac(a){function b(b){var c=a.listener,e=a.dh||a.target;a.fh&&Bc(a);return c.call(e,b)}return a.eh=b}function Cc(a,b,c,d){for(var e,f=0,g=a.length;f<g;++f)if(e=a[f],e.listener===b&&e.dh===c)return d&&(e.deleteIndex=f),e}function Dc(a,b){var c=a.mb;return c?c[b]:void 0}function Ec(a){var b=a.mb;b||(b=a.mb={});return b} -function Fc(a,b){var c=Dc(a,b);if(c){for(var d=0,e=c.length;d<e;++d)a.removeEventListener(b,c[d].eh),rb(c[d]);c.length=0;if(c=a.mb)delete c[b],Object.keys(c).length||delete a.mb}}function z(a,b,c,d,e){var f=Ec(a),g=f[b];g||(g=f[b]=[]);(f=Cc(g,c,d,!1))?e||(f.fh=!1):(f={dh:d,fh:!!e,listener:c,target:a,type:b},a.addEventListener(b,Ac(f)),g.push(f));return f}function Gc(a,b,c,d){return z(a,b,c,d,!0)}function Hc(a,b,c,d){(a=Dc(a,b))&&(c=Cc(a,c,d,!0))&&Bc(c)} -function Bc(a){if(a&&a.target){a.target.removeEventListener(a.type,a.eh);var b=Dc(a.target,a.type);if(b){var c="deleteIndex"in a?a.deleteIndex:b.indexOf(a);-1!==c&&b.splice(c,1);b.length||Fc(a.target,a.type)}rb(a)}}function Ic(a){var b=Ec(a),c;for(c in b)Fc(a,c)};function Jc(){}Jc.prototype.$b=!1;function Kc(a){a.$b||(a.$b=!0,a.ra())}Jc.prototype.ra=oa;function Lc(a){this.type=a;this.target=null}Lc.prototype.preventDefault=Lc.prototype.stopPropagation=function(){this.gp=!0};function Mc(a){a.stopPropagation()};function Nc(){this.$a={};this.ta={};this.qa={}}u(Nc,Jc);Nc.prototype.addEventListener=function(a,b){var c=this.qa[a];c||(c=this.qa[a]=[]);-1===c.indexOf(b)&&c.push(b)}; -Nc.prototype.b=function(a){var b="string"===typeof a?new Lc(a):a;a=b.type;b.target=this;var c=this.qa[a],d;if(c){a in this.ta||(this.ta[a]=0,this.$a[a]=0);++this.ta[a];for(var e=0,f=c.length;e<f;++e)if(!1===c[e].call(this,b)||b.gp){d=!1;break}--this.ta[a];if(!this.ta[a]){b=this.$a[a];for(delete this.$a[a];b--;)this.removeEventListener(a,oa);delete this.ta[a]}return d}};Nc.prototype.ra=function(){Ic(this)};function Oc(a,b){return b?b in a.qa:0<Object.keys(a.qa).length} -Nc.prototype.removeEventListener=function(a,b){var c=this.qa[a];if(c){var d=c.indexOf(b);a in this.$a?(c[d]=oa,++this.$a[a]):(c.splice(d,1),c.length||delete this.qa[a])}};function Pc(){Nc.call(this);this.g=0}u(Pc,Nc);k=Pc.prototype;k.s=function(){++this.g;this.b("change")};k.L=function(){return this.g};k.J=function(a,b,c){if(Array.isArray(a)){for(var d=a.length,e=Array(d),f=0;f<d;++f)e[f]=z(this,a[f],b,c);return e}return z(this,a,b,c)};k.once=function(a,b,c){if(Array.isArray(a)){for(var d=a.length,e=Array(d),f=0;f<d;++f)e[f]=Gc(this,a[f],b,c);return e}return Gc(this,a,b,c)}; -k.K=function(a,b,c){if(Array.isArray(a))for(var d=0,e=a.length;d<e;++d)Hc(this,a[d],b,c);else Hc(this,a,b,c)};function Qc(a){Pc.call(this);w(this);this.O={};void 0!==a&&this.H(a)}u(Qc,Pc);var Rc={};function Sc(a){return Rc.hasOwnProperty(a)?Rc[a]:Rc[a]="change:"+a}k=Qc.prototype;k.get=function(a){var b;this.O.hasOwnProperty(a)&&(b=this.O[a]);return b};k.P=function(){return Object.keys(this.O)};k.M=function(){return qb({},this.O)};function Tc(a,b,c){var d;d=Sc(b);a.b(new Uc(d,b,c));a.b(new Uc("propertychange",b,c))}k.set=function(a,b,c){c?this.O[a]=b:(c=this.O[a],this.O[a]=b,c!==b&&Tc(this,a,c))}; -k.H=function(a,b){for(var c in a)this.set(c,a[c],b)};k.R=function(a,b){if(a in this.O){var c=this.O[a];delete this.O[a];b||Tc(this,a,c)}};function Uc(a,b,c){Lc.call(this,a);this.key=b;this.oldValue=c}u(Uc,Lc);function D(a,b){Qc.call(this);this.c=!!(b||{}).unique;this.a=a?a:[];if(this.c)for(var c=0,d=this.a.length;c<d;++c)Vc(this,this.a[c],c);Wc(this)}u(D,Qc);k=D.prototype;k.clear=function(){for(;0<this.fc();)this.pop()};k.ag=function(a){var b,c;b=0;for(c=a.length;b<c;++b)this.push(a[b]);return this};k.forEach=function(a,b){this.a.forEach(a,b)};k.pm=function(){return this.a};k.item=function(a){return this.a[a]};k.fc=function(){return this.get(Xc)}; -k.Ge=function(a,b){this.c&&Vc(this,b);this.a.splice(a,0,b);Wc(this);this.b(new Yc("add",b))};k.pop=function(){return this.Bg(this.fc()-1)};k.push=function(a){this.c&&Vc(this,a);var b=this.fc();this.Ge(b,a);return this.fc()};k.remove=function(a){var b=this.a,c,d;c=0;for(d=b.length;c<d;++c)if(b[c]===a)return this.Bg(c)};k.Bg=function(a){var b=this.a[a];this.a.splice(a,1);Wc(this);this.b(new Yc("remove",b));return b}; -k.Mp=function(a,b){var c=this.fc();if(a<c)this.c&&Vc(this,b,a),c=this.a[a],this.a[a]=b,this.b(new Yc("remove",c)),this.b(new Yc("add",b));else{for(;c<a;++c)this.Ge(c,void 0);this.Ge(a,b)}};function Wc(a){a.set(Xc,a.a.length)}function Vc(a,b,c){for(var d=0,e=a.a.length;d<e;++d)if(a.a[d]===b&&d!==c)throw new qa(58);}var Xc="length";function Yc(a,b){Lc.call(this,a);this.element=b}u(Yc,Lc);var Zc=/^#(?:[0-9a-f]{3}){1,2}$/i,ad=/^([a-z]*)$/i;function bd(a){return Array.isArray(a)?a:cd(a)}function dd(a){if("string"!==typeof a){var b=a[0];b!=(b|0)&&(b=b+.5|0);var c=a[1];c!=(c|0)&&(c=c+.5|0);var d=a[2];d!=(d|0)&&(d=d+.5|0);a="rgba("+b+","+c+","+d+","+(void 0===a[3]?1:a[3])+")"}return a} -var cd=function(){var a={},b=0;return function(c){var d;if(a.hasOwnProperty(c))d=a[c];else{if(1024<=b){d=0;for(var e in a)d++&3||(delete a[e],--b)}d=c;var f;ad.exec(d)&&(e=document.createElement("div"),e.style.color=d,document.body.appendChild(e),d=getComputedStyle(e).color,document.body.removeChild(e));if(Zc.exec(d)){f=d.length-1;sa(3==f||6==f,54);var g=3==f?1:2;f=parseInt(d.substr(1+0*g,g),16);e=parseInt(d.substr(1+1*g,g),16);d=parseInt(d.substr(1+2*g,g),16);1==g&&(f=(f<<4)+f,e=(e<<4)+e,d=(d<<4)+ -d);f=[f,e,d,1]}else d.indexOf("rgba(")?d.indexOf("rgb(")?sa(!1,14):(d=d.slice(4,-1).split(",").map(Number),d.push(1),f=ed(d)):(d=d.slice(5,-1).split(",").map(Number),f=ed(d));d=f;a[c]=d;++b}return d}}();function ed(a){var b=[];b[0]=xa(a[0]+.5|0,0,255);b[1]=xa(a[1]+.5|0,0,255);b[2]=xa(a[2]+.5|0,0,255);b[3]=xa(a[3],0,1);return b};function fd(a){return"string"===typeof a||a instanceof CanvasPattern||a instanceof CanvasGradient?a:dd(a)};function gd(a,b,c){this.center=a;this.resolution=b;this.rotation=c};function hd(a,b){var c=document.createElement("CANVAS");a&&(c.width=a);b&&(c.height=b);return c.getContext("2d")}function id(a,b){var c=b.parentNode;c&&c.replaceChild(a,b)}function jd(a){a&&a.parentNode&&a.parentNode.removeChild(a)};function kd(a){Qc.call(this);this.element=a.element?a.element:null;this.a=this.Z=null;this.u=[];this.render=a.render?a.render:oa;a.target&&this.i(a.target)}u(kd,Qc);kd.prototype.ra=function(){jd(this.element);Qc.prototype.ra.call(this)};kd.prototype.f=function(){return this.a}; -kd.prototype.setMap=function(a){this.a&&jd(this.element);for(var b=0,c=this.u.length;b<c;++b)Bc(this.u[b]);this.u.length=0;if(this.a=a)(this.Z?this.Z:a.v).appendChild(this.element),this.render!==oa&&this.u.push(z(a,"postrender",this.render,this)),a.render()};kd.prototype.i=function(a){this.Z="string"===typeof a?document.getElementById(a):a};function ld(a){a=a?a:{};this.I=document.createElement("UL");this.v=document.createElement("LI");this.I.appendChild(this.v);this.v.style.display="none";this.c=void 0!==a.collapsed?a.collapsed:!0;this.l=void 0!==a.collapsible?a.collapsible:!0;this.l||(this.c=!1);var b=void 0!==a.className?a.className:"ol-attribution",c=void 0!==a.tipLabel?a.tipLabel:"Attributions",d=void 0!==a.collapseLabel?a.collapseLabel:"\u00bb";"string"===typeof d?(this.A=document.createElement("span"),this.A.textContent=d):this.A= -d;d=void 0!==a.label?a.label:"i";"string"===typeof d?(this.C=document.createElement("span"),this.C.textContent=d):this.C=d;var e=this.l&&!this.c?this.A:this.C,d=document.createElement("button");d.setAttribute("type","button");d.title=c;d.appendChild(e);z(d,"click",this.Pm,this);c=document.createElement("div");c.className=b+" ol-unselectable ol-control"+(this.c&&this.l?" ol-collapsed":"")+(this.l?"":" ol-uncollapsible");c.appendChild(this.I);c.appendChild(d);kd.call(this,{element:c,render:a.render? -a.render:md,target:a.target});this.G=!0;this.o={};this.j={};this.T={}}u(ld,kd); -function md(a){if(a=a.frameState){var b,c,d,e,f,g,h,l,m,n,p,q=a.layerStatesArray,r=qb({},a.attributions),v={},x={},y=a.viewState.projection;c=0;for(b=q.length;c<b;c++)if(g=q[c].layer.ka())if(n=w(g).toString(),m=g.j)for(d=0,e=m.length;d<e;d++)if(h=m[d],l=w(h).toString(),!(l in r)){if(f=a.usedTiles[n]){var A=g.Jb(y);a:{p=void 0;var B,aa,Ra=h,ra=A,Ka=y;if(Ra.a){for(p in f)if(p in Ra.a){var A=f[p],C;aa=0;for(B=Ra.a[p].length;aa<B;++aa){C=Ra.a[p][aa];if(wa(C,A)){p=!0;break a}var Na=nc(ra,uc(Ka),parseInt(p, -10)),wb=Na.ba-Na.da+1;if(A.da<Na.da||A.ba>Na.ba)if(wa(C,new ta(Da(A.da,wb),Da(A.ba,wb),A.ga,A.ja))||A.ba-A.da+1>wb&&wa(C,Na)){p=!0;break a}}}p=!1}else p=!0}}else p=!1;p?(l in v&&delete v[l],p=h.b,p in x||(x[p]=!0,r[l]=h)):v[l]=h}b=[r,v];c=b[0];b=b[1];for(var Z in this.o)Z in c?(this.j[Z]||(this.o[Z].style.display="",this.j[Z]=!0),delete c[Z]):Z in b?(this.j[Z]&&(this.o[Z].style.display="none",delete this.j[Z]),delete b[Z]):(jd(this.o[Z]),delete this.o[Z],delete this.j[Z]);for(Z in c)d=document.createElement("LI"), -d.innerHTML=c[Z].b,this.I.appendChild(d),this.o[Z]=d,this.j[Z]=!0;for(Z in b)d=document.createElement("LI"),d.innerHTML=b[Z].b,d.style.display="none",this.I.appendChild(d),this.o[Z]=d;Z=!tb(this.j)||!tb(a.logos);this.G!=Z&&(this.element.style.display=Z?"":"none",this.G=Z);Z&&tb(this.j)?this.element.classList.add("ol-logo-only"):this.element.classList.remove("ol-logo-only");var Ta;a=a.logos;Z=this.T;for(Ta in Z)Ta in a||(jd(Z[Ta]),delete Z[Ta]);for(var Pb in a)b=a[Pb],b instanceof HTMLElement&&(this.v.appendChild(b), -Z[Pb]=b),Pb in Z||(Ta=new Image,Ta.src=Pb,""===b?c=Ta:(c=document.createElement("a"),c.href=b,c.appendChild(Ta)),this.v.appendChild(c),Z[Pb]=c);this.v.style.display=tb(a)?"none":""}else this.G&&(this.element.style.display="none",this.G=!1)}k=ld.prototype;k.Pm=function(a){a.preventDefault();nd(this)};function nd(a){a.element.classList.toggle("ol-collapsed");a.c?id(a.A,a.C):id(a.C,a.A);a.c=!a.c}k.Om=function(){return this.l}; -k.Rm=function(a){this.l!==a&&(this.l=a,this.element.classList.toggle("ol-uncollapsible"),!a&&this.c&&nd(this))};k.Qm=function(a){this.l&&this.c!==a&&nd(this)};k.Nm=function(){return this.c};function od(a){return Math.pow(a,3)}function pd(a){return 1-od(1-a)}function qd(a){return 3*a*a-2*a*a*a}function rd(a){return a};function sd(a){a=a?a:{};var b=void 0!==a.className?a.className:"ol-rotate",c=void 0!==a.label?a.label:"\u21e7";this.c=null;"string"===typeof c?(this.c=document.createElement("span"),this.c.className="ol-compass",this.c.textContent=c):(this.c=c,this.c.classList.add("ol-compass"));var d=a.tipLabel?a.tipLabel:"Reset rotation",c=document.createElement("button");c.className=b+"-reset";c.setAttribute("type","button");c.title=d;c.appendChild(this.c);z(c,"click",sd.prototype.A,this);d=document.createElement("div"); -d.className=b+" ol-unselectable ol-control";d.appendChild(c);b=a.render?a.render:td;this.l=a.resetNorth?a.resetNorth:void 0;kd.call(this,{element:d,render:b,target:a.target});this.o=void 0!==a.duration?a.duration:250;this.j=void 0!==a.autoHide?a.autoHide:!0;this.v=void 0;this.j&&this.element.classList.add("ol-hidden")}u(sd,kd);sd.prototype.A=function(a){a.preventDefault();this.l?this.l():(a=this.a.$())&&void 0!==a.Sa()&&(0<this.o?a.animate({rotation:0,duration:this.o,easing:pd}):a.Ne(0))}; -function td(a){if(a=a.frameState){a=a.viewState.rotation;if(a!=this.v){var b="rotate("+a+"rad)";if(this.j){var c=this.element.classList.contains("ol-hidden");c||a?c&&a&&this.element.classList.remove("ol-hidden"):this.element.classList.add("ol-hidden")}this.c.style.msTransform=b;this.c.style.webkitTransform=b;this.c.style.transform=b}this.v=a}};function ud(a){a=a?a:{};var b=void 0!==a.className?a.className:"ol-zoom",c=void 0!==a.delta?a.delta:1,d=void 0!==a.zoomInLabel?a.zoomInLabel:"+",e=void 0!==a.zoomOutLabel?a.zoomOutLabel:"\u2212",f=void 0!==a.zoomInTipLabel?a.zoomInTipLabel:"Zoom in",g=void 0!==a.zoomOutTipLabel?a.zoomOutTipLabel:"Zoom out",h=document.createElement("button");h.className=b+"-in";h.setAttribute("type","button");h.title=f;h.appendChild("string"===typeof d?document.createTextNode(d):d);z(h,"click",ud.prototype.j.bind(this, -c));d=document.createElement("button");d.className=b+"-out";d.setAttribute("type","button");d.title=g;d.appendChild("string"===typeof e?document.createTextNode(e):e);z(d,"click",ud.prototype.j.bind(this,-c));c=document.createElement("div");c.className=b+" ol-unselectable ol-control";c.appendChild(h);c.appendChild(d);kd.call(this,{element:c,target:a.target});this.c=void 0!==a.duration?a.duration:250}u(ud,kd); -ud.prototype.j=function(a,b){b.preventDefault();var c=this.a.$();if(c){var d=c.Ra();d&&(d=c.constrainResolution(d,a),0<this.c?(c.Kc()&&c.kd(),c.animate({resolution:d,duration:this.c,easing:pd})):c.$c(d))}};function vd(a){a=a?a:{};var b=new D;(void 0!==a.zoom?a.zoom:1)&&b.push(new ud(a.zoomOptions));(void 0!==a.rotate?a.rotate:1)&&b.push(new sd(a.rotateOptions));(void 0!==a.attribution?a.attribution:1)&&b.push(new ld(a.attributionOptions));return b};function wd(a){a=a?a:{};this.c=void 0!==a.className?a.className:"ol-full-screen";var b=void 0!==a.label?a.label:"\u2922";this.l="string"===typeof b?document.createTextNode(b):b;b=void 0!==a.labelActive?a.labelActive:"\u00d7";this.o="string"===typeof b?document.createTextNode(b):b;var c=a.tipLabel?a.tipLabel:"Toggle full-screen",b=document.createElement("button");b.className=this.c+"-"+xd();b.setAttribute("type","button");b.title=c;b.appendChild(this.l);z(b,"click",this.C,this);c=document.createElement("div"); -c.className=this.c+" ol-unselectable ol-control "+(yd()?"":"ol-unsupported");c.appendChild(b);kd.call(this,{element:c,target:a.target});this.A=void 0!==a.keys?a.keys:!1;this.j=a.source}u(wd,kd); -wd.prototype.C=function(a){a.preventDefault();yd()&&(a=this.a)&&(xd()?document.exitFullscreen?document.exitFullscreen():document.msExitFullscreen?document.msExitFullscreen():document.mozCancelFullScreen?document.mozCancelFullScreen():document.webkitExitFullscreen&&document.webkitExitFullscreen():(a=this.j?"string"===typeof this.j?document.getElementById(this.j):this.j:a.vc(),this.A?a.mozRequestFullScreenWithKeys?a.mozRequestFullScreenWithKeys():a.webkitRequestFullscreen?a.webkitRequestFullscreen(Element.ALLOW_KEYBOARD_INPUT): -zd(a):zd(a)))};wd.prototype.v=function(){var a=this.element.firstElementChild,b=this.a;xd()?(a.className=this.c+"-true",id(this.o,this.l)):(a.className=this.c+"-false",id(this.l,this.o));b&&b.Cd()};wd.prototype.setMap=function(a){kd.prototype.setMap.call(this,a);a&&this.u.push(z(document,Ad(),this.v,this))}; -function yd(){var a=document.body;return!!(a.webkitRequestFullscreen||a.mozRequestFullScreen&&document.mozFullScreenEnabled||a.msRequestFullscreen&&document.msFullscreenEnabled||a.requestFullscreen&&document.fullscreenEnabled)}function xd(){return!!(document.webkitIsFullScreen||document.mozFullScreen||document.msFullscreenElement||document.fullscreenElement)} -function zd(a){a.requestFullscreen?a.requestFullscreen():a.msRequestFullscreen?a.msRequestFullscreen():a.mozRequestFullScreen?a.mozRequestFullScreen():a.webkitRequestFullscreen&&a.webkitRequestFullscreen()}var Ad=function(){var a;return function(){if(!a){var b=document.body;b.webkitRequestFullscreen?a="webkitfullscreenchange":b.mozRequestFullScreen?a="mozfullscreenchange":b.msRequestFullscreen?a="MSFullscreenChange":b.requestFullscreen&&(a="fullscreenchange")}return a}}();function Bd(a){a=a?a:{};var b=document.createElement("DIV");b.className=void 0!==a.className?a.className:"ol-mouse-position";kd.call(this,{element:b,render:a.render?a.render:Cd,target:a.target});z(this,Sc(Dd),this.Sm,this);a.coordinateFormat&&this.fj(a.coordinateFormat);a.projection&&this.Th(Tb(a.projection));this.v=void 0!==a.undefinedHTML?a.undefinedHTML:"";this.o=b.innerHTML;this.l=this.j=this.c=null}u(Bd,kd); -function Cd(a){a=a.frameState;a?this.c!=a.viewState.projection&&(this.c=a.viewState.projection,this.j=null):this.c=null;Ed(this,this.l)}k=Bd.prototype;k.Sm=function(){this.j=null};k.qh=function(){return this.get(Fd)};k.Sh=function(){return this.get(Dd)};k.Gl=function(a){this.l=this.a.xe(a);Ed(this,this.l)};k.Hl=function(){Ed(this,null);this.l=null};k.setMap=function(a){kd.prototype.setMap.call(this,a);a&&(a=a.c,this.u.push(z(a,"mousemove",this.Gl,this),z(a,"mouseout",this.Hl,this)))}; -k.fj=function(a){this.set(Fd,a)};k.Th=function(a){this.set(Dd,a)};function Ed(a,b){var c=a.v;if(b&&a.c){if(!a.j){var d=a.Sh();a.j=d?Sb(a.c,d):ec}if(d=a.a.Xa(b))a.j(d,d),c=(c=a.qh())?c(d):d.toString()}a.o&&c==a.o||(a.element.innerHTML=c,a.o=c)}var Dd="projection",Fd="coordinateFormat";function Gd(a,b,c){Lc.call(this,a);this.map=b;this.frameState=void 0!==c?c:null}u(Gd,Lc);function Hd(a,b,c,d,e){Gd.call(this,a,b,e);this.originalEvent=c;this.pixel=b.xe(c);this.coordinate=b.Xa(this.pixel);this.dragging=void 0!==d?d:!1}u(Hd,Gd);Hd.prototype.preventDefault=function(){Gd.prototype.preventDefault.call(this);this.originalEvent.preventDefault()};Hd.prototype.stopPropagation=function(){Gd.prototype.stopPropagation.call(this);this.originalEvent.stopPropagation()};var Id={xq:"singleclick",mq:"click",nq:"dblclick",qq:"pointerdrag",tq:"pointermove",pq:"pointerdown",wq:"pointerup",vq:"pointerover",uq:"pointerout",rq:"pointerenter",sq:"pointerleave",oq:"pointercancel"};function Kd(a,b,c,d,e){Hd.call(this,a,b,c.b,d,e);this.b=c}u(Kd,Hd);var Ld=["experimental-webgl","webgl","webkit-3d","moz-webgl"];function Md(a,b){var c,d,e=Ld.length;for(d=0;d<e;++d)try{if(c=a.getContext(Ld[d],b))return c}catch(f){}return null};var Nd,Od="undefined"!==typeof navigator?navigator.userAgent.toLowerCase():"",Pd=-1!==Od.indexOf("firefox"),Qd=-1!==Od.indexOf("safari")&&-1==Od.indexOf("chrom"),Rd=-1!==Od.indexOf("webkit")&&-1==Od.indexOf("edge"),Sd=-1!==Od.indexOf("macintosh"),Td=window.devicePixelRatio||1,Ud=!1,Vd=function(){if(!("HTMLCanvasElement"in window))return!1;try{var a=document.createElement("CANVAS").getContext("2d");return a?(void 0!==a.setLineDash&&(Ud=!0),!0):!1}catch(b){return!1}}(),Wd="DeviceOrientationEvent"in -window,Xd="geolocation"in navigator,Yd="ontouchstart"in window,Zd="PointerEvent"in window,$d=!!navigator.msPointerEnabled,ae=!1,be,ce=[];if("WebGLRenderingContext"in window)try{var de=Md(document.createElement("CANVAS"),{failIfMajorPerformanceCaveat:!0});de&&(ae=!0,be=de.getParameter(de.MAX_TEXTURE_SIZE),ce=de.getSupportedExtensions())}catch(a){}Nd=ae;da=ce;ca=be;function ee(a,b){this.b=a;this.i=b};function fe(a){ee.call(this,a,{mousedown:this.am,mousemove:this.bm,mouseup:this.em,mouseover:this.dm,mouseout:this.cm});this.a=a.g;this.g=[]}u(fe,ee);function ge(a,b){for(var c=a.g,d=b.clientX,e=b.clientY,f=0,g=c.length,h;f<g&&(h=c[f]);f++){var l=Math.abs(e-h[1]);if(25>=Math.abs(d-h[0])&&25>=l)return!0}return!1}function he(a){var b=ie(a,a),c=b.preventDefault;b.preventDefault=function(){a.preventDefault();c()};b.pointerId=1;b.isPrimary=!0;b.pointerType="mouse";return b}k=fe.prototype; -k.am=function(a){if(!ge(this,a)){(1).toString()in this.a&&this.cancel(a);var b=he(a);this.a[(1).toString()]=a;je(this.b,"pointerdown",b,a)}};k.bm=function(a){if(!ge(this,a)){var b=he(a);je(this.b,"pointermove",b,a)}};k.em=function(a){if(!ge(this,a)){var b=this.a[(1).toString()];b&&b.button===a.button&&(b=he(a),je(this.b,"pointerup",b,a),delete this.a[(1).toString()])}};k.dm=function(a){if(!ge(this,a)){var b=he(a);ke(this.b,b,a)}};k.cm=function(a){if(!ge(this,a)){var b=he(a);le(this.b,b,a)}}; -k.cancel=function(a){var b=he(a);this.b.cancel(b,a);delete this.a[(1).toString()]};function me(a){ee.call(this,a,{MSPointerDown:this.jm,MSPointerMove:this.km,MSPointerUp:this.nm,MSPointerOut:this.lm,MSPointerOver:this.mm,MSPointerCancel:this.im,MSGotPointerCapture:this.gm,MSLostPointerCapture:this.hm});this.a=a.g;this.g=["","unavailable","touch","pen","mouse"]}u(me,ee);function ne(a,b){var c=b;"number"===typeof b.pointerType&&(c=ie(b,b),c.pointerType=a.g[b.pointerType]);return c}k=me.prototype; -k.jm=function(a){this.a[a.pointerId.toString()]=a;var b=ne(this,a);je(this.b,"pointerdown",b,a)};k.km=function(a){var b=ne(this,a);je(this.b,"pointermove",b,a)};k.nm=function(a){var b=ne(this,a);je(this.b,"pointerup",b,a);delete this.a[a.pointerId.toString()]};k.lm=function(a){var b=ne(this,a);le(this.b,b,a)};k.mm=function(a){var b=ne(this,a);ke(this.b,b,a)};k.im=function(a){var b=ne(this,a);this.b.cancel(b,a);delete this.a[a.pointerId.toString()]}; -k.hm=function(a){this.b.b(new oe("lostpointercapture",a,a))};k.gm=function(a){this.b.b(new oe("gotpointercapture",a,a))};function pe(a){ee.call(this,a,{pointerdown:this.Yo,pointermove:this.Zo,pointerup:this.bp,pointerout:this.$o,pointerover:this.ap,pointercancel:this.Xo,gotpointercapture:this.pl,lostpointercapture:this.$l})}u(pe,ee);k=pe.prototype;k.Yo=function(a){qe(this.b,a)};k.Zo=function(a){qe(this.b,a)};k.bp=function(a){qe(this.b,a)};k.$o=function(a){qe(this.b,a)};k.ap=function(a){qe(this.b,a)};k.Xo=function(a){qe(this.b,a)};k.$l=function(a){qe(this.b,a)};k.pl=function(a){qe(this.b,a)};function oe(a,b,c){Lc.call(this,a);this.b=b;a=c?c:{};this.buttons=se(a);this.pressure=te(a,this.buttons);this.bubbles="bubbles"in a?a.bubbles:!1;this.cancelable="cancelable"in a?a.cancelable:!1;this.view="view"in a?a.view:null;this.detail="detail"in a?a.detail:null;this.screenX="screenX"in a?a.screenX:0;this.screenY="screenY"in a?a.screenY:0;this.clientX="clientX"in a?a.clientX:0;this.clientY="clientY"in a?a.clientY:0;this.button="button"in a?a.button:0;this.relatedTarget="relatedTarget"in a?a.relatedTarget: -null;this.pointerId="pointerId"in a?a.pointerId:0;this.width="width"in a?a.width:0;this.height="height"in a?a.height:0;this.pointerType="pointerType"in a?a.pointerType:"";this.isPrimary="isPrimary"in a?a.isPrimary:!1;b.preventDefault&&(this.preventDefault=function(){b.preventDefault()})}u(oe,Lc);function se(a){if(a.buttons||ue)a=a.buttons;else switch(a.which){case 1:a=1;break;case 2:a=4;break;case 3:a=2;break;default:a=0}return a} -function te(a,b){var c=0;a.pressure?c=a.pressure:c=b?.5:0;return c}var ue=!1;try{ue=1===(new MouseEvent("click",{buttons:1})).buttons}catch(a){};function ve(a,b){ee.call(this,a,{touchstart:this.gq,touchmove:this.fq,touchend:this.eq,touchcancel:this.cq});this.a=a.g;this.j=b;this.g=void 0;this.f=0;this.c=void 0}u(ve,ee);k=ve.prototype;k.dj=function(){this.f=0;this.c=void 0}; -function we(a,b,c){b=ie(b,c);b.pointerId=c.identifier+2;b.bubbles=!0;b.cancelable=!0;b.detail=a.f;b.button=0;b.buttons=1;b.width=c.webkitRadiusX||c.radiusX||0;b.height=c.webkitRadiusY||c.radiusY||0;b.pressure=c.webkitForce||c.force||.5;b.isPrimary=a.g===c.identifier;b.pointerType="touch";b.clientX=c.clientX;b.clientY=c.clientY;b.screenX=c.screenX;b.screenY=c.screenY;return b} -function xe(a,b,c){function d(){b.preventDefault()}var e=Array.prototype.slice.call(b.changedTouches),f=e.length,g,h;for(g=0;g<f;++g)h=we(a,b,e[g]),h.preventDefault=d,c.call(a,b,h)} -k.gq=function(a){var b=a.touches,c=Object.keys(this.a),d=c.length;if(d>=b.length){var e=[],f,g,h;for(f=0;f<d;++f){g=c[f];h=this.a[g];var l;if(!(l=1==g))a:{for(var m=b.length,n=0;n<m;n++)if(l=b[n],l.identifier===g-2){l=!0;break a}l=!1}l||e.push(h.out)}for(f=0;f<e.length;++f)this.Gf(a,e[f])}b=a.changedTouches[0];c=Object.keys(this.a).length;if(!c||1===c&&(1).toString()in this.a)this.g=b.identifier,void 0!==this.c&&clearTimeout(this.c);ye(this,a);this.f++;xe(this,a,this.To)}; -k.To=function(a,b){this.a[b.pointerId]={target:b.target,out:b,Qi:b.target};var c=this.b;b.bubbles=!0;je(c,"pointerover",b,a);c=this.b;b.bubbles=!1;je(c,"pointerenter",b,a);je(this.b,"pointerdown",b,a)};k.fq=function(a){a.preventDefault();xe(this,a,this.fm)}; -k.fm=function(a,b){var c=this.a[b.pointerId];if(c){var d=c.out,e=c.Qi;je(this.b,"pointermove",b,a);d&&e!==b.target&&(d.relatedTarget=b.target,b.relatedTarget=e,d.target=e,b.target?(le(this.b,d,a),ke(this.b,b,a)):(b.target=e,b.relatedTarget=null,this.Gf(a,b)));c.out=b;c.Qi=b.target}};k.eq=function(a){ye(this,a);xe(this,a,this.hq)}; -k.hq=function(a,b){je(this.b,"pointerup",b,a);this.b.out(b,a);ze(this.b,b,a);delete this.a[b.pointerId];b.isPrimary&&(this.g=void 0,this.c=setTimeout(this.dj.bind(this),200))};k.cq=function(a){xe(this,a,this.Gf)};k.Gf=function(a,b){this.b.cancel(b,a);this.b.out(b,a);ze(this.b,b,a);delete this.a[b.pointerId];b.isPrimary&&(this.g=void 0,this.c=setTimeout(this.dj.bind(this),200))}; -function ye(a,b){var c=a.j.g,d=b.changedTouches[0];if(a.g===d.identifier){var e=[d.clientX,d.clientY];c.push(e);setTimeout(function(){var a=c.indexOf(e);-1<a&&c.splice(a,1)},2500)}};function Ae(a){Nc.call(this);this.f=a;this.g={};this.i={};this.a=[];Zd?Be(this,new pe(this)):$d?Be(this,new me(this)):(a=new fe(this),Be(this,a),Yd&&Be(this,new ve(this,a)));a=this.a.length;for(var b,c=0;c<a;c++)b=this.a[c],Ce(this,Object.keys(b.i))}u(Ae,Nc);function Be(a,b){var c=Object.keys(b.i);c&&(c.forEach(function(a){var c=b.i[a];c&&(this.i[a]=c.bind(b))},a),a.a.push(b))}Ae.prototype.c=function(a){var b=this.i[a.type];b&&b(a)}; -function Ce(a,b){b.forEach(function(a){z(this.f,a,this.c,this)},a)}function De(a,b){b.forEach(function(a){Hc(this.f,a,this.c,this)},a)}function ie(a,b){for(var c={},d,e=0,f=Ee.length;e<f;e++)d=Ee[e][0],c[d]=a[d]||b[d]||Ee[e][1];return c}function ze(a,b,c){b.bubbles=!1;je(a,"pointerleave",b,c)}Ae.prototype.out=function(a,b){a.bubbles=!0;je(this,"pointerout",a,b)};Ae.prototype.cancel=function(a,b){je(this,"pointercancel",a,b)}; -function le(a,b,c){a.out(b,c);var d=b.target,e=b.relatedTarget;d&&e&&d.contains(e)||ze(a,b,c)}function ke(a,b,c){b.bubbles=!0;je(a,"pointerover",b,c);var d=b.target,e=b.relatedTarget;d&&e&&d.contains(e)||(b.bubbles=!1,je(a,"pointerenter",b,c))}function je(a,b,c,d){a.b(new oe(b,d,c))}function qe(a,b){a.b(new oe(b.type,b,b))}Ae.prototype.ra=function(){for(var a=this.a.length,b,c=0;c<a;c++)b=this.a[c],De(this,Object.keys(b.i));Nc.prototype.ra.call(this)}; -var Ee=[["bubbles",!1],["cancelable",!1],["view",null],["detail",null],["screenX",0],["screenY",0],["clientX",0],["clientY",0],["ctrlKey",!1],["altKey",!1],["shiftKey",!1],["metaKey",!1],["button",0],["relatedTarget",null],["buttons",0],["pointerId",0],["width",0],["height",0],["pressure",0],["tiltX",0],["tiltY",0],["pointerType",""],["hwTimestamp",0],["isPrimary",!1],["type",""],["target",null],["currentTarget",null],["which",0]];function Fe(a){Nc.call(this);this.c=a;this.j=0;this.l=!1;this.i=[];this.g=null;a=this.c.c;this.O=0;this.v={};this.f=new Ae(a);this.a=null;this.o=z(this.f,"pointerdown",this.Jl,this);this.u=z(this.f,"pointermove",this.Bp,this)}u(Fe,Nc);function Ge(a,b){var c=new Kd("click",a.c,b);a.b(c);a.j?(clearTimeout(a.j),a.j=0,c=new Kd("dblclick",a.c,b),a.b(c)):a.j=setTimeout(function(){this.j=0;var a=new Kd("singleclick",this.c,b);this.b(a)}.bind(a),250)} -function He(a,b){"pointerup"==b.type||"pointercancel"==b.type?delete a.v[b.pointerId]:"pointerdown"==b.type&&(a.v[b.pointerId]=!0);a.O=Object.keys(a.v).length}k=Fe.prototype;k.Ch=function(a){He(this,a);var b=new Kd("pointerup",this.c,a);this.b(b);this.l||a.button||Ge(this,this.g);this.O||(this.i.forEach(Bc),this.i.length=0,this.l=!1,this.g=null,Kc(this.a),this.a=null)}; -k.Jl=function(a){He(this,a);var b=new Kd("pointerdown",this.c,a);this.b(b);this.g=a;this.i.length||(this.a=new Ae(document),this.i.push(z(this.a,"pointermove",this.Dm,this),z(this.a,"pointerup",this.Ch,this),z(this.f,"pointercancel",this.Ch,this)))};k.Dm=function(a){if(a.clientX!=this.g.clientX||a.clientY!=this.g.clientY){this.l=!0;var b=new Kd("pointerdrag",this.c,a,this.l);this.b(b)}a.preventDefault()}; -k.Bp=function(a){this.b(new Kd(a.type,this.c,a,!(!this.g||a.clientX==this.g.clientX&&a.clientY==this.g.clientY)))};k.ra=function(){this.u&&(Bc(this.u),this.u=null);this.o&&(Bc(this.o),this.o=null);this.i.forEach(Bc);this.i.length=0;this.a&&(Kc(this.a),this.a=null);this.f&&(Kc(this.f),this.f=null);Nc.prototype.ra.call(this)};function Ie(a,b){this.o=a;this.c=b;this.b=[];this.g=[];this.a={}}Ie.prototype.clear=function(){this.b.length=0;this.g.length=0;rb(this.a)};function Je(a){var b=a.b,c=a.g,d=b[0];1==b.length?(b.length=0,c.length=0):(b[0]=b.pop(),c[0]=c.pop(),Ke(a,0));b=a.c(d);delete a.a[b];return d}Ie.prototype.i=function(a){sa(!(this.c(a)in this.a),31);var b=this.o(a);return Infinity!=b?(this.b.push(a),this.g.push(b),this.a[this.c(a)]=!0,Le(this,0,this.b.length-1),!0):!1}; -function Ke(a,b){for(var c=a.b,d=a.g,e=c.length,f=c[b],g=d[b],h=b;b<e>>1;){var l=2*b+1,m=2*b+2,l=m<e&&d[m]<d[l]?m:l;c[b]=c[l];d[b]=d[l];b=l}c[b]=f;d[b]=g;Le(a,h,b)}function Le(a,b,c){var d=a.b;a=a.g;for(var e=d[c],f=a[c];c>b;){var g=c-1>>1;if(a[g]>f)d[c]=d[g],a[c]=a[g],c=g;else break}d[c]=e;a[c]=f}function Me(a){var b=a.o,c=a.b,d=a.g,e=0,f=c.length,g,h,l;for(h=0;h<f;++h)g=c[h],l=b(g),Infinity==l?delete a.a[a.c(g)]:(d[e]=l,c[e++]=g);c.length=e;d.length=e;for(b=(a.b.length>>1)-1;0<=b;b--)Ke(a,b)};function Ne(a,b){Ie.call(this,function(b){return a.apply(null,b)},function(a){return a[0].hb()});this.u=b;this.j=0;this.f={}}u(Ne,Ie);Ne.prototype.i=function(a){var b=Ie.prototype.i.call(this,a);b&&z(a[0],"change",this.l,this);return b};Ne.prototype.l=function(a){a=a.target;var b=a.V();if(2===b||3===b||4===b||5===b)Hc(a,"change",this.l,this),a=a.hb(),a in this.f&&(delete this.f[a],--this.j),this.u()}; -function Oe(a,b,c){for(var d=0,e,f;a.j<b&&d<c&&0<a.b.length;)e=Je(a)[0],f=e.hb(),0!==e.V()||f in a.f||(a.f[f]=!0,++a.j,++d,e.load())};function Pe(a){return function(b,c,d){if(void 0!==b)return b=ga(a,b,d),b=xa(b+c,0,a.length-1),c=Math.floor(b),b!=c&&c<a.length-1?a[c]/Math.pow(a[c]/a[c+1],b-c):a[c]}}function Qe(a,b,c){return function(d,e,f){if(void 0!==d)return d=Math.max(Math.floor(Math.log(b/d)/Math.log(a)+(-f/2+.5))+e,0),void 0!==c&&(d=Math.min(d,c)),b/Math.pow(a,d)}};function Re(a){if(void 0!==a)return 0}function Se(a,b){if(void 0!==a)return a+b}function Te(a){var b=2*Math.PI/a;return function(a,d){if(void 0!==a)return a=Math.floor((a+d)/b+.5)*b}}function Ue(){var a=Ca(5);return function(b,c){if(void 0!==b)return Math.abs(b+c)<=a?0:b+c}};function Ve(a,b){var c=void 0!==b?a.toFixed(b):""+a,d=c.indexOf("."),d=-1===d?c.length:d;return 2<d?c:Array(3-d).join("0")+c}function We(a){a=(""+a).split(".");for(var b=["1","3"],c=0;c<Math.max(a.length,b.length);c++){var d=parseInt(a[c]||"0",10),e=parseInt(b[c]||"0",10);if(d>e)return 1;if(e>d)return-1}return 0};function Xe(a,b){a[0]+=b[0];a[1]+=b[1];return a}function Ye(a,b){var c=a[0],d=a[1],e=b[0],f=b[1],g=e[0],e=e[1],h=f[0],f=f[1],l=h-g,m=f-e,c=l||m?(l*(c-g)+m*(d-e))/(l*l+m*m||0):0;0>=c||(1<=c?(g=h,e=f):(g+=c*l,e+=c*m));return[g,e]} -function Ze(a,b,c){a=Da(a+180,360)-180;var d=Math.abs(3600*a);c=c||0;var e=Math.pow(10,c),f=Math.floor(d/3600),g=Math.floor((d-3600*f)/60),d=Math.ceil((d-3600*f-60*g)*e)/e;60<=d&&(d=0,g+=1);60<=g&&(g=0,f+=1);return f+"\u00b0 "+Ve(g)+"\u2032 "+Ve(d,c)+"\u2033 "+b.charAt(0>a?1:0)}function $e(a,b,c){return a?b.replace("{x}",a[0].toFixed(c)).replace("{y}",a[1].toFixed(c)):""}function af(a,b){for(var c=!0,d=a.length-1;0<=d;--d)if(a[d]!=b[d]){c=!1;break}return c} -function cf(a,b){var c=Math.cos(b),d=Math.sin(b),e=a[1]*c+a[0]*d;a[0]=a[0]*c-a[1]*d;a[1]=e;return a}function df(a,b){a[0]*=b;a[1]*=b}function ef(a,b){var c=a[0]-b[0],d=a[1]-b[1];return c*c+d*d}function ff(a,b){return Math.sqrt(ef(a,b))}function gf(a,b){return ef(a,Ye(a,b))}function hf(a,b){return $e(a,"{x}, {y}",b)};function jf(){return!0}function kf(){return!1};function lf(){Qc.call(this);this.o=Ja();this.u=-1;this.i={};this.l=this.f=0}u(lf,Qc);k=lf.prototype;k.Ab=function(a,b){var c=b?b:[NaN,NaN];this.Hb(a[0],a[1],c,Infinity);return c};k.sb=function(a){return this.Sc(a[0],a[1])};k.Sc=kf;k.D=function(a){this.u!=this.g&&(this.o=this.se(this.o),this.u=this.g);var b=this.o;a?(a[0]=b[0],a[1]=b[1],a[2]=b[2],a[3]=b[3]):a=b;return a};k.Qb=function(a){return this.Td(a*a)};k.tb=function(a,b){this.Fc(dc(a,b));return this};function mf(a,b,c,d,e,f){for(var g=f?f:[],h=0;b<c;b+=d){var l=a[b],m=a[b+1];g[h++]=e[0]*l+e[2]*m+e[4];g[h++]=e[1]*l+e[3]*m+e[5]}f&&g.length!=h&&(g.length=h);return g}function nf(a,b,c,d,e,f){var g=f?f:[],h=0,l,m;for(l=0;l<b;l+=c)for(g[h++]=a[l]+d,g[h++]=a[l+1]+e,m=l+2;m<l+c;++m)g[h++]=a[m];f&&g.length!=h&&(g.length=h);return g};function of(){lf.call(this);this.la="XY";this.a=2;this.B=null}u(of,lf);function pf(a){var b;"XY"==a?b=2:"XYZ"==a||"XYM"==a?b=3:"XYZM"==a&&(b=4);return b}k=of.prototype;k.Sc=kf;k.se=function(a){return Ya(this.B,0,this.B.length,this.a,a)};k.cc=function(){return this.B.slice(0,this.a)};k.ia=function(){return this.B};k.dc=function(){return this.B.slice(this.B.length-this.a)};k.ec=function(){return this.la}; -k.Td=function(a){this.l!=this.g&&(rb(this.i),this.f=0,this.l=this.g);if(0>a||this.f&&a<=this.f)return this;var b=a.toString();if(this.i.hasOwnProperty(b))return this.i[b];var c=this.od(a);if(c.ia().length<this.B.length)return this.i[b]=c;this.f=a;return this};k.od=function(){return this};k.sa=function(){return this.a};function qf(a,b,c){a.a=pf(b);a.la=b;a.B=c} -function rf(a,b,c,d){if(b)c=pf(b);else{for(b=0;b<d;++b)if(c.length)c=c[0];else{a.la="XY";a.a=2;return}c=c.length;var e;2==c?e="XY":3==c?e="XYZ":4==c&&(e="XYZM");b=e}a.la=b;a.a=c}k.Fc=function(a){this.B&&(a(this.B,this.B,this.a),this.s())}; -k.rotate=function(a,b){var c=this.ia();if(c){for(var d=c.length,e=this.sa(),f=c?c:[],g=Math.cos(a),h=Math.sin(a),l=b[0],m=b[1],n=0,p=0;p<d;p+=e){var q=c[p]-l,r=c[p+1]-m;f[n++]=l+q*g-r*h;f[n++]=m+q*h+r*g;for(q=p+2;q<p+e;++q)f[n++]=c[q]}c&&f.length!=n&&(f.length=n);this.s()}}; -k.scale=function(a,b,c){var d=b;void 0===d&&(d=a);var e=c;e||(e=kb(this.D()));if(c=this.ia()){b=c.length;for(var f=this.sa(),g=c?c:[],h=e[0],e=e[1],l=0,m=0;m<b;m+=f){var n=c[m]-h,p=c[m+1]-e;g[l++]=h+a*n;g[l++]=e+d*p;for(n=m+2;n<m+f;++n)g[l++]=c[n]}c&&g.length!=l&&(g.length=l);this.s()}};k.translate=function(a,b){var c=this.ia();c&&(nf(c,c.length,this.sa(),a,b,c),this.s())};function sf(a,b,c,d){for(var e=0,f=a[c-d],g=a[c-d+1];b<c;b+=d)var h=a[b],l=a[b+1],e=e+(g*h-f*l),f=h,g=l;return e/2}function tf(a,b,c,d){var e=0,f,g;f=0;for(g=c.length;f<g;++f){var h=c[f],e=e+sf(a,b,h,d);b=h}return e};function uf(a,b,c,d,e,f,g){var h=a[b],l=a[b+1],m=a[c]-h,n=a[c+1]-l;if(m||n)if(f=((e-h)*m+(f-l)*n)/(m*m+n*n),1<f)b=c;else if(0<f){for(e=0;e<d;++e)g[e]=Ea(a[b+e],a[c+e],f);g.length=d;return}for(e=0;e<d;++e)g[e]=a[b+e];g.length=d}function vf(a,b,c,d,e){var f=a[b],g=a[b+1];for(b+=d;b<c;b+=d){var h=a[b],l=a[b+1],f=Ba(f,g,h,l);f>e&&(e=f);f=h;g=l}return e}function wf(a,b,c,d,e){var f,g;f=0;for(g=c.length;f<g;++f){var h=c[f];e=vf(a,b,h,d,e);b=h}return e} -function xf(a,b,c,d,e,f,g,h,l,m,n){if(b==c)return m;var p;if(!e){p=Ba(g,h,a[b],a[b+1]);if(p<m){for(n=0;n<d;++n)l[n]=a[b+n];l.length=d;return p}return m}for(var q=n?n:[NaN,NaN],r=b+d;r<c;)if(uf(a,r-d,r,d,g,h,q),p=Ba(g,h,q[0],q[1]),p<m){m=p;for(n=0;n<d;++n)l[n]=q[n];l.length=d;r+=d}else r+=d*Math.max((Math.sqrt(p)-Math.sqrt(m))/e|0,1);if(f&&(uf(a,c-d,b,d,g,h,q),p=Ba(g,h,q[0],q[1]),p<m)){m=p;for(n=0;n<d;++n)l[n]=q[n];l.length=d}return m} -function yf(a,b,c,d,e,f,g,h,l,m,n){n=n?n:[NaN,NaN];var p,q;p=0;for(q=c.length;p<q;++p){var r=c[p];m=xf(a,b,r,d,e,f,g,h,l,m,n);b=r}return m};function zf(a,b){var c=0,d,e;d=0;for(e=b.length;d<e;++d)a[c++]=b[d];return c}function Af(a,b,c,d){var e,f;e=0;for(f=c.length;e<f;++e){var g=c[e],h;for(h=0;h<d;++h)a[b++]=g[h]}return b}function Bf(a,b,c,d,e){e=e?e:[];var f=0,g,h;g=0;for(h=c.length;g<h;++g)b=Af(a,b,c[g],d),e[f++]=b;e.length=f;return e};function Cf(a,b,c,d,e){e=void 0!==e?e:[];for(var f=0;b<c;b+=d)e[f++]=a.slice(b,b+d);e.length=f;return e}function Df(a,b,c,d,e){e=void 0!==e?e:[];var f=0,g,h;g=0;for(h=c.length;g<h;++g){var l=c[g];e[f++]=Cf(a,b,l,d,e[f]);b=l}e.length=f;return e};function Ef(a,b,c,d,e,f,g){var h=(c-b)/d;if(3>h){for(;b<c;b+=d)f[g++]=a[b],f[g++]=a[b+1];return g}var l=Array(h);l[0]=1;l[h-1]=1;c=[b,c-d];for(var m=0,n;0<c.length;){var p=c.pop(),q=c.pop(),r=0,v=a[q],x=a[q+1],y=a[p],A=a[p+1];for(n=q+d;n<p;n+=d){var B=Aa(a[n],a[n+1],v,x,y,A);B>r&&(m=n,r=B)}r>e&&(l[(m-b)/d]=1,q+d<m&&c.push(q,m),m+d<p&&c.push(m,p))}for(n=0;n<h;++n)l[n]&&(f[g++]=a[b+n*d],f[g++]=a[b+n*d+1]);return g} -function Ff(a,b,c,d,e,f,g,h){var l,m;l=0;for(m=c.length;l<m;++l){var n=c[l];a:{var p,q=a,r=n,v=d,x=e,y=f,A=g;if(b!=r){var B=x*Math.round(q[b]/x),aa=x*Math.round(q[b+1]/x);b+=v;y[A++]=B;y[A++]=aa;do if(p=x*Math.round(q[b]/x),g=x*Math.round(q[b+1]/x),b+=v,b==r){y[A++]=p;y[A++]=g;g=A;break a}while(p==B&&g==aa);for(;b<r;){var Ra,ra;Ra=x*Math.round(q[b]/x);ra=x*Math.round(q[b+1]/x);b+=v;if(Ra!=p||ra!=g){var Ka=p-B,C=g-aa,Na=Ra-B,wb=ra-aa;Ka*wb==C*Na&&(0>Ka&&Na<Ka||Ka==Na||0<Ka&&Na>Ka)&&(0>C&&wb<C||C== -wb||0<C&&wb>C)||(y[A++]=p,y[A++]=g,B=p,aa=g);p=Ra;g=ra}}y[A++]=p;y[A++]=g}g=A}h.push(g);b=n}return g};function Gf(a,b){of.call(this);this.c=this.j=-1;this.pa(a,b)}u(Gf,of);k=Gf.prototype;k.clone=function(){var a=new Gf(null);Hf(a,this.la,this.B.slice());return a};k.Hb=function(a,b,c,d){if(d<Pa(this.D(),a,b))return d;this.c!=this.g&&(this.j=Math.sqrt(vf(this.B,0,this.B.length,this.a,0)),this.c=this.g);return xf(this.B,0,this.B.length,this.a,this.j,!0,a,b,c,d)};k.jn=function(){return sf(this.B,0,this.B.length,this.a)};k.W=function(){return Cf(this.B,0,this.B.length,this.a)}; -k.od=function(a){var b=[];b.length=Ef(this.B,0,this.B.length,this.a,a,b,0);a=new Gf(null);Hf(a,"XY",b);return a};k.S=function(){return"LinearRing"};k.Ya=function(){};k.pa=function(a,b){a?(rf(this,b,a,1),this.B||(this.B=[]),this.B.length=Af(this.B,0,a,this.a),this.s()):Hf(this,"XY",null)};function Hf(a,b,c){qf(a,b,c);a.s()};function E(a,b){of.call(this);this.pa(a,b)}u(E,of);k=E.prototype;k.clone=function(){var a=new E(null);a.ca(this.la,this.B.slice());return a};k.Hb=function(a,b,c,d){var e=this.B;a=Ba(a,b,e[0],e[1]);if(a<d){d=this.a;for(b=0;b<d;++b)c[b]=e[b];c.length=d;return a}return d};k.W=function(){return this.B?this.B.slice():[]};k.se=function(a){return Xa(this.B,a)};k.S=function(){return"Point"};k.Ya=function(a){return Sa(a,this.B[0],this.B[1])}; -k.pa=function(a,b){a?(rf(this,b,a,0),this.B||(this.B=[]),this.B.length=zf(this.B,a),this.s()):this.ca("XY",null)};k.ca=function(a,b){qf(this,a,b);this.s()};function If(a,b,c,d,e){return!bb(e,function(e){return!Jf(a,b,c,d,e[0],e[1])})}function Jf(a,b,c,d,e,f){for(var g=0,h=a[c-d],l=a[c-d+1];b<c;b+=d){var m=a[b],n=a[b+1];l<=f?n>f&&0<(m-h)*(f-l)-(e-h)*(n-l)&&g++:n<=f&&0>(m-h)*(f-l)-(e-h)*(n-l)&&g--;h=m;l=n}return!!g}function Kf(a,b,c,d,e,f){if(!c.length||!Jf(a,b,c[0],d,e,f))return!1;var g;b=1;for(g=c.length;b<g;++b)if(Jf(a,c[b-1],c[b],d,e,f))return!1;return!0};function Lf(a,b,c,d,e,f,g){var h,l,m,n,p,q=e[f+1],r=[],v=c[0];m=a[v-d];p=a[v-d+1];for(h=b;h<v;h+=d){n=a[h];l=a[h+1];if(q<=p&&l<=q||p<=q&&q<=l)m=(q-p)/(l-p)*(n-m)+m,r.push(m);m=n;p=l}v=NaN;p=-Infinity;r.sort(ea);m=r[0];h=1;for(l=r.length;h<l;++h){n=r[h];var x=Math.abs(n-m);x>p&&(m=(m+n)/2,Kf(a,b,c,d,m,q)&&(v=m,p=x));m=n}isNaN(v)&&(v=e[f]);return g?(g.push(v,q),g):[v,q]};function Mf(a,b,c,d,e,f){for(var g=[a[b],a[b+1]],h=[],l;b+d<c;b+=d){h[0]=a[b+d];h[1]=a[b+d+1];if(l=e.call(f,g,h))return l;g[0]=h[0];g[1]=h[1]}return!1};function Nf(a,b,c,d,e){var f=Za(Ja(),a,b,c,d);return nb(e,f)?Ua(e,f)||f[0]>=e[0]&&f[2]<=e[2]||f[1]>=e[1]&&f[3]<=e[3]?!0:Mf(a,b,c,d,function(a,b){var c=!1,d=Va(e,a),f=Va(e,b);if(1===d||1===f)c=!0;else{var g=e[0],h=e[1],r=e[2],v=e[3],x=b[0],y=b[1],A=(y-a[1])/(x-a[0]);f&2&&!(d&2)&&(c=x-(y-v)/A,c=c>=g&&c<=r);c||!(f&4)||d&4||(c=y-(x-r)*A,c=c>=h&&c<=v);c||!(f&8)||d&8||(c=x-(y-h)/A,c=c>=g&&c<=r);c||!(f&16)||d&16||(c=y-(x-g)*A,c=c>=h&&c<=v)}return c}):!1} -function Of(a,b,c,d,e){var f=c[0];if(!(Nf(a,b,f,d,e)||Jf(a,b,f,d,e[0],e[1])||Jf(a,b,f,d,e[0],e[3])||Jf(a,b,f,d,e[2],e[1])||Jf(a,b,f,d,e[2],e[3])))return!1;if(1===c.length)return!0;b=1;for(f=c.length;b<f;++b)if(If(a,c[b-1],c[b],d,e))return!1;return!0};function Pf(a,b,c,d){for(var e=0,f=a[c-d],g=a[c-d+1];b<c;b+=d)var h=a[b],l=a[b+1],e=e+(h-f)*(l+g),f=h,g=l;return 0<e}function Qf(a,b,c,d){var e=0;d=void 0!==d?d:!1;var f,g;f=0;for(g=b.length;f<g;++f){var h=b[f],e=Pf(a,e,h,c);if(!f){if(d&&e||!d&&!e)return!1}else if(d&&!e||!d&&e)return!1;e=h}return!0} -function Rf(a,b,c,d,e){e=void 0!==e?e:!1;var f,g;f=0;for(g=c.length;f<g;++f){var h=c[f],l=Pf(a,b,h,d);if(f?e&&!l||!e&&l:e&&l||!e&&!l)for(var l=a,m=h,n=d;b<m-n;){var p;for(p=0;p<n;++p){var q=l[b+p];l[b+p]=l[m-n+p];l[m-n+p]=q}b+=n;m-=n}b=h}return b}function Sf(a,b,c,d){var e=0,f,g;f=0;for(g=b.length;f<g;++f)e=Rf(a,e,b[f],c,d);return e};function F(a,b){of.call(this);this.c=[];this.v=-1;this.A=null;this.I=this.C=this.G=-1;this.j=null;this.pa(a,b)}u(F,of);k=F.prototype;k.kk=function(a){this.B?ha(this.B,a.ia()):this.B=a.ia().slice();this.c.push(this.B.length);this.s()};k.clone=function(){var a=new F(null);a.ca(this.la,this.B.slice(),this.c.slice());return a}; -k.Hb=function(a,b,c,d){if(d<Pa(this.D(),a,b))return d;this.C!=this.g&&(this.G=Math.sqrt(wf(this.B,0,this.c,this.a,0)),this.C=this.g);return yf(this.B,0,this.c,this.a,this.G,!0,a,b,c,d)};k.Sc=function(a,b){return Kf(this.gc(),0,this.c,this.a,a,b)};k.mn=function(){return tf(this.gc(),0,this.c,this.a)};k.W=function(a){var b;void 0!==a?(b=this.gc().slice(),Rf(b,0,this.c,this.a,a)):b=this.B;return Df(b,0,this.c,this.a)};k.Sb=function(){return this.c}; -function Tf(a){if(a.v!=a.g){var b=kb(a.D());a.A=Lf(a.gc(),0,a.c,a.a,b,0);a.v=a.g}return a.A}k.Ok=function(){return new E(Tf(this))};k.Uk=function(){return this.c.length};k.vh=function(a){if(0>a||this.c.length<=a)return null;var b=new Gf(null);Hf(b,this.la,this.B.slice(a?this.c[a-1]:0,this.c[a]));return b};k.Oc=function(){var a=this.la,b=this.B,c=this.c,d=[],e=0,f,g;f=0;for(g=c.length;f<g;++f){var h=c[f],l=new Gf(null);Hf(l,a,b.slice(e,h));d.push(l);e=h}return d}; -k.gc=function(){if(this.I!=this.g){var a=this.B;Qf(a,this.c,this.a)?this.j=a:(this.j=a.slice(),this.j.length=Rf(this.j,0,this.c,this.a));this.I=this.g}return this.j};k.od=function(a){var b=[],c=[];b.length=Ff(this.B,0,this.c,this.a,Math.sqrt(a),b,0,c);a=new F(null);a.ca("XY",b,c);return a};k.S=function(){return"Polygon"};k.Ya=function(a){return Of(this.gc(),0,this.c,this.a,a)}; -k.pa=function(a,b){if(a){rf(this,b,a,2);this.B||(this.B=[]);var c=Bf(this.B,0,a,this.a,this.c);this.B.length=c.length?c[c.length-1]:0;this.s()}else this.ca("XY",null,this.c)};k.ca=function(a,b,c){qf(this,a,b);this.c=c;this.s()};function Uf(a,b,c,d){var e=d?d:32;d=[];var f;for(f=0;f<e;++f)ha(d,a.offset(b,c,2*Math.PI*f/e));d.push(d[0],d[1]);a=new F(null);a.ca("XY",d,[d.length]);return a} -function Vf(a){var b=a[0],c=a[1],d=a[2];a=a[3];b=[b,c,b,a,d,a,d,c,b,c];c=new F(null);c.ca("XY",b,[b.length]);return c}function Wf(a,b,c){var d=b?b:32,e=a.sa();b=a.la;for(var f=new F(null,b),d=e*(d+1),e=Array(d),g=0;g<d;g++)e[g]=0;f.ca(b,e,[e.length]);Xf(f,a.za(),a.Yd(),c);return f}function Xf(a,b,c,d){var e=a.ia(),f=a.la,g=a.sa(),h=a.Sb(),l=e.length/g-1;d=d?d:0;for(var m,n,p=0;p<=l;++p)n=p*g,m=d+2*Da(p,l)*Math.PI/l,e[n]=b[0]+c*Math.cos(m),e[n+1]=b[1]+c*Math.sin(m);a.ca(f,e,h)};function G(a){Qc.call(this);a=qb({},a);this.j=[0,0];this.c=[];this.vf=this.vf.bind(this);this.o=Zb(a.projection);Yf(this,a)}u(G,Qc); -function Yf(a,b){var c={};c.center=void 0!==b.center?b.center:null;var d,e,f,g=void 0!==b.minZoom?b.minZoom:0;d=void 0!==b.maxZoom?b.maxZoom:28;var h=void 0!==b.zoomFactor?b.zoomFactor:2;if(void 0!==b.resolutions)d=b.resolutions,e=d[0],f=d[d.length-1],d=Pe(d);else{e=Zb(b.projection);f=e.D();var l=(f?Math.max(ib(f),jb(f)):360*xb.degrees/e.uc())/256/Math.pow(2,0),m=l/Math.pow(2,28);e=b.maxResolution;void 0!==e?g=0:e=l/Math.pow(h,g);f=b.minResolution;void 0===f&&(f=void 0!==b.maxZoom?void 0!==b.maxResolution? -e/Math.pow(h,d):l/Math.pow(h,d):m);d=g+Math.floor(Math.log(e/f)/Math.log(h));f=e/Math.pow(h,d-g);d=Qe(h,e,d-g)}a.a=e;a.i=f;a.C=h;a.f=b.resolutions;a.l=g;(void 0!==b.enableRotation?b.enableRotation:1)?(g=b.constrainRotation,g=void 0===g||!0===g?Ue():!1===g?Se:"number"===typeof g?Te(g):Se):g=Re;a.v=new gd(void 0!==b.extent?yc(b.extent):zc,d,g);void 0!==b.resolution?c.resolution=b.resolution:void 0!==b.zoom&&(c.resolution=a.constrainResolution(a.a,b.zoom-a.l));c.rotation=void 0!==b.rotation?b.rotation: -0;a.H(c);a.A=b}function Zf(a,b){var c=qb({},a.A);void 0!==c.resolution?c.resolution=a.Ra():c.zoom=a.Ah();c.center=a.za();c.rotation=a.Sa();return qb({},c,b)}k=G.prototype; -k.animate=function(a){var b=Date.now(),c=this.za().slice(),d=this.Ra(),e=this.Sa(),f=arguments.length,g;1<f&&"function"===typeof arguments[f-1]&&(g=arguments[f-1],--f);for(var h=[],l=0;l<f;++l){var m=arguments[l],n={start:b,complete:!1,anchor:m.anchor,duration:void 0!==m.duration?m.duration:1E3,easing:m.easing||qd};m.center&&(n.Jg=c,n.Lg=m.center,c=n.Lg);void 0!==m.zoom?(n.sf=d,n.Bd=this.constrainResolution(this.a,m.zoom-this.l,0),d=n.Bd):m.resolution&&(n.sf=d,n.Bd=m.resolution,d=n.Bd);void 0!==m.rotation&& -(n.Kg=e,n.tf=m.rotation,e=n.tf);n.jd=g;b+=n.duration;h.push(n)}this.c.push(h);$f(this,0,1);this.vf()};k.Kc=function(){return 0<ag(this)[0]};k.kd=function(){$f(this,0,-ag(this)[0]);for(var a=0,b=this.c.length;a<b;++a){var c=this.c[a];c[0].jd&&c[0].jd(!1)}this.c.length=0}; -k.vf=function(){void 0!==this.u&&(cancelAnimationFrame(this.u),this.u=void 0);if(this.Kc()){for(var a=Date.now(),b=!1,c=this.c.length-1;0<=c;--c){for(var d=this.c[c],e=!0,f=0,g=d.length;f<g;++f){var h=d[f];if(!h.complete){b=a-h.start;b=0<h.duration?b/h.duration:1;1<=b?(h.complete=!0,b=1):e=!1;b=h.easing(b);if(h.Jg){var l=h.Jg[0],m=h.Jg[1];this.set("center",[l+b*(h.Lg[0]-l),m+b*(h.Lg[1]-m)])}h.sf&&h.Bd&&(l=1===b?h.Bd:h.sf+b*(h.Bd-h.sf),h.anchor&&this.set("center",bg(this,l,h.anchor)),this.set("resolution", -l));void 0!==h.Kg&&void 0!==h.tf&&(b=1===b?h.tf:h.Kg+b*(h.tf-h.Kg),h.anchor&&this.set("center",cg(this,b,h.anchor)),this.set("rotation",b));b=!0;if(!h.complete)break}}e&&(this.c[c]=null,$f(this,0,-1),(d=d[0].jd)&&d(!0))}this.c=this.c.filter(Boolean);b&&void 0===this.u&&(this.u=requestAnimationFrame(this.vf))}};function cg(a,b,c){var d,e=a.za();void 0!==e&&(d=[e[0]-c[0],e[1]-c[1]],cf(d,b-a.Sa()),Xe(d,c));return d} -function bg(a,b,c){var d,e=a.za();a=a.Ra();void 0!==e&&void 0!==a&&(d=[c[0]-b*(c[0]-e[0])/a,c[1]-b*(c[1]-e[1])/a]);return d}function dg(a){var b=[100,100];a='.ol-viewport[data-view="'+w(a)+'"]';if(a=document.querySelector(a))a=getComputedStyle(a),b[0]=parseInt(a.width,10),b[1]=parseInt(a.height,10);return b}k.Gc=function(a){return this.v.center(a)};k.constrainResolution=function(a,b,c){return this.v.resolution(a,b||0,c||0)};k.constrainRotation=function(a,b){return this.v.rotation(a,b||0)};k.za=function(){return this.get("center")}; -function ag(a,b){return void 0!==b?(b[0]=a.j[0],b[1]=a.j[1],b):a.j.slice()}k.hd=function(a){a=a||dg(this);var b=this.za();sa(b,1);var c=this.Ra();sa(void 0!==c,2);var d=this.Sa();sa(void 0!==d,3);return lb(b,c,d,a)};k.Hm=function(){return this.a};k.Jm=function(){return this.i};k.Im=function(){return this.Be(this.i)};k.Up=function(a){Yf(this,Zf(this,{maxZoom:a}))};k.Km=function(){return this.Be(this.a)};k.Vp=function(a){Yf(this,Zf(this,{minZoom:a}))};k.Lm=function(){return this.o};k.Ra=function(){return this.get("resolution")}; -k.Mm=function(){return this.f};function eg(a,b){return Math.max(ib(a)/b[0],jb(a)/b[1])}function fg(a){var b=a.a,c=Math.log(b/a.i)/Math.log(2);return function(a){return b/Math.pow(2,a*c)}}k.Sa=function(){return this.get("rotation")};function gg(a){var b=a.a,c=Math.log(b/a.i)/Math.log(2);return function(a){return Math.log(b/a)/Math.log(2)/c}}k.V=function(){var a=this.za(),b=this.o,c=this.Ra(),d=this.Sa();return{center:a.slice(),projection:void 0!==b?b:null,resolution:c,rotation:d}}; -k.Ah=function(){var a,b=this.Ra();void 0!==b&&(a=this.Be(b));return a};k.Be=function(a){var b;if(a>=this.i&&a<=this.a){b=this.l||0;var c,d;if(this.f){d=ga(this.f,a,1);b+=d;if(d==this.f.length-1)return b;c=this.f[d];d=c/this.f[d+1]}else c=this.a,d=this.C;b+=Math.log(c/a)/Math.log(d)}return b}; -k.Mf=function(a,b){var c=b||{},d=c.size;d||(d=dg(this));var e;a instanceof of?"Circle"===a.S()?(a=a.D(),e=Vf(a),e.rotate(this.Sa(),kb(a))):e=a:(sa(Array.isArray(a),24),sa(!hb(a),25),e=Vf(a));var f=c.padding?c.padding:[0,0,0,0],g=void 0!==c.constrainResolution?c.constrainResolution:!0,h=void 0!==c.nearest?c.nearest:!1,l;void 0!==c.minResolution?l=c.minResolution:void 0!==c.maxZoom?l=this.constrainResolution(this.a,c.maxZoom-this.l,0):l=0;var m=e.ia(),n=this.Sa(),p=Math.cos(-n),n=Math.sin(-n),q=Infinity, -r=Infinity,v=-Infinity,x=-Infinity;e=e.sa();for(var y=0,A=m.length;y<A;y+=e)var B=m[y]*p-m[y+1]*n,aa=m[y]*n+m[y+1]*p,q=Math.min(q,B),r=Math.min(r,aa),v=Math.max(v,B),x=Math.max(x,aa);d=eg([q,r,v,x],[d[0]-f[1]-f[3],d[1]-f[0]-f[2]]);d=isNaN(d)?l:Math.max(d,l);g&&(g=this.constrainResolution(d,0,0),!h&&g<d&&(g=this.constrainResolution(g,-1,0)),d=g);n=-n;h=(q+v)/2+(f[1]-f[3])/2*d;f=(r+x)/2+(f[0]-f[2])/2*d;p=[h*p-f*n,f*p+h*n];void 0!==c.duration?this.animate({resolution:d,center:p,duration:c.duration,easing:c.easing}): -(this.$c(d),this.lb(p))};k.qk=function(a,b,c){var d=this.Sa(),e=Math.cos(-d),d=Math.sin(-d),f=a[0]*e-a[1]*d;a=a[1]*e+a[0]*d;var g=this.Ra(),f=f+(b[0]/2-c[0])*g;a+=(c[1]-b[1]/2)*g;d=-d;this.lb([f*e-a*d,a*e+f*d])};function hg(a){return!!a.za()&&void 0!==a.Ra()}k.rotate=function(a,b){if(void 0!==b){var c=cg(this,a,b);this.lb(c)}this.Ne(a)};k.lb=function(a){this.set("center",a);this.Kc()&&this.kd()};function $f(a,b,c){a.j[b]+=c;a.s()}k.$c=function(a){this.set("resolution",a);this.Kc()&&this.kd()}; -k.Ne=function(a){this.set("rotation",a);this.Kc()&&this.kd()};k.aq=function(a){a=this.constrainResolution(this.a,a-this.l,0);this.$c(a)};function ig(a,b,c){this.i=a;this.c=b;this.f=c;this.b=[];this.a=this.g=0}function jg(a){a.b.length=0;a.g=0;a.a=0};function kg(a){Qc.call(this);this.v=null;this.Ia(!0);this.handleEvent=a.handleEvent}u(kg,Qc);kg.prototype.c=function(){return this.get("active")};kg.prototype.i=function(){return this.v};kg.prototype.Ia=function(a){this.set("active",a)};kg.prototype.setMap=function(a){this.v=a};function lg(a,b,c,d){if(void 0!==b){var e=a.Sa(),f=a.za();void 0!==e&&f&&0<d?a.animate({rotation:b,anchor:c,duration:d,easing:pd}):a.rotate(b,c)}} -function mg(a,b,c,d){var e=a.Ra();b=a.constrainResolution(e,b,0);if(c&&void 0!==b&&b!==e){var f=a.za();c=bg(a,b,c);c=a.Gc(c);c=[(b*f[0]-e*c[0])/(b-e),(b*f[1]-e*c[1])/(b-e)]}ng(a,b,c,d)}function ng(a,b,c,d){if(b){var e=a.Ra(),f=a.za();void 0!==e&&f&&b!==e&&d?a.animate({resolution:b,anchor:c,duration:d,easing:pd}):(c&&(c=bg(a,b,c),a.lb(c)),a.$c(b))}};function og(a){a=a?a:{};this.a=a.delta?a.delta:1;kg.call(this,{handleEvent:pg});this.f=void 0!==a.duration?a.duration:250}u(og,kg);function pg(a){var b=!1,c=a.originalEvent;if("dblclick"==a.type){var b=a.coordinate,c=c.shiftKey?-this.a:this.a,d=a.map.$();mg(d,c,b,this.f);a.preventDefault();b=!0}return!b};function qg(a){a=a.originalEvent;return a.altKey&&!(a.metaKey||a.ctrlKey)&&a.shiftKey}function rg(a){a=a.originalEvent;return!a.button&&!(Rd&&Sd&&a.ctrlKey)}function sg(a){return"pointermove"==a.type}function tg(a){return"singleclick"==a.type}function vg(a){a=a.originalEvent;return!a.altKey&&!(a.metaKey||a.ctrlKey)&&!a.shiftKey}function wg(a){a=a.originalEvent;return!a.altKey&&!(a.metaKey||a.ctrlKey)&&a.shiftKey} -function xg(a){a=a.originalEvent.target.tagName;return"INPUT"!==a&&"SELECT"!==a&&"TEXTAREA"!==a}function yg(a){sa(a.b,56);return"mouse"==a.b.pointerType}function zg(a){a=a.b;return a.isPrimary&&0===a.button};function Ag(a){a=a?a:{};kg.call(this,{handleEvent:a.handleEvent?a.handleEvent:Bg});this.wf=a.handleDownEvent?a.handleDownEvent:kf;this.Ef=a.handleDragEvent?a.handleDragEvent:oa;this.Ff=a.handleMoveEvent?a.handleMoveEvent:oa;this.nk=a.handleUpEvent?a.handleUpEvent:kf;this.A=!1;this.ea={};this.l=[]}u(Ag,kg);function Cg(a){for(var b=a.length,c=0,d=0,e=0;e<b;e++)c+=a[e].clientX,d+=a[e].clientY;return[c/b,d/b]} -function Bg(a){if(!(a instanceof Kd))return!0;var b=!1,c=a.type;if("pointerdown"===c||"pointerdrag"===c||"pointerup"===c)c=a.b,"pointerup"==a.type?delete this.ea[c.pointerId]:"pointerdown"==a.type?this.ea[c.pointerId]=c:c.pointerId in this.ea&&(this.ea[c.pointerId]=c),this.l=sb(this.ea);this.A?"pointerdrag"==a.type?this.Ef(a):"pointerup"==a.type&&(this.A=this.nk(a)&&0<this.l.length):"pointerdown"==a.type?(this.A=a=this.wf(a),b=this.bd(a)):"pointermove"==a.type&&this.Ff(a);return!b} -Ag.prototype.bd=function(a){return a};function Dg(a){Ag.call(this,{handleDownEvent:Eg,handleDragEvent:Fg,handleUpEvent:Gg});a=a?a:{};this.a=a.kinetic;this.f=null;this.u=a.condition?a.condition:vg;this.j=!1}u(Dg,Ag);function Fg(a){var b=this.l,c=Cg(b);if(b.length==this.o){if(this.a&&this.a.b.push(c[0],c[1],Date.now()),this.f){var d=this.f[0]-c[0],e=c[1]-this.f[1];a=a.map.$();var f=a.V(),d=[d,e];df(d,f.resolution);cf(d,f.rotation);Xe(d,f.center);d=a.Gc(d);a.lb(d)}}else this.a&&jg(this.a);this.f=c;this.o=b.length} -function Gg(a){var b=a.map;a=b.$();if(this.l.length)return this.a&&jg(this.a),this.f=null,!0;var c;if(c=!this.j&&this.a)if(c=this.a,6>c.b.length)c=!1;else{var d=Date.now()-c.f,e=c.b.length-3;if(c.b[e+2]<d)c=!1;else{for(var f=e-3;0<f&&c.b[f+2]>d;)f-=3;var d=c.b[e+2]-c.b[f+2],g=c.b[e]-c.b[f],e=c.b[e+1]-c.b[f+1];c.g=Math.atan2(e,g);c.a=Math.sqrt(g*g+e*e)/d;c=c.a>c.c}}c&&(c=this.a,c=(c.c-c.a)/c.i,e=this.a.g,f=a.za(),f=b.Ka(f),b=b.Xa([f[0]-c*Math.cos(e),f[1]-c*Math.sin(e)]),a.animate({center:a.Gc(b),duration:500, -easing:pd}));$f(a,1,-1);return!1}function Eg(a){if(0<this.l.length&&this.u(a)){var b=a.map.$();this.f=null;this.A||$f(b,1,1);ag(b)[0]&&b.lb(a.frameState.viewState.center);this.a&&jg(this.a);this.j=1<this.l.length;return!0}return!1}Dg.prototype.bd=kf;function Hg(a){a=a?a:{};Ag.call(this,{handleDownEvent:Ig,handleDragEvent:Jg,handleUpEvent:Kg});this.f=a.condition?a.condition:qg;this.a=void 0;this.j=void 0!==a.duration?a.duration:250}u(Hg,Ag);function Jg(a){if(yg(a)){var b=a.map,c=b.Nb();a=a.pixel;c=Math.atan2(c[1]/2-a[1],a[0]-c[0]/2);if(void 0!==this.a){a=c-this.a;var b=b.$(),d=b.Sa();lg(b,d-a)}this.a=c}}function Kg(a){if(!yg(a))return!0;a=a.map.$();$f(a,1,-1);var b=a.Sa(),c=this.j,b=a.constrainRotation(b,0);lg(a,b,void 0,c);return!1} -function Ig(a){return yg(a)&&rg(a)&&this.f(a)?($f(a.map.$(),1,1),this.a=void 0,!0):!1}Hg.prototype.bd=kf;function Lg(a){this.Ic=null;this.a=document.createElement("div");this.a.style.position="absolute";this.a.className="ol-box "+a;this.g=this.c=this.b=null}u(Lg,Jc);Lg.prototype.ra=function(){this.setMap(null)};function Mg(a){var b=a.c,c=a.g;a=a.a.style;a.left=Math.min(b[0],c[0])+"px";a.top=Math.min(b[1],c[1])+"px";a.width=Math.abs(c[0]-b[0])+"px";a.height=Math.abs(c[1]-b[1])+"px"} -Lg.prototype.setMap=function(a){if(this.b){this.b.A.removeChild(this.a);var b=this.a.style;b.left=b.top=b.width=b.height="inherit"}(this.b=a)&&this.b.A.appendChild(this.a)};function Ng(a){var b=a.c,c=a.g,b=[b,[b[0],c[1]],c,[c[0],b[1]]].map(a.b.Xa,a.b);b[4]=b[0].slice();a.Ic?a.Ic.pa([b]):a.Ic=new F([b])}Lg.prototype.U=function(){return this.Ic};function Og(a){Ag.call(this,{handleDownEvent:Pg,handleDragEvent:Qg,handleUpEvent:Rg});a=a?a:{};this.a=new Lg(a.className||"ol-dragbox");this.u=void 0!==a.minArea?a.minArea:64;this.f=null;this.C=a.condition?a.condition:jf;this.o=a.boxEndCondition?a.boxEndCondition:Sg}u(Og,Ag);function Sg(a,b,c){a=c[0]-b[0];b=c[1]-b[1];return a*a+b*b>=this.u}function Qg(a){if(yg(a)){var b=this.a,c=a.pixel;b.c=this.f;b.g=c;Ng(b);Mg(b);this.b(new Tg(Ug,a.coordinate,a))}}Og.prototype.U=function(){return this.a.U()}; -Og.prototype.j=oa;function Rg(a){if(!yg(a))return!0;this.a.setMap(null);this.o(a,this.f,a.pixel)&&(this.j(a),this.b(new Tg(Vg,a.coordinate,a)));return!1}function Pg(a){if(yg(a)&&rg(a)&&this.C(a)){this.f=a.pixel;this.a.setMap(a.map);var b=this.a,c=this.f;b.c=this.f;b.g=c;Ng(b);Mg(b);this.b(new Tg(Wg,a.coordinate,a));return!0}return!1}var Wg="boxstart",Ug="boxdrag",Vg="boxend";function Tg(a,b,c){Lc.call(this,a);this.coordinate=b;this.mapBrowserEvent=c}u(Tg,Lc);function Xg(a){a=a?a:{};var b=a.condition?a.condition:wg;this.G=void 0!==a.duration?a.duration:200;this.I=void 0!==a.out?a.out:!1;Og.call(this,{condition:b,className:a.className||"ol-dragzoom"})}u(Xg,Og); -Xg.prototype.j=function(){var a=this.v,b=a.$(),c=a.Nb(),d=this.U().D();if(this.I){var e=b.hd(c),d=[a.Ka(cb(d)),a.Ka(eb(d))],a=Wa(Infinity,Infinity,-Infinity,-Infinity,void 0),f,g;f=0;for(g=d.length;f<g;++f)La(a,d[f]);ob(e,1/eg(a,c));d=e}c=b.constrainResolution(eg(d,c));e=kb(d);e=b.Gc(e);b.animate({resolution:c,center:e,duration:this.G,easing:pd})};function Yg(a){kg.call(this,{handleEvent:Zg});a=a||{};this.a=function(a){return vg(a)&&xg(a)};this.f=a.condition?a.condition:this.a;this.j=void 0!==a.duration?a.duration:100;this.l=void 0!==a.pixelDelta?a.pixelDelta:128}u(Yg,kg); -function Zg(a){var b=!1;if("keydown"==a.type){var c=a.originalEvent.keyCode;if(this.f(a)&&(40==c||37==c||39==c||38==c)){var b=a.map.$(),d=b.Ra()*this.l,e=0,f=0;40==c?f=-d:37==c?e=-d:39==c?e=d:f=d;d=[e,f];cf(d,b.Sa());c=this.j;if(e=b.za())d=b.Gc([e[0]+d[0],e[1]+d[1]]),c?b.animate({duration:c,easing:rd,center:d}):b.lb(d);a.preventDefault();b=!0}}return!b};function $g(a){kg.call(this,{handleEvent:ah});a=a?a:{};this.f=a.condition?a.condition:xg;this.a=a.delta?a.delta:1;this.j=void 0!==a.duration?a.duration:100}u($g,kg);function ah(a){var b=!1;if("keydown"==a.type||"keypress"==a.type){var c=a.originalEvent.charCode;!this.f(a)||43!=c&&45!=c||(b=43==c?this.a:-this.a,c=a.map.$(),mg(c,b,void 0,this.j),a.preventDefault(),b=!0)}return!b};function bh(a){kg.call(this,{handleEvent:ch});a=a||{};this.j=0;this.A=void 0!==a.duration?a.duration:250;this.ea=void 0!==a.timeout?a.timeout:80;this.C=void 0!==a.useAnchor?a.useAnchor:!0;this.Z=a.constrainResolution||!1;this.a=null;this.o=this.l=this.u=this.f=void 0}u(bh,kg); -function ch(a){var b=a.type;if("wheel"!==b&&"mousewheel"!==b)return!0;a.preventDefault();var b=a.map,c=a.originalEvent;this.C&&(this.a=a.coordinate);var d;"wheel"==a.type?(d=c.deltaY,Pd&&c.deltaMode===WheelEvent.DOM_DELTA_PIXEL&&(d/=Td),c.deltaMode===WheelEvent.DOM_DELTA_LINE&&(d*=40)):"mousewheel"==a.type&&(d=-c.wheelDeltaY,Qd&&(d/=3));if(0===d)return!1;a=Date.now();void 0===this.f&&(this.f=a);if(!this.l||400<a-this.f)this.l=4>Math.abs(d)?dh:eh;if(this.l===dh){b=b.$();this.o?clearTimeout(this.o): -$f(b,1,1);this.o=setTimeout(this.G.bind(this),400);var c=b.Ra()*Math.pow(2,d/300),e=b.i,f=b.a,g=0;c<e?(c=Math.max(c,e/1.5),g=1):c>f&&(c=Math.min(c,1.5*f),g=-1);if(this.a){var h=bg(b,c,this.a);b.lb(b.Gc(h))}b.$c(c);!g&&this.Z&&b.animate({resolution:b.constrainResolution(c,0<d?-1:1),easing:pd,anchor:this.a,duration:this.A});0<g?b.animate({resolution:e,easing:pd,anchor:this.a,duration:500}):0>g&&b.animate({resolution:f,easing:pd,anchor:this.a,duration:500});this.f=a;return!1}this.j+=d;d=Math.max(this.ea- -(a-this.f),0);clearTimeout(this.u);this.u=setTimeout(this.I.bind(this,b),d);return!1}bh.prototype.G=function(){this.o=void 0;$f(this.v.$(),1,-1)};bh.prototype.I=function(a){a=a.$();a.Kc()&&a.kd();mg(a,-xa(this.j,-1,1),this.a,this.A);this.l=void 0;this.j=0;this.a=null;this.u=this.f=void 0};bh.prototype.T=function(a){this.C=a;a||(this.a=null)};var dh="trackpad",eh="wheel";function fh(a){Ag.call(this,{handleDownEvent:gh,handleDragEvent:hh,handleUpEvent:ih});a=a||{};this.f=null;this.j=void 0;this.a=!1;this.o=0;this.C=void 0!==a.threshold?a.threshold:.3;this.u=void 0!==a.duration?a.duration:250}u(fh,Ag); -function hh(a){var b=0,c=this.l[0],d=this.l[1],c=Math.atan2(d.clientY-c.clientY,d.clientX-c.clientX);void 0!==this.j&&(b=c-this.j,this.o+=b,!this.a&&Math.abs(this.o)>this.C&&(this.a=!0));this.j=c;a=a.map;c=a.c.getBoundingClientRect();d=Cg(this.l);d[0]-=c.left;d[1]-=c.top;this.f=a.Xa(d);this.a&&(c=a.$(),d=c.Sa(),a.render(),lg(c,d+b,this.f))}function ih(a){if(2>this.l.length){a=a.map.$();$f(a,1,-1);if(this.a){var b=a.Sa(),c=this.f,d=this.u,b=a.constrainRotation(b,0);lg(a,b,c,d)}return!1}return!0} -function gh(a){return 2<=this.l.length?(a=a.map,this.f=null,this.j=void 0,this.a=!1,this.o=0,this.A||$f(a.$(),1,1),!0):!1}fh.prototype.bd=kf;function jh(a){Ag.call(this,{handleDownEvent:kh,handleDragEvent:lh,handleUpEvent:nh});a=a?a:{};this.o=a.constrainResolution||!1;this.f=null;this.u=void 0!==a.duration?a.duration:400;this.a=void 0;this.j=1}u(jh,Ag); -function lh(a){var b=1,c=this.l[0],d=this.l[1],e=c.clientX-d.clientX,c=c.clientY-d.clientY,e=Math.sqrt(e*e+c*c);void 0!==this.a&&(b=this.a/e);this.a=e;a=a.map;var e=a.$(),d=e.Ra(),f=e.a,g=e.i,c=d*b;c>f?(b=f/d,c=f):c<g&&(b=g/d,c=g);1!=b&&(this.j=b);b=a.c.getBoundingClientRect();d=Cg(this.l);d[0]-=b.left;d[1]-=b.top;this.f=a.Xa(d);a.render();ng(e,c,this.f)} -function nh(a){if(2>this.l.length){a=a.map.$();$f(a,1,-1);var b=a.Ra();if(this.o||b<a.i||b>a.a){var c=this.f,d=this.u,b=a.constrainResolution(b,0,this.j-1);ng(a,b,c,d)}return!1}return!0}function kh(a){return 2<=this.l.length?(a=a.map,this.f=null,this.a=void 0,this.j=1,this.A||$f(a.$(),1,1),!0):!1}jh.prototype.bd=kf;function oh(a){a=a?a:{};var b=new D,c=new ig(-.005,.05,100);(void 0!==a.altShiftDragRotate?a.altShiftDragRotate:1)&&b.push(new Hg);(void 0!==a.doubleClickZoom?a.doubleClickZoom:1)&&b.push(new og({delta:a.zoomDelta,duration:a.zoomDuration}));(void 0!==a.dragPan?a.dragPan:1)&&b.push(new Dg({kinetic:c}));(void 0!==a.pinchRotate?a.pinchRotate:1)&&b.push(new fh);(void 0!==a.pinchZoom?a.pinchZoom:1)&&b.push(new jh({constrainResolution:a.constrainResolution,duration:a.zoomDuration}));if(void 0!==a.keyboard? -a.keyboard:1)b.push(new Yg),b.push(new $g({delta:a.zoomDelta,duration:a.zoomDuration}));(void 0!==a.mouseWheelZoom?a.mouseWheelZoom:1)&&b.push(new bh({constrainResolution:a.constrainResolution,duration:a.zoomDuration}));(void 0!==a.shiftDragZoom?a.shiftDragZoom:1)&&b.push(new Xg({duration:a.zoomDuration}));return b};function ph(a){Qc.call(this);var b=qb({},a);b.opacity=void 0!==a.opacity?a.opacity:1;b.visible=void 0!==a.visible?a.visible:!0;b.zIndex=void 0!==a.zIndex?a.zIndex:0;b.maxResolution=void 0!==a.maxResolution?a.maxResolution:Infinity;b.minResolution=void 0!==a.minResolution?a.minResolution:0;this.H(b);this.a={layer:this,Ie:!0}}u(ph,Qc); -function qh(a){a.a.opacity=xa(a.jc(),0,1);a.a.uj=a.Vf();a.a.visible=a.Lb();a.a.extent=a.D();a.a.zIndex=a.Aa();a.a.maxResolution=a.hc();a.a.minResolution=Math.max(a.ic(),0);return a.a}k=ph.prototype;k.D=function(){return this.get("extent")};k.hc=function(){return this.get("maxResolution")};k.ic=function(){return this.get("minResolution")};k.jc=function(){return this.get("opacity")};k.Lb=function(){return this.get("visible")};k.Aa=function(){return this.get("zIndex")}; -k.xc=function(a){this.set("extent",a)};k.Cc=function(a){this.set("maxResolution",a)};k.Dc=function(a){this.set("minResolution",a)};k.yc=function(a){this.set("opacity",a)};k.zc=function(a){this.set("visible",a)};k.Xb=function(a){this.set("zIndex",a)};function rh(a){var b=a||{};a=qb({},b);delete a.layers;b=b.layers;ph.call(this,a);this.i=[];this.c={};z(this,Sc(sh),this.Cl,this);b?Array.isArray(b)?b=new D(b.slice(),{unique:!0}):sa(b instanceof D,43):b=new D(void 0,{unique:!0});this.pi(b)}u(rh,ph);k=rh.prototype;k.Gd=function(){};k.Ee=function(){this.Lb()&&this.s()}; -k.Cl=function(){this.i.forEach(Bc);this.i.length=0;var a=this.sd();this.i.push(z(a,"add",this.Bl,this),z(a,"remove",this.Dl,this));for(var b in this.c)this.c[b].forEach(Bc);rb(this.c);var a=a.a,c,d;b=0;for(c=a.length;b<c;b++)d=a[b],this.c[w(d).toString()]=[z(d,"propertychange",this.Ee,this),z(d,"change",this.Ee,this)];this.s()};k.Bl=function(a){a=a.element;var b=w(a).toString();this.c[b]=[z(a,"propertychange",this.Ee,this),z(a,"change",this.Ee,this)];this.s()}; -k.Dl=function(a){a=w(a.element).toString();this.c[a].forEach(Bc);delete this.c[a];this.s()};k.sd=function(){return this.get(sh)};k.pi=function(a){this.set(sh,a)}; -k.Tf=function(a){var b=void 0!==a?a:[],c=b.length;this.sd().forEach(function(a){a.Tf(b)});a=qh(this);var d,e;for(d=b.length;c<d;c++)e=b[c],e.opacity*=a.opacity,e.visible=e.visible&&a.visible,e.maxResolution=Math.min(e.maxResolution,a.maxResolution),e.minResolution=Math.max(e.minResolution,a.minResolution),void 0!==a.extent&&(e.extent=void 0!==e.extent?mb(e.extent,a.extent):a.extent);return b};k.Vf=function(){return"ready"};var sh="layers";function th(a){var b=qb({},a);delete b.source;ph.call(this,b);this.v=this.o=this.l=null;a.map&&this.setMap(a.map);z(this,Sc("source"),this.Pl,this);this.ad(a.source?a.source:null)}u(th,ph);function uh(a,b){return a.visible&&b>=a.minResolution&&b<a.maxResolution}k=th.prototype;k.Tf=function(a){a=a?a:[];a.push(qh(this));return a};k.ka=function(){return this.get("source")||null};k.Vf=function(){var a=this.ka();return a?a.V():"undefined"};k.Ln=function(){this.s()}; -k.Pl=function(){this.v&&(Bc(this.v),this.v=null);var a=this.ka();a&&(this.v=z(a,"change",this.Ln,this));this.s()};k.setMap=function(a){this.l&&(Bc(this.l),this.l=null);a||this.s();this.o&&(Bc(this.o),this.o=null);a&&(this.l=z(a,"precompose",function(a){var b=qh(this);b.Ie=!1;b.zIndex=Infinity;a.frameState.layerStatesArray.push(b);a.frameState.layerStates[w(this)]=b},this),this.o=z(this,"change",a.render,a),this.s())};k.ad=function(a){this.set("source",a)};function vh(){this.b={};this.a=0}vh.prototype.clear=function(){this.b={};this.a=0};vh.prototype.get=function(a,b,c){a=b+":"+a+":"+(c?dd(c):"null");return a in this.b?this.b[a]:null};vh.prototype.set=function(a,b,c,d){this.b[b+":"+a+":"+(c?dd(c):"null")]=d;++this.a};var wh=new vh;var xh=Array(6);function yh(){return[1,0,0,1,0,0]}function zh(a){return Ah(a,1,0,0,1,0,0)}function Bh(a,b){var c=a[0],d=a[1],e=a[2],f=a[3],g=a[4],h=a[5],l=b[0],m=b[1],n=b[2],p=b[3],q=b[4],r=b[5];a[0]=c*l+e*m;a[1]=d*l+f*m;a[2]=c*n+e*p;a[3]=d*n+f*p;a[4]=c*q+e*r+g;a[5]=d*q+f*r+h;return a}function Ah(a,b,c,d,e,f,g){a[0]=b;a[1]=c;a[2]=d;a[3]=e;a[4]=f;a[5]=g;return a}function Ch(a,b){a[0]=b[0];a[1]=b[1];a[2]=b[2];a[3]=b[3];a[4]=b[4];a[5]=b[5];return a} -function Dh(a,b){var c=b[0],d=b[1];b[0]=a[0]*c+a[2]*d+a[4];b[1]=a[1]*c+a[3]*d+a[5];return b}function Eh(a,b){var c=Math.cos(b),d=Math.sin(b);Bh(a,Ah(xh,c,d,-d,c,0,0))}function Fh(a,b,c){return Bh(a,Ah(xh,b,0,0,c,0,0))}function Gh(a,b,c){Bh(a,Ah(xh,1,0,0,1,b,c))}function Hh(a,b,c,d,e,f,g,h){var l=Math.sin(f);f=Math.cos(f);a[0]=d*f;a[1]=e*l;a[2]=-d*l;a[3]=e*f;a[4]=g*d*f-h*d*l+b;a[5]=g*e*l+h*e*f+c;return a} -function Ih(a){var b=a[0]*a[3]-a[1]*a[2];sa(!!b,32);var c=a[0],d=a[1],e=a[2],f=a[3],g=a[4],h=a[5];a[0]=f/b;a[1]=-d/b;a[2]=-e/b;a[3]=c/b;a[4]=(e*h-f*g)/b;a[5]=-(c*h-d*g)/b;return a};function Jh(a,b){this.l=b;this.c={};this.u={}}u(Jh,Jc);function Kh(a){var b=a.viewState,c=a.coordinateToPixelTransform,d=a.pixelToCoordinateTransform;Hh(c,a.size[0]/2,a.size[1]/2,1/b.resolution,-1/b.resolution,-b.rotation,-b.center[0],-b.center[1]);Ih(Ch(d,c))}k=Jh.prototype;k.ra=function(){for(var a in this.c)Kc(this.c[a])};function Lh(){if(32<wh.a){var a=0,b,c;for(b in wh.b)c=wh.b[b],a++&3||Oc(c)||(delete wh.b[b],--wh.a)}} -k.Ba=function(a,b,c,d,e,f,g){function h(a,c){var f=w(a).toString(),g=b.layerStates[w(c)].Ie;if(!(f in b.skippedFeatureUids)||g)return d.call(e,a,g?c:null)}var l,m=b.viewState,n=m.resolution,p=m.projection,m=a;if(p.a){var p=p.D(),q=ib(p),r=a[0];if(r<p[0]||r>p[2])m=[r+q*Math.ceil((p[0]-r)/q),a[1]]}p=b.layerStatesArray;for(q=p.length-1;0<=q;--q){var v=p[q],r=v.layer;if(uh(v,n)&&f.call(g,r)&&(v=Mh(this,r),r.ka()&&(l=v.Ba(r.ka().G?m:a,b,c,h,e)),l))return l}}; -k.xi=function(a,b,c,d,e){return void 0!==this.Ba(a,b,c,jf,this,d,e)};function Mh(a,b){var c=w(b).toString();if(c in a.c)return a.c[c];var d=b.Gd(a);a.c[c]=d;a.u[c]=z(d,"change",a.Al,a);return d}k.Al=function(){this.l.render()};k.Dg=oa;k.Hp=function(a,b){for(var c in this.c)if(!(b&&c in b.layerStates)){var d=c,e=this.c[d];delete this.c[d];Bc(this.u[d]);delete this.u[d];Kc(e)}};function Nh(a,b){for(var c in a.c)if(!(c in b.layerStates)){b.postRenderFunctions.push(a.Hp.bind(a));break}} -function la(a,b){return a.zIndex-b.zIndex};function Oh(a,b,c,d,e){Lc.call(this,a);this.vectorContext=b;this.frameState=c;this.context=d;this.glContext=e}u(Oh,Lc);var Ph=[0,0,0,1],Qh=[],Rh=[0,0,0,1];function Sh(a,b,c,d){b&&(a.translate(c,d),a.rotate(b),a.translate(-c,-d))};function Th(){}k=Th.prototype;k.oc=function(){};k.td=function(){};k.ac=function(){};k.te=function(){};k.ue=function(){};k.Rb=function(){};k.pc=function(){};k.qc=function(){};k.rc=function(){};k.sc=function(){};k.tc=function(){};k.Ac=function(){};k.Na=function(){};k.Wb=function(){};k.Ub=function(){};function Uh(a,b,c,d,e){this.g=a;this.v=b;this.c=c;this.O=d;this.Gb=e;this.N=this.b=this.a=this.$a=this.Z=this.I=null;this.ea=this.T=this.o=this.G=this.C=this.A=0;this.fa=!1;this.i=this.mb=0;this.na=!1;this.qa=0;this.Fa="";this.Ja=this.$b=0;this.Ha=!1;this.j=this.Va=0;this.ta=this.l=this.f=null;this.u=[];this.yb=yh()}u(Uh,Th); -function Vh(a,b,c){if(a.N){b=mf(b,0,c,2,a.O,a.u);c=a.g;var d=a.yb,e=c.globalAlpha;1!=a.o&&(c.globalAlpha=e*a.o);var f=a.mb;a.fa&&(f+=a.Gb);var g,h;g=0;for(h=b.length;g<h;g+=2){var l=b[g]-a.A,m=b[g+1]-a.C;a.na&&(l=Math.round(l),m=Math.round(m));if(f||1!=a.i){var n=l+a.A,p=m+a.C;Hh(d,n,p,a.i,a.i,f,-n,-p);c.setTransform.apply(c,d)}c.drawImage(a.N,a.T,a.ea,a.qa,a.G,l,m,a.qa,a.G)}(f||1!=a.i)&&c.setTransform(1,0,0,1,0,0);1!=a.o&&(c.globalAlpha=e)}} -function Wh(a,b,c,d){var e=0;if(a.ta&&""!==a.Fa){a.f&&Xh(a,a.f);a.l&&Yh(a,a.l);var f=a.ta,g=a.g,h=a.$a;h?(h.font!=f.font&&(h.font=g.font=f.font),h.textAlign!=f.textAlign&&(h.textAlign=g.textAlign=f.textAlign),h.textBaseline!=f.textBaseline&&(h.textBaseline=g.textBaseline=f.textBaseline)):(g.font=f.font,g.textAlign=f.textAlign,g.textBaseline=f.textBaseline,a.$a={font:f.font,textAlign:f.textAlign,textBaseline:f.textBaseline});b=mf(b,e,c,d,a.O,a.u);f=a.g;g=a.Va;for(a.Ha&&(g+=a.Gb);e<c;e+=d){var h=b[e]+ -a.$b,l=b[e+1]+a.Ja;if(g||1!=a.j){var m=Hh(a.yb,h,l,a.j,a.j,g,-h,-l);f.setTransform.apply(f,m)}a.l&&f.strokeText(a.Fa,h,l);a.f&&f.fillText(a.Fa,h,l)}(g||1!=a.j)&&f.setTransform(1,0,0,1,0,0)}}function Zh(a,b,c,d,e,f){var g=a.g;a=mf(b,c,d,e,a.O,a.u);g.moveTo(a[0],a[1]);b=a.length;f&&(b-=2);for(c=2;c<b;c+=2)g.lineTo(a[c],a[c+1]);f&&g.closePath();return d}function $h(a,b,c,d,e){var f,g;f=0;for(g=d.length;f<g;++f)c=Zh(a,b,c,d[f],e,!0);return c}k=Uh.prototype; -k.ac=function(a){if(nb(this.c,a.D())){if(this.a||this.b){this.a&&Xh(this,this.a);this.b&&Yh(this,this.b);var b;b=this.O;var c=this.u,d=a.ia();b=d?mf(d,0,d.length,a.sa(),b,c):null;c=b[2]-b[0];d=b[3]-b[1];c=Math.sqrt(c*c+d*d);d=this.g;d.beginPath();d.arc(b[0],b[1],c,0,2*Math.PI);this.a&&d.fill();this.b&&d.stroke()}""!==this.Fa&&Wh(this,a.za(),2,2)}};k.td=function(a){this.Na(a.Ca(),a.Da());this.Wb(a.Y());this.Ub(a.Oa())}; -k.oc=function(a){switch(a.S()){case "Point":this.sc(a);break;case "LineString":this.Rb(a);break;case "Polygon":this.tc(a);break;case "MultiPoint":this.qc(a);break;case "MultiLineString":this.pc(a);break;case "MultiPolygon":this.rc(a);break;case "GeometryCollection":this.ue(a);break;case "Circle":this.ac(a)}};k.te=function(a,b){var c=(0,b.Qa)(a);c&&nb(this.c,c.D())&&(this.td(b),this.oc(c))};k.ue=function(a){a=a.a;var b,c;b=0;for(c=a.length;b<c;++b)this.oc(a[b])}; -k.sc=function(a){var b=a.ia();a=a.sa();this.N&&Vh(this,b,b.length);""!==this.Fa&&Wh(this,b,b.length,a)};k.qc=function(a){var b=a.ia();a=a.sa();this.N&&Vh(this,b,b.length);""!==this.Fa&&Wh(this,b,b.length,a)};k.Rb=function(a){if(nb(this.c,a.D())){if(this.b){Yh(this,this.b);var b=this.g,c=a.ia();b.beginPath();Zh(this,c,0,c.length,a.sa(),!1);b.stroke()}""!==this.Fa&&(a=ai(a),Wh(this,a,2,2))}}; -k.pc=function(a){var b=a.D();if(nb(this.c,b)){if(this.b){Yh(this,this.b);var b=this.g,c=a.ia(),d=0,e=a.Sb(),f=a.sa();b.beginPath();var g,h;g=0;for(h=e.length;g<h;++g)d=Zh(this,c,d,e[g],f,!1);b.stroke()}""!==this.Fa&&(a=bi(a),Wh(this,a,a.length,2))}};k.tc=function(a){if(nb(this.c,a.D())){if(this.b||this.a){this.a&&Xh(this,this.a);this.b&&Yh(this,this.b);var b=this.g;b.beginPath();$h(this,a.gc(),0,a.Sb(),a.sa());this.a&&b.fill();this.b&&b.stroke()}""!==this.Fa&&(a=Tf(a),Wh(this,a,2,2))}}; -k.rc=function(a){if(nb(this.c,a.D())){if(this.b||this.a){this.a&&Xh(this,this.a);this.b&&Yh(this,this.b);var b=this.g,c=ci(a),d=0,e=a.c,f=a.sa(),g,h;b.beginPath();g=0;for(h=e.length;g<h;++g)d=$h(this,c,d,e[g],f);this.a&&b.fill();this.b&&b.stroke()}""!==this.Fa&&(a=di(a),Wh(this,a,a.length,2))}};function Xh(a,b){var c=a.g,d=a.I;d?d.fillStyle!=b.fillStyle&&(d.fillStyle=c.fillStyle=b.fillStyle):(c.fillStyle=b.fillStyle,a.I={fillStyle:b.fillStyle})} -function Yh(a,b){var c=a.g,d=a.Z;d?(d.lineCap!=b.lineCap&&(d.lineCap=c.lineCap=b.lineCap),Ud&&!ja(d.lineDash,b.lineDash)&&c.setLineDash(d.lineDash=b.lineDash),d.lineJoin!=b.lineJoin&&(d.lineJoin=c.lineJoin=b.lineJoin),d.lineWidth!=b.lineWidth&&(d.lineWidth=c.lineWidth=b.lineWidth),d.miterLimit!=b.miterLimit&&(d.miterLimit=c.miterLimit=b.miterLimit),d.strokeStyle!=b.strokeStyle&&(d.strokeStyle=c.strokeStyle=b.strokeStyle)):(c.lineCap=b.lineCap,Ud&&c.setLineDash(b.lineDash),c.lineJoin=b.lineJoin,c.lineWidth= -b.lineWidth,c.miterLimit=b.miterLimit,c.strokeStyle=b.strokeStyle,a.Z={lineCap:b.lineCap,lineDash:b.lineDash,lineJoin:b.lineJoin,lineWidth:b.lineWidth,miterLimit:b.miterLimit,strokeStyle:b.strokeStyle})} -k.Na=function(a,b){if(a){var c=a.b;this.a={fillStyle:fd(c?c:Ph)}}else this.a=null;if(b){var c=b.a,d=b.i,e=b.g,f=b.f,g=b.j,h=b.c,l=b.l;this.b={lineCap:void 0!==d?d:"round",lineDash:e?e:Qh,lineDashOffset:f?f:0,lineJoin:void 0!==g?g:"round",lineWidth:this.v*(void 0!==h?h:1),miterLimit:void 0!==l?l:10,strokeStyle:fd(c?c:Rh)}}else this.b=null}; -k.Wb=function(a){if(a){var b=a.Jc(),c=a.Y(1),d=a.Tc(),e=a.kc();this.A=b[0];this.C=b[1];this.G=e[1];this.N=c;this.o=a.f;this.T=d[0];this.ea=d[1];this.fa=a.o;this.mb=a.j;this.i=a.c;this.na=a.u;this.qa=e[0]}else this.N=null}; -k.Ub=function(a){if(a){var b=a.Ca();b?(b=b.b,this.f={fillStyle:fd(b?b:Ph)}):this.f=null;var c=a.Da();if(c){var b=c.a,d=c.i,e=c.g,f=c.f,g=c.j,h=c.c,c=c.l;this.l={lineCap:void 0!==d?d:"round",lineDash:e?e:Qh,lineDashOffset:f?f:0,lineJoin:void 0!==g?g:"round",lineWidth:void 0!==h?h:1,miterLimit:void 0!==c?c:10,strokeStyle:fd(b?b:Rh)}}else this.l=null;var b=a.a,d=a.g,e=a.c,f=a.l,g=a.i,h=a.b,c=a.Oa(),l=a.f;a=a.j;this.ta={font:void 0!==b?b:"10px sans-serif",textAlign:void 0!==l?l:"center",textBaseline:void 0!== -a?a:"middle"};this.Fa=void 0!==c?c:"";this.$b=void 0!==d?this.v*d:0;this.Ja=void 0!==e?this.v*e:0;this.Ha=void 0!==f?f:!1;this.Va=void 0!==g?g:0;this.j=this.v*(void 0!==h?h:1)}else this.Fa=""};function ei(a,b){Jh.call(this,0,b);this.g=hd();this.b=this.g.canvas;this.b.style.width="100%";this.b.style.height="100%";this.b.style.display="block";this.b.className="ol-unselectable";a.insertBefore(this.b,a.childNodes[0]||null);this.a=!0;this.i=yh()}u(ei,Jh); -function fi(a,b,c){var d=a.l,e=a.g;if(Oc(d,b)){var f=c.extent,g=c.pixelRatio,h=c.viewState.rotation,l=c.viewState,m=c.pixelRatio/l.resolution;a=Hh(a.i,a.b.width/2,a.b.height/2,m,-m,-l.rotation,-l.center[0],-l.center[1]);d.b(new Oh(b,new Uh(e,g,f,a,h),c,e,null))}}ei.prototype.S=function(){return"canvas"}; -ei.prototype.Dg=function(a){if(a){var b=this.g,c=a.pixelRatio,d=Math.round(a.size[0]*c),e=Math.round(a.size[1]*c);this.b.width!=d||this.b.height!=e?(this.b.width=d,this.b.height=e):b.clearRect(0,0,d,e);c=a.viewState.rotation;Kh(a);fi(this,"precompose",a);var f=a.layerStatesArray;ka(f);c&&(b.save(),Sh(b,c,d/2,e/2));var d=a.viewState.resolution,g,h,l,e=0;for(g=f.length;e<g;++e)l=f[e],h=l.layer,h=Mh(this,h),uh(l,d)&&"ready"==l.uj&&h.ud(a,l)&&h.O(a,l,b);c&&b.restore();fi(this,"postcompose",a);this.a|| -(this.b.style.display="",this.a=!0);Nh(this,a);a.postRenderFunctions.push(Lh)}else this.a&&(this.b.style.display="none",this.a=!1)};ei.prototype.wi=function(a,b,c,d,e,f){var g,h=b.viewState.resolution,l=b.layerStatesArray,m=l.length;a=Dh(b.pixelToCoordinateTransform,a.slice());for(--m;0<=m;--m){g=l[m];var n=g.layer;if(uh(g,h)&&e.call(f,n)&&(g=Mh(this,n).v(a,b,c,d)))return g}};var gi=["Polygon","Circle","LineString","Image","Text"];function hi(){};function ii(a){this.b=a};function ji(a){this.b=a}u(ji,ii);ji.prototype.S=function(){return 35632};function ki(a){this.b=a}u(ki,ii);ki.prototype.S=function(){return 35633};function li(){this.b="precision mediump float;varying vec2 a;varying vec2 b;varying float c;varying float d;uniform float m;uniform vec4 n;uniform vec4 o;uniform vec2 p;void main(void){vec2 windowCenter=vec2((a.x+1.0)/2.0*p.x*d,(a.y+1.0)/2.0*p.y*d);vec2 windowOffset=vec2((b.x+1.0)/2.0*p.x*d,(b.y+1.0)/2.0*p.y*d);float radius=length(windowCenter-windowOffset);float dist=length(windowCenter-gl_FragCoord.xy);if(dist>radius+c){if(o.a==0.0){gl_FragColor=n;}else{gl_FragColor=o;}gl_FragColor.a=gl_FragColor.a-(dist-(radius+c));}else if(n.a==0.0){gl_FragColor=o;if(dist<radius-c){gl_FragColor.a=gl_FragColor.a-(radius-c-dist);}} else{gl_FragColor=n;float strokeDist=radius-c;float antialias=2.0*d;if(dist>strokeDist){gl_FragColor=o;}else if(dist>=strokeDist-antialias){float step=smoothstep(strokeDist-antialias,strokeDist,dist);gl_FragColor=mix(n,o,step);}} gl_FragColor.a=gl_FragColor.a*m;if(gl_FragColor.a<=0.0){discard;}}"} -u(li,ji);var mi=new li; -function ni(){this.b="varying vec2 a;varying vec2 b;varying float c;varying float d;attribute vec2 e;attribute float f;attribute float g;uniform mat4 h;uniform mat4 i;uniform mat4 j;uniform float k;uniform float l;void main(void){mat4 offsetMatrix=i*j;a=vec4(h*vec4(e,0.0,1.0)).xy;d=l;float lineWidth=k*l;c=lineWidth/2.0;if(lineWidth==0.0){lineWidth=2.0*l;}vec2 offset;float radius=g+3.0*l;if(f==0.0){offset=vec2(-1.0,1.0);}else if(f==1.0){offset=vec2(-1.0,-1.0);}else if(f==2.0){offset=vec2(1.0,-1.0);}else{offset=vec2(1.0,1.0);}gl_Position=h*vec4(e+offset*radius,0.0,1.0)+offsetMatrix*vec4(offset*lineWidth,0.0,0.0);b=vec4(h*vec4(e.x+g,e.y,0.0,1.0)).xy;if(distance(a,b)>20000.0){gl_Position=vec4(a,0.0,1.0);}}"} -u(ni,ki);var oi=new ni;function pi(a,b){this.G=a.getUniformLocation(b,"n");this.qa=a.getUniformLocation(b,"k");this.c=a.getUniformLocation(b,"j");this.i=a.getUniformLocation(b,"i");this.a=a.getUniformLocation(b,"m");this.ta=a.getUniformLocation(b,"l");this.g=a.getUniformLocation(b,"h");this.I=a.getUniformLocation(b,"p");this.Z=a.getUniformLocation(b,"o");this.j=a.getAttribLocation(b,"f");this.b=a.getAttribLocation(b,"e");this.O=a.getAttribLocation(b,"g")};function qi(){return[1,0,0,0,0,1,0,0,0,0,1,0,0,0,0,1]}function ri(a,b){a[0]=b[0];a[1]=b[1];a[4]=b[2];a[5]=b[3];a[12]=b[4];a[13]=b[5];return a};function si(a,b){this.origin=kb(b);this.Gb=yh();this.Va=yh();this.yb=yh();this.Ja=qi();this.b=[];this.o=null;this.g=[];this.f=[];this.a=[];this.u=null;this.j=void 0}u(si,Th); -si.prototype.i=function(a,b,c,d,e,f,g,h,l,m,n){var p=a.b,q,r,v,x,y,A,B,aa;this.j&&(q=p.isEnabled(p.STENCIL_TEST),r=p.getParameter(p.STENCIL_FUNC),v=p.getParameter(p.STENCIL_VALUE_MASK),x=p.getParameter(p.STENCIL_REF),y=p.getParameter(p.STENCIL_WRITEMASK),A=p.getParameter(p.STENCIL_FAIL),B=p.getParameter(p.STENCIL_PASS_DEPTH_PASS),aa=p.getParameter(p.STENCIL_PASS_DEPTH_FAIL),p.enable(p.STENCIL_TEST),p.clear(p.STENCIL_BUFFER_BIT),p.stencilMask(255),p.stencilFunc(p.ALWAYS,1,255),p.stencilOp(p.KEEP,p.KEEP, -p.REPLACE),this.j.i(a,b,c,d,e,f,g,h,l,m,n),p.stencilMask(0),p.stencilFunc(p.NOTEQUAL,1,255));ti(a,34962,this.u);ti(a,34963,this.o);f=this.qf(p,a,e,f);var Ra=zh(this.Gb);Fh(Ra,2/(c*e[0]),2/(c*e[1]));Eh(Ra,-d);Gh(Ra,-(b[0]-this.origin[0]),-(b[1]-this.origin[1]));b=zh(this.yb);Fh(b,2/e[0],2/e[1]);e=zh(this.Va);d&&Eh(e,-d);p.uniformMatrix4fv(f.g,!1,ri(this.Ja,Ra));p.uniformMatrix4fv(f.i,!1,ri(this.Ja,b));p.uniformMatrix4fv(f.c,!1,ri(this.Ja,e));p.uniform1f(f.a,g);var ra;l?(m?a=this.ve(p,a,h,l,n):(p.clear(p.COLOR_BUFFER_BIT| -p.DEPTH_BUFFER_BIT),this.Pd(p,a,h,!0),a=(a=l(null))?a:void 0),ra=a):this.Pd(p,a,h,!1);this.rf(p,f);this.j&&(q||p.disable(p.STENCIL_TEST),p.clear(p.STENCIL_BUFFER_BIT),p.stencilFunc(r,x,v),p.stencilMask(y),p.stencilOp(A,aa,B));return ra};function ui(a,b,c,d){a.drawElements(4,d-c,b.f?5125:5123,c*(b.f?4:2))};var vi=[0,0,0,1],wi=[],xi=[0,0,0,1];function yi(a,b,c,d,e,f){a=(c-a)*(f-b)-(e-a)*(d-b);return a<=zi&&a>=-zi?void 0:0<a}var zi=Number.EPSILON||2.220446049250313E-16;function Ai(a){this.b=void 0!==a?a:[];this.a=Bi}var Bi=35044;function Ci(a,b){si.call(this,0,b);this.v=null;this.l=[];this.O=[];this.A=0;this.c={fillColor:null,strokeColor:null,lineDash:null,lineDashOffset:void 0,lineWidth:void 0,s:!1}}u(Ci,si);k=Ci.prototype; -k.ac=function(a,b){var c=a.Yd(),d=a.sa();if(c){this.g.push(this.b.length);this.f.push(b);this.c.s&&(this.O.push(this.b.length),this.c.s=!1);this.A=c;var c=a.ia(),c=nf(c,2,d,-this.origin[0],-this.origin[1]),e=this.a.length,f=this.b.length,g=e/4,h;for(h=0;2>h;h+=d)this.a[e++]=c[h],this.a[e++]=c[h+1],this.a[e++]=0,this.a[e++]=this.A,this.a[e++]=c[h],this.a[e++]=c[h+1],this.a[e++]=1,this.a[e++]=this.A,this.a[e++]=c[h],this.a[e++]=c[h+1],this.a[e++]=2,this.a[e++]=this.A,this.a[e++]=c[h],this.a[e++]=c[h+ -1],this.a[e++]=3,this.a[e++]=this.A,this.b[f++]=g,this.b[f++]=g+1,this.b[f++]=g+2,this.b[f++]=g+2,this.b[f++]=g+3,this.b[f++]=g,g+=4}else this.c.s&&(this.l.pop(),this.l.length&&(d=this.l[this.l.length-1],this.c.fillColor=d[0],this.c.strokeColor=d[1],this.c.lineWidth=d[2],this.c.s=!1))};k.Bb=function(){this.u=new Ai(this.a);this.o=new Ai(this.b);this.g.push(this.b.length);!this.O.length&&0<this.l.length&&(this.l=[]);this.b=this.a=null}; -k.Cb=function(a){var b=this.u,c=this.o;return function(){Di(a,b);Di(a,c)}};k.qf=function(a,b,c,d){var e=Ei(b,mi,oi),f;this.v?f=this.v:this.v=f=new pi(a,e);b.Vc(e);a.enableVertexAttribArray(f.b);a.vertexAttribPointer(f.b,2,5126,!1,16,0);a.enableVertexAttribArray(f.j);a.vertexAttribPointer(f.j,1,5126,!1,16,8);a.enableVertexAttribArray(f.O);a.vertexAttribPointer(f.O,1,5126,!1,16,12);a.uniform2fv(f.I,c);a.uniform1f(f.ta,d);return f}; -k.rf=function(a,b){a.disableVertexAttribArray(b.b);a.disableVertexAttribArray(b.j);a.disableVertexAttribArray(b.O)}; -k.Pd=function(a,b,c){if(tb(c)){var d,e,f;e=this.g[this.g.length-1];for(c=this.O.length-1;0<=c;--c)d=this.O[c],f=this.l[c],a.uniform4fv(this.v.G,f[0]),Fi(this,a,f[1],f[2]),ui(a,b,d,e),e=d}else{var g,h,l,m;l=this.g.length-2;f=e=this.g[l+1];for(d=this.O.length-1;0<=d;--d){g=this.l[d];a.uniform4fv(this.v.G,g[0]);Fi(this,a,g[1],g[2]);for(g=this.O[d];0<=l&&this.g[l]>=g;)m=this.g[l],h=this.f[l],h=w(h).toString(),c[h]&&(e!==f&&ui(a,b,e,f),f=m),l--,e=m;e!==f&&ui(a,b,e,f);e=f=g}}}; -k.ve=function(a,b,c,d,e){var f,g,h,l,m,n,p;p=this.g.length-2;h=this.g[p+1];for(f=this.O.length-1;0<=f;--f)for(g=this.l[f],a.uniform4fv(this.v.G,g[0]),Fi(this,a,g[1],g[2]),l=this.O[f];0<=p&&this.g[p]>=l;){g=this.g[p];m=this.f[p];n=w(m).toString();if(void 0===c[n]&&m.U()&&(void 0===e||nb(e,m.U().D()))&&(a.clear(a.COLOR_BUFFER_BIT|a.DEPTH_BUFFER_BIT),ui(a,b,g,h),h=d(m)))return h;p--;h=g}};function Fi(a,b,c,d){b.uniform4fv(a.v.Z,c);b.uniform1f(a.v.qa,d)} -k.Na=function(a,b){var c,d;b?(c=b.g,this.c.lineDash=c?c:wi,c=b.f,this.c.lineDashOffset=c?c:0,c=b.a,c instanceof CanvasGradient||c instanceof CanvasPattern?c=xi:c=bd(c).map(function(a,b){return 3!=b?a/255:a})||xi,d=b.c,d=void 0!==d?d:1):(c=[0,0,0,0],d=0);var e=a?a.b:[0,0,0,0];e instanceof CanvasGradient||e instanceof CanvasPattern?e=vi:e=bd(e).map(function(a,b){return 3!=b?a/255:a})||vi;this.c.strokeColor&&ja(this.c.strokeColor,c)&&this.c.fillColor&&ja(this.c.fillColor,e)&&this.c.lineWidth===d||(this.c.s= -!0,this.c.fillColor=e,this.c.strokeColor=c,this.c.lineWidth=d,this.l.push([e,c,d]))};function Gi(){this.b="precision mediump float;varying vec2 a;varying float b;uniform float k;uniform sampler2D l;void main(void){vec4 texColor=texture2D(l,a);gl_FragColor.rgb=texColor.rgb;float alpha=texColor.a*b*k;if(alpha==0.0){discard;}gl_FragColor.a=alpha;}"}u(Gi,ji);var Hi=new Gi; -function Ii(){this.b="varying vec2 a;varying float b;attribute vec2 c;attribute vec2 d;attribute vec2 e;attribute float f;attribute float g;uniform mat4 h;uniform mat4 i;uniform mat4 j;void main(void){mat4 offsetMatrix=i;if(g==1.0){offsetMatrix=i*j;}vec4 offsets=offsetMatrix*vec4(e,0.0,0.0);gl_Position=h*vec4(c,0.0,1.0)+offsets;a=d;b=f;}"}u(Ii,ki);var Ji=new Ii; -function Ki(a,b){this.c=a.getUniformLocation(b,"j");this.i=a.getUniformLocation(b,"i");this.a=a.getUniformLocation(b,"k");this.g=a.getUniformLocation(b,"h");this.u=a.getAttribLocation(b,"e");this.v=a.getAttribLocation(b,"f");this.b=a.getAttribLocation(b,"c");this.A=a.getAttribLocation(b,"g");this.C=a.getAttribLocation(b,"d")};function Li(a,b){this.j=a;this.b=b;this.a={};this.c={};this.g={};this.o=this.u=this.i=this.l=null;(this.f=fa(da,"OES_element_index_uint"))&&b.getExtension("OES_element_index_uint");z(this.j,"webglcontextlost",this.No,this);z(this.j,"webglcontextrestored",this.Oo,this)}u(Li,Jc); -function ti(a,b,c){var d=a.b,e=c.b,f=String(w(c));if(f in a.a)d.bindBuffer(b,a.a[f].buffer);else{var g=d.createBuffer();d.bindBuffer(b,g);var h;34962==b?h=new Float32Array(e):34963==b&&(h=a.f?new Uint32Array(e):new Uint16Array(e));d.bufferData(b,h,c.a);a.a[f]={nc:c,buffer:g}}}function Di(a,b){var c=a.b,d=String(w(b)),e=a.a[d];c.isContextLost()||c.deleteBuffer(e.buffer);delete a.a[d]}k=Li.prototype; -k.ra=function(){Ic(this.j);var a=this.b;if(!a.isContextLost()){for(var b in this.a)a.deleteBuffer(this.a[b].buffer);for(b in this.g)a.deleteProgram(this.g[b]);for(b in this.c)a.deleteShader(this.c[b]);a.deleteFramebuffer(this.i);a.deleteRenderbuffer(this.o);a.deleteTexture(this.u)}};k.Mo=function(){return this.b}; -function Mi(a){if(!a.i){var b=a.b,c=b.createFramebuffer();b.bindFramebuffer(b.FRAMEBUFFER,c);var d=Ni(b,1,1),e=b.createRenderbuffer();b.bindRenderbuffer(b.RENDERBUFFER,e);b.renderbufferStorage(b.RENDERBUFFER,b.DEPTH_COMPONENT16,1,1);b.framebufferTexture2D(b.FRAMEBUFFER,b.COLOR_ATTACHMENT0,b.TEXTURE_2D,d,0);b.framebufferRenderbuffer(b.FRAMEBUFFER,b.DEPTH_ATTACHMENT,b.RENDERBUFFER,e);b.bindTexture(b.TEXTURE_2D,null);b.bindRenderbuffer(b.RENDERBUFFER,null);b.bindFramebuffer(b.FRAMEBUFFER,null);a.i=c; -a.u=d;a.o=e}return a.i}function Oi(a,b){var c=String(w(b));if(c in a.c)return a.c[c];var d=a.b,e=d.createShader(b.S());d.shaderSource(e,b.b);d.compileShader(e);return a.c[c]=e}function Ei(a,b,c){var d=w(b)+"/"+w(c);if(d in a.g)return a.g[d];var e=a.b,f=e.createProgram();e.attachShader(f,Oi(a,b));e.attachShader(f,Oi(a,c));e.linkProgram(f);return a.g[d]=f}k.No=function(){rb(this.a);rb(this.c);rb(this.g);this.o=this.u=this.i=this.l=null};k.Oo=function(){}; -k.Vc=function(a){if(a==this.l)return!1;this.b.useProgram(a);this.l=a;return!0};function Pi(a,b,c){var d=a.createTexture();a.bindTexture(a.TEXTURE_2D,d);a.texParameteri(a.TEXTURE_2D,a.TEXTURE_MAG_FILTER,a.LINEAR);a.texParameteri(a.TEXTURE_2D,a.TEXTURE_MIN_FILTER,a.LINEAR);void 0!==b&&a.texParameteri(3553,10242,b);void 0!==c&&a.texParameteri(3553,10243,c);return d}function Ni(a,b,c){var d=Pi(a,void 0,void 0);a.texImage2D(a.TEXTURE_2D,0,a.RGBA,b,c,0,a.RGBA,a.UNSIGNED_BYTE,null);return d} -function Qi(a,b){var c=Pi(a,33071,33071);a.texImage2D(a.TEXTURE_2D,0,a.RGBA,a.RGBA,a.UNSIGNED_BYTE,b);return c};function Ri(a,b){si.call(this,0,b);this.G=this.C=void 0;this.A=[];this.v=[];this.ta=void 0;this.l=[];this.c=[];this.Z=this.I=void 0;this.qa=null;this.na=this.mb=this.fa=this.ea=this.T=this.$a=void 0;this.Ha=[];this.O=[];this.$b=void 0}u(Ri,si);k=Ri.prototype;k.Cb=function(a){var b=this.u,c=this.o,d=this.Ha,e=this.O,f=a.b;return function(){if(!f.isContextLost()){var g,h;g=0;for(h=d.length;g<h;++g)f.deleteTexture(d[g]);g=0;for(h=e.length;g<h;++g)f.deleteTexture(e[g])}Di(a,b);Di(a,c)}}; -function Si(a,b,c,d){var e=a.C,f=a.G,g=a.ta,h=a.I,l=a.Z,m=a.$a,n=a.T,p=a.ea,q=a.fa?1:0,r=-a.mb,v=a.na,x=a.$b,y=Math.cos(r),r=Math.sin(r),A=a.b.length,B=a.a.length,aa,Ra,ra,Ka,C,Na;for(aa=0;aa<c;aa+=d)C=b[aa]-a.origin[0],Na=b[aa+1]-a.origin[1],Ra=B/8,ra=-v*e,Ka=-v*(g-f),a.a[B++]=C,a.a[B++]=Na,a.a[B++]=ra*y-Ka*r,a.a[B++]=ra*r+Ka*y,a.a[B++]=n/l,a.a[B++]=(p+g)/h,a.a[B++]=m,a.a[B++]=q,ra=v*(x-e),Ka=-v*(g-f),a.a[B++]=C,a.a[B++]=Na,a.a[B++]=ra*y-Ka*r,a.a[B++]=ra*r+Ka*y,a.a[B++]=(n+x)/l,a.a[B++]=(p+g)/h, -a.a[B++]=m,a.a[B++]=q,ra=v*(x-e),Ka=v*f,a.a[B++]=C,a.a[B++]=Na,a.a[B++]=ra*y-Ka*r,a.a[B++]=ra*r+Ka*y,a.a[B++]=(n+x)/l,a.a[B++]=p/h,a.a[B++]=m,a.a[B++]=q,ra=-v*e,Ka=v*f,a.a[B++]=C,a.a[B++]=Na,a.a[B++]=ra*y-Ka*r,a.a[B++]=ra*r+Ka*y,a.a[B++]=n/l,a.a[B++]=p/h,a.a[B++]=m,a.a[B++]=q,a.b[A++]=Ra,a.b[A++]=Ra+1,a.b[A++]=Ra+2,a.b[A++]=Ra,a.b[A++]=Ra+2,a.b[A++]=Ra+3}k.qc=function(a,b){this.g.push(this.b.length);this.f.push(b);var c=a.ia();Si(this,c,c.length,a.sa())}; -k.sc=function(a,b){this.g.push(this.b.length);this.f.push(b);var c=a.ia();Si(this,c,c.length,a.sa())};k.Bb=function(a){a=a.b;this.A.push(this.b.length);this.v.push(this.b.length);this.u=new Ai(this.a);this.o=new Ai(this.b);var b={};Ti(this.Ha,this.l,b,a);Ti(this.O,this.c,b,a);this.ta=this.G=this.C=void 0;this.c=this.l=null;this.Z=this.I=void 0;this.b=null;this.na=this.mb=this.fa=this.ea=this.T=this.$a=void 0;this.a=null;this.$b=void 0}; -function Ti(a,b,c,d){var e,f,g,h=b.length;for(g=0;g<h;++g)e=b[g],f=w(e).toString(),f in c?e=c[f]:(e=Qi(d,e),c[f]=e),a[g]=e} -k.qf=function(a,b){var c=Ei(b,Hi,Ji),d;this.qa?d=this.qa:this.qa=d=new Ki(a,c);b.Vc(c);a.enableVertexAttribArray(d.b);a.vertexAttribPointer(d.b,2,5126,!1,32,0);a.enableVertexAttribArray(d.u);a.vertexAttribPointer(d.u,2,5126,!1,32,8);a.enableVertexAttribArray(d.C);a.vertexAttribPointer(d.C,2,5126,!1,32,16);a.enableVertexAttribArray(d.v);a.vertexAttribPointer(d.v,1,5126,!1,32,24);a.enableVertexAttribArray(d.A);a.vertexAttribPointer(d.A,1,5126,!1,32,28);return d}; -k.rf=function(a,b){a.disableVertexAttribArray(b.b);a.disableVertexAttribArray(b.u);a.disableVertexAttribArray(b.C);a.disableVertexAttribArray(b.v);a.disableVertexAttribArray(b.A)}; -k.Pd=function(a,b,c,d){var e=d?this.O:this.Ha;d=d?this.v:this.A;if(tb(c)){var f,g;c=0;f=e.length;for(g=0;c<f;++c){a.bindTexture(3553,e[c]);var h=d[c];ui(a,b,g,h);g=h}}else for(g=f=0,h=e.length;g<h;++g){a.bindTexture(3553,e[g]);for(var l=0<g?d[g-1]:0,m=d[g],n=l;f<this.g.length&&this.g[f]<=m;){var p=w(this.f[f]).toString();void 0!==c[p]?(n!==l&&ui(a,b,n,l),l=n=f===this.g.length-1?m:this.g[f+1]):l=f===this.g.length-1?m:this.g[f+1];f++}n!==l&&ui(a,b,n,l)}}; -k.ve=function(a,b,c,d,e){var f,g,h,l,m,n,p=this.g.length-1;for(f=this.O.length-1;0<=f;--f)for(a.bindTexture(3553,this.O[f]),g=0<f?this.v[f-1]:0,l=this.v[f];0<=p&&this.g[p]>=g;){h=this.g[p];m=this.f[p];n=w(m).toString();if(void 0===c[n]&&m.U()&&(void 0===e||nb(e,m.U().D()))&&(a.clear(a.COLOR_BUFFER_BIT|a.DEPTH_BUFFER_BIT),ui(a,b,h,l),l=d(m)))return l;l=h;p--}}; -k.Wb=function(a){var b=a.Jc(),c=a.Y(1),d=a.ye(),e=a.kg(1),f=a.f,g=a.Tc(),h=a.o,l=a.j,m=a.kc();a=a.c;var n;this.l.length?(n=this.l[this.l.length-1],w(n)!=w(c)&&(this.A.push(this.b.length),this.l.push(c))):this.l.push(c);this.c.length?(n=this.c[this.c.length-1],w(n)!=w(e)&&(this.v.push(this.b.length),this.c.push(e))):this.c.push(e);this.C=b[0];this.G=b[1];this.ta=m[1];this.I=d[1];this.Z=d[0];this.$a=f;this.T=g[0];this.ea=g[1];this.mb=l;this.fa=h;this.na=a;this.$b=m[0]};function Ui(a,b,c){var d=b-c;return a[0]===a[d]&&a[1]===a[d+1]&&3<(b-0)/c?!!sf(a,0,b,c):!1};function Vi(){this.b="precision mediump float;varying float a;varying vec2 b;varying float c;uniform float m;uniform vec4 n;uniform vec2 o;uniform float p;void main(void){if(a>0.0){vec2 windowCoords=vec2((b.x+1.0)/2.0*o.x*p,(b.y+1.0)/2.0*o.y*p);if(length(windowCoords-gl_FragCoord.xy)>c*p){discard;}} gl_FragColor=n;float alpha=n.a*m;if(alpha==0.0){discard;}gl_FragColor.a=alpha;}"}u(Vi,ji);var Wi=new Vi; -function Xi(){this.b="varying float a;varying vec2 b;varying float c;attribute vec2 d;attribute vec2 e;attribute vec2 f;attribute float g;uniform mat4 h;uniform mat4 i;uniform mat4 j;uniform float k;uniform float l;bool nearlyEquals(in float value,in float ref){float epsilon=0.000000000001;return value>=ref-epsilon&&value<=ref+epsilon;}void alongNormal(out vec2 offset,in vec2 nextP,in float turnDir,in float direction){vec2 dirVect=nextP-e;vec2 normal=normalize(vec2(-turnDir*dirVect.y,turnDir*dirVect.x));offset=k/2.0*normal*direction;}void miterUp(out vec2 offset,out float round,in bool isRound,in float direction){float halfWidth=k/2.0;vec2 tangent=normalize(normalize(f-e)+normalize(e-d));vec2 normal=vec2(-tangent.y,tangent.x);vec2 dirVect=f-e;vec2 tmpNormal=normalize(vec2(-dirVect.y,dirVect.x));float miterLength=abs(halfWidth/dot(normal,tmpNormal));offset=normal*direction*miterLength;round=0.0;if(isRound){round=1.0;}else if(miterLength>l+k){offset=halfWidth*tmpNormal*direction;}} bool miterDown(out vec2 offset,in vec4 projPos,in mat4 offsetMatrix,in float direction){bool degenerate=false;vec2 tangent=normalize(normalize(f-e)+normalize(e-d));vec2 normal=vec2(-tangent.y,tangent.x);vec2 dirVect=d-e;vec2 tmpNormal=normalize(vec2(-dirVect.y,dirVect.x));vec2 longOffset,shortOffset,longVertex;vec4 shortProjVertex;float halfWidth=k/2.0;if(length(f-e)>length(d-e)){longOffset=tmpNormal*direction*halfWidth;shortOffset=normalize(vec2(dirVect.y,-dirVect.x))*direction*halfWidth;longVertex=f;shortProjVertex=h*vec4(d,0.0,1.0);}else{shortOffset=tmpNormal*direction*halfWidth;longOffset=normalize(vec2(dirVect.y,-dirVect.x))*direction*halfWidth;longVertex=d;shortProjVertex=h*vec4(f,0.0,1.0);}vec4 p1=h*vec4(longVertex,0.0,1.0)+offsetMatrix*vec4(longOffset,0.0,0.0);vec4 p2=projPos+offsetMatrix*vec4(longOffset,0.0,0.0);vec4 p3=shortProjVertex+offsetMatrix*vec4(-shortOffset,0.0,0.0);vec4 p4=shortProjVertex+offsetMatrix*vec4(shortOffset,0.0,0.0);float denom=(p4.y-p3.y)*(p2.x-p1.x)-(p4.x-p3.x)*(p2.y-p1.y);float firstU=((p4.x-p3.x)*(p1.y-p3.y)-(p4.y-p3.y)*(p1.x-p3.x))/denom;float secondU=((p2.x-p1.x)*(p1.y-p3.y)-(p2.y-p1.y)*(p1.x-p3.x))/denom;float epsilon=0.000000000001;if(firstU>epsilon&&firstU<1.0-epsilon&&secondU>epsilon&&secondU<1.0-epsilon){shortProjVertex.x=p1.x+firstU*(p2.x-p1.x);shortProjVertex.y=p1.y+firstU*(p2.y-p1.y);offset=shortProjVertex.xy;degenerate=true;}else{float miterLength=abs(halfWidth/dot(normal,tmpNormal));offset=normal*direction*miterLength;}return degenerate;}void squareCap(out vec2 offset,out float round,in bool isRound,in vec2 nextP,in float turnDir,in float direction){round=0.0;vec2 dirVect=e-nextP;vec2 firstNormal=normalize(dirVect);vec2 secondNormal=vec2(turnDir*firstNormal.y*direction,-turnDir*firstNormal.x*direction);vec2 hypotenuse=normalize(firstNormal-secondNormal);vec2 normal=vec2(turnDir*hypotenuse.y*direction,-turnDir*hypotenuse.x*direction);float length=sqrt(c*c*2.0);offset=normal*length;if(isRound){round=1.0;}} void main(void){bool degenerate=false;float direction=float(sign(g));mat4 offsetMatrix=i*j;vec2 offset;vec4 projPos=h*vec4(e,0.0,1.0);bool round=nearlyEquals(mod(g,2.0),0.0);a=0.0;c=k/2.0;b=projPos.xy;if(nearlyEquals(mod(g,3.0),0.0)||nearlyEquals(mod(g,17.0),0.0)){alongNormal(offset,f,1.0,direction);}else if(nearlyEquals(mod(g,5.0),0.0)||nearlyEquals(mod(g,13.0),0.0)){alongNormal(offset,d,-1.0,direction);}else if(nearlyEquals(mod(g,23.0),0.0)){miterUp(offset,a,round,direction);}else if(nearlyEquals(mod(g,19.0),0.0)){degenerate=miterDown(offset,projPos,offsetMatrix,direction);}else if(nearlyEquals(mod(g,7.0),0.0)){squareCap(offset,a,round,f,1.0,direction);}else if(nearlyEquals(mod(g,11.0),0.0)){squareCap(offset,a,round,d,-1.0,direction);}if(!degenerate){vec4 offsets=offsetMatrix*vec4(offset,0.0,0.0);gl_Position=projPos+offsets;}else{gl_Position=vec4(offset,0.0,1.0);}}"} -u(Xi,ki);var Yi=new Xi;function Zi(a,b){this.G=a.getUniformLocation(b,"n");this.qa=a.getUniformLocation(b,"k");this.Z=a.getUniformLocation(b,"l");this.c=a.getUniformLocation(b,"j");this.i=a.getUniformLocation(b,"i");this.a=a.getUniformLocation(b,"m");this.ta=a.getUniformLocation(b,"p");this.g=a.getUniformLocation(b,"h");this.I=a.getUniformLocation(b,"o");this.f=a.getAttribLocation(b,"g");this.l=a.getAttribLocation(b,"d");this.o=a.getAttribLocation(b,"f");this.b=a.getAttribLocation(b,"e")};function $i(a,b){si.call(this,0,b);this.v=null;this.O=[];this.l=[];this.c={strokeColor:null,lineCap:void 0,lineDash:null,lineDashOffset:void 0,lineJoin:void 0,lineWidth:void 0,miterLimit:void 0,s:!1}}u($i,si); -function aj(a,b,c,d){var e,f=a.a.length,g=a.b.length,h="bevel"===a.c.lineJoin?0:"miter"===a.c.lineJoin?1:2,l="butt"===a.c.lineCap?0:"square"===a.c.lineCap?1:2,m=Ui(b,c,d),n,p,q,r=g,v=1,x,y,A;for(e=0;e<c;e+=d){q=f/7;x=y;y=A||[b[e],b[e+1]];if(e)if(e===c-d){m?A=n:(x=x||[0,0],f=bj(a,x,y,[0,0],v*cj*(l||1),f),f=bj(a,x,y,[0,0],-v*cj*(l||1),f),a.b[g++]=q,a.b[g++]=r-1,a.b[g++]=r,a.b[g++]=r,a.b[g++]=q+1,a.b[g++]=q,l&&(f=bj(a,x,y,[0,0],v*dj*l,f),f=bj(a,x,y,[0,0],-v*dj*l,f),a.b[g++]=q+2,a.b[g++]=q,a.b[g++]=q+ -1,a.b[g++]=q+1,a.b[g++]=q+3,a.b[g++]=q+2));break}else A=[b[e+d],b[e+d+1]];else{A=[b[e+d],b[e+d+1]];if(c-0===2*d&&ja(y,A))break;if(m)x=[b[c-2*d],b[c-2*d+1]],n=A;else{l&&(f=bj(a,[0,0],y,A,v*ej*l,f),f=bj(a,[0,0],y,A,-v*ej*l,f),a.b[g++]=q+2,a.b[g++]=q,a.b[g++]=q+1,a.b[g++]=q+1,a.b[g++]=q+3,a.b[g++]=q+2);f=bj(a,[0,0],y,A,v*fj*(l||1),f);f=bj(a,[0,0],y,A,-v*fj*(l||1),f);r=f/7-1;continue}}p=yi(x[0],x[1],y[0],y[1],A[0],A[1])?-1:1;f=bj(a,x,y,A,p*gj*(h||1),f);f=bj(a,x,y,A,p*hj*(h||1),f);f=bj(a,x,y,A,-p*ij*(h|| -1),f);0<e&&(a.b[g++]=q,a.b[g++]=r-1,a.b[g++]=r,a.b[g++]=q+2,a.b[g++]=q,a.b[g++]=0<v*p?r:r-1);a.b[g++]=q;a.b[g++]=q+2;a.b[g++]=q+1;r=q+2;v=p;h&&(f=bj(a,x,y,A,p*jj*h,f),a.b[g++]=q+1,a.b[g++]=q+3,a.b[g++]=q)}m&&(q=q||f/7,p=Pf([x[0],x[1],y[0],y[1],A[0],A[1]],0,6,2)?1:-1,f=bj(a,x,y,A,p*gj*(h||1),f),bj(a,x,y,A,-p*ij*(h||1),f),a.b[g++]=q,a.b[g++]=r-1,a.b[g++]=r,a.b[g++]=q+1,a.b[g++]=q,a.b[g++]=0<v*p?r:r-1)} -function bj(a,b,c,d,e,f){a.a[f++]=b[0];a.a[f++]=b[1];a.a[f++]=c[0];a.a[f++]=c[1];a.a[f++]=d[0];a.a[f++]=d[1];a.a[f++]=e;return f}function kj(a,b,c){b-=0;return b<2*c?!1:b===2*c?!ja([a[0],a[1]],[a[0+c],a[c+1]]):!0}k=$i.prototype;k.Rb=function(a,b){var c=a.ia(),d=a.sa();kj(c,c.length,d)&&(c=nf(c,c.length,d,-this.origin[0],-this.origin[1]),this.c.s&&(this.l.push(this.b.length),this.c.s=!1),this.g.push(this.b.length),this.f.push(b),aj(this,c,c.length,d))}; -k.pc=function(a,b){var c=this.b.length,d=a.Nc(),e,f;e=0;for(f=d.length;e<f;++e){var g=d[e].ia(),h=d[e].sa();kj(g,g.length,h)&&(g=nf(g,g.length,h,-this.origin[0],-this.origin[1]),aj(this,g,g.length,h))}this.b.length>c&&(this.g.push(c),this.f.push(b),this.c.s&&(this.l.push(c),this.c.s=!1))}; -function lj(a,b,c,d){Ui(b,b.length,d)||(b.push(b[0]),b.push(b[1]));aj(a,b,b.length,d);if(c.length){var e;b=0;for(e=c.length;b<e;++b)Ui(c[b],c[b].length,d)||(c[b].push(c[b][0]),c[b].push(c[b][1])),aj(a,c[b],c[b].length,d)}}function mj(a,b,c){c=void 0===c?a.b.length:c;a.g.push(c);a.f.push(b);a.c.s&&(a.l.push(c),a.c.s=!1)}k.Bb=function(){this.u=new Ai(this.a);this.o=new Ai(this.b);this.g.push(this.b.length);!this.l.length&&0<this.O.length&&(this.O=[]);this.b=this.a=null}; -k.Cb=function(a){var b=this.u,c=this.o;return function(){Di(a,b);Di(a,c)}};k.qf=function(a,b,c,d){var e=Ei(b,Wi,Yi),f;this.v?f=this.v:this.v=f=new Zi(a,e);b.Vc(e);a.enableVertexAttribArray(f.l);a.vertexAttribPointer(f.l,2,5126,!1,28,0);a.enableVertexAttribArray(f.b);a.vertexAttribPointer(f.b,2,5126,!1,28,8);a.enableVertexAttribArray(f.o);a.vertexAttribPointer(f.o,2,5126,!1,28,16);a.enableVertexAttribArray(f.f);a.vertexAttribPointer(f.f,1,5126,!1,28,24);a.uniform2fv(f.I,c);a.uniform1f(f.ta,d);return f}; -k.rf=function(a,b){a.disableVertexAttribArray(b.l);a.disableVertexAttribArray(b.b);a.disableVertexAttribArray(b.o);a.disableVertexAttribArray(b.f)}; -k.Pd=function(a,b,c,d){var e=a.getParameter(a.DEPTH_FUNC),f=a.getParameter(a.DEPTH_WRITEMASK);d||(a.enable(a.DEPTH_TEST),a.depthMask(!0),a.depthFunc(a.NOTEQUAL));if(tb(c)){var g,h,l;h=this.g[this.g.length-1];for(c=this.l.length-1;0<=c;--c)g=this.l[c],l=this.O[c],nj(this,a,l[0],l[1],l[2]),ui(a,b,g,h),a.clear(a.DEPTH_BUFFER_BIT),h=g}else{var m,n,p,q;p=this.g.length-2;l=h=this.g[p+1];for(g=this.l.length-1;0<=g;--g){m=this.O[g];nj(this,a,m[0],m[1],m[2]);for(m=this.l[g];0<=p&&this.g[p]>=m;)q=this.g[p], -n=this.f[p],n=w(n).toString(),c[n]&&(h!==l&&(ui(a,b,h,l),a.clear(a.DEPTH_BUFFER_BIT)),l=q),p--,h=q;h!==l&&(ui(a,b,h,l),a.clear(a.DEPTH_BUFFER_BIT));h=l=m}}d||(a.disable(a.DEPTH_TEST),a.clear(a.DEPTH_BUFFER_BIT),a.depthMask(f),a.depthFunc(e))}; -k.ve=function(a,b,c,d,e){var f,g,h,l,m,n,p;p=this.g.length-2;h=this.g[p+1];for(f=this.l.length-1;0<=f;--f)for(g=this.O[f],nj(this,a,g[0],g[1],g[2]),l=this.l[f];0<=p&&this.g[p]>=l;){g=this.g[p];m=this.f[p];n=w(m).toString();if(void 0===c[n]&&m.U()&&(void 0===e||nb(e,m.U().D()))&&(a.clear(a.COLOR_BUFFER_BIT|a.DEPTH_BUFFER_BIT),ui(a,b,g,h),h=d(m)))return h;p--;h=g}};function nj(a,b,c,d,e){b.uniform4fv(a.v.G,c);b.uniform1f(a.v.qa,d);b.uniform1f(a.v.Z,e)} -k.Na=function(a,b){var c=b.i;this.c.lineCap=void 0!==c?c:"round";c=b.g;this.c.lineDash=c?c:wi;c=b.f;this.c.lineDashOffset=c?c:0;c=b.j;this.c.lineJoin=void 0!==c?c:"round";c=b.a;c instanceof CanvasGradient||c instanceof CanvasPattern?c=xi:c=bd(c).map(function(a,b){return 3!=b?a/255:a})||xi;var d=b.c,d=void 0!==d?d:1,e=b.l,e=void 0!==e?e:10;this.c.strokeColor&&ja(this.c.strokeColor,c)&&this.c.lineWidth===d&&this.c.miterLimit===e||(this.c.s=!0,this.c.strokeColor=c,this.c.lineWidth=d,this.c.miterLimit= -e,this.O.push([c,d,e]))};var fj=3,cj=5,ej=7,dj=11,gj=13,hj=17,ij=19,jj=23;function oj(){this.b="precision mediump float;uniform vec4 e;uniform float f;void main(void){gl_FragColor=e;float alpha=e.a*f;if(alpha==0.0){discard;}gl_FragColor.a=alpha;}"}u(oj,ji);var pj=new oj;function qj(){this.b="attribute vec2 a;uniform mat4 b;uniform mat4 c;uniform mat4 d;void main(void){gl_Position=b*vec4(a,0.0,1.0);}"}u(qj,ki);var rj=new qj; -function sj(a,b){this.G=a.getUniformLocation(b,"e");this.c=a.getUniformLocation(b,"d");this.i=a.getUniformLocation(b,"c");this.a=a.getUniformLocation(b,"f");this.g=a.getUniformLocation(b,"b");this.b=a.getAttribLocation(b,"a")};function tj(a){a=a||{};this.a=void 0!==a.color?a.color:null;this.i=a.lineCap;this.g=void 0!==a.lineDash?a.lineDash:null;this.f=a.lineDashOffset;this.j=a.lineJoin;this.l=a.miterLimit;this.c=a.width;this.b=void 0}k=tj.prototype;k.clone=function(){var a=this.a;return new tj({color:a&&a.slice?a.slice():a||void 0,lineCap:this.i,lineDash:this.g?this.g.slice():void 0,lineDashOffset:this.f,lineJoin:this.j,miterLimit:this.l,width:this.c})};k.Do=function(){return this.a};k.Qk=function(){return this.i}; -k.Eo=function(){return this.g};k.Rk=function(){return this.f};k.Sk=function(){return this.j};k.Xk=function(){return this.l};k.Fo=function(){return this.c};k.Go=function(a){this.a=a;this.b=void 0};k.Rp=function(a){this.i=a;this.b=void 0};k.setLineDash=function(a){this.g=a;this.b=void 0};k.Sp=function(a){this.f=a;this.b=void 0};k.Tp=function(a){this.j=a;this.b=void 0};k.Wp=function(a){this.l=a;this.b=void 0};k.Zp=function(a){this.c=a;this.b=void 0};function uj(a){this.b=this.a=this.g=void 0;this.i=void 0===a?!0:a;this.c=0}function vj(a){var b=a.b;if(b){var c=b.next,d=b.ub;c&&(c.ub=d);d&&(d.next=c);a.b=c||d;a.g===a.a?(a.b=void 0,a.g=void 0,a.a=void 0):a.g===b?a.g=a.b:a.a===b&&(a.a=d?a.b.ub:a.b);a.c--}}function wj(a){a.b=a.g;if(a.b)return a.b.data}function xj(a){if(a.b&&a.b.next)return a.b=a.b.next,a.b.data}function yj(a){if(a.b&&a.b.next)return a.b.next.data}function zj(a){if(a.b&&a.b.ub)return a.b=a.b.ub,a.b.data} -function Aj(a){if(a.b&&a.b.ub)return a.b.ub.data}function Bj(a){if(a.b)return a.b.data}uj.prototype.concat=function(a){if(a.b){if(this.b){var b=this.b.next;this.b.next=a.g;a.g.ub=this.b;b.ub=a.a;a.a.next=b;this.c+=a.c}else this.b=a.b,this.g=a.g,this.a=a.a,this.c=a.c;a.b=void 0;a.g=void 0;a.a=void 0;a.c=0}};var Cj,Dj,Ej,Fj; -(function(){var a={},b={ma:a};(function(c){if("object"===typeof a&&"undefined"!==typeof b)b.ma=c();else{var d;"undefined"!==typeof window?d=window:"undefined"!==typeof global?d=global:"undefined"!==typeof self?d=self:d=this;d.Dq=c()}})(function(){return function d(a,b,g){function e(h,l){if(!b[h]){if(!a[h]){var m="function"==typeof require&&require;if(!l&&m)return m(h,!0);if(f)return f(h,!0);m=Error("Cannot find module '"+h+"'");throw m.code="MODULE_NOT_FOUND",m;}m=b[h]={ma:{}};a[h][0].call(m.ma,function(b){var d= -a[h][1][b];return e(d?d:b)},m,m.ma,d,a,b,g)}return b[h].ma}for(var f="function"==typeof require&&require,m=0;m<g.length;m++)e(g[m]);return e}({1:[function(a,b){function d(a,b,f,g,q){f=f||0;g=g||a.length-1;for(q=q||h;g>f;){if(600<g-f){var l=g-f+1,m=b-f+1,p=Math.log(l),n=.5*Math.exp(2*p/3),p=.5*Math.sqrt(p*n*(l-n)/l)*(0>m-l/2?-1:1);d(a,b,Math.max(f,Math.floor(b-m*n/l+p)),Math.min(g,Math.floor(b+(l-m)*n/l+p)),q)}l=a[b];m=f;n=g;e(a,f,b);for(0<q(a[g],l)&&e(a,f,g);m<n;){e(a,m,n);m++;for(n--;0>q(a[m],l);)m++; -for(;0<q(a[n],l);)n--}0===q(a[f],l)?e(a,f,n):(n++,e(a,n,g));n<=b&&(f=n+1);b<=n&&(g=n-1)}}function e(a,b,d){var e=a[b];a[b]=a[d];a[d]=e}function h(a,b){return a<b?-1:a>b?1:0}b.ma=d},{}],2:[function(a,b){function d(a,b){if(!(this instanceof d))return new d(a,b);this.Df=Math.max(4,a||9);this.Xg=Math.max(2,Math.ceil(.4*this.Df));b&&this.ak(b);this.clear()}function e(a,b){h(a,0,a.children.length,b,a)}function h(a,b,d,e,f){f||(f=x(null));f.da=Infinity;f.ga=Infinity;f.ba=-Infinity;f.ja=-Infinity;for(var g;b< -d;b++)g=a.children[b],l(f,a.gb?e(g):g);return f}function l(a,b){a.da=Math.min(a.da,b.da);a.ga=Math.min(a.ga,b.ga);a.ba=Math.max(a.ba,b.ba);a.ja=Math.max(a.ja,b.ja)}function m(a,b){return a.da-b.da}function n(a,b){return a.ga-b.ga}function p(a){return(a.ba-a.da)*(a.ja-a.ga)}function q(a){return a.ba-a.da+(a.ja-a.ga)}function r(a,b){return a.da<=b.da&&a.ga<=b.ga&&b.ba<=a.ba&&b.ja<=a.ja}function v(a,b){return b.da<=a.ba&&b.ga<=a.ja&&b.ba>=a.da&&b.ja>=a.ga}function x(a){return{children:a,height:1,gb:!0, -da:Infinity,ga:Infinity,ba:-Infinity,ja:-Infinity}}function y(a,b,d,e,f){for(var g=[b,d],h;g.length;)d=g.pop(),b=g.pop(),d-b<=e||(h=b+Math.ceil((d-b)/e/2)*e,A(a,h,b,d,f),g.push(b,h,h,d))}b.ma=d;var A=a("quickselect");d.prototype={all:function(){return this.Sg(this.data,[])},search:function(a){var b=this.data,d=[],e=this.xb;if(!v(a,b))return d;for(var f=[],g,h,l,m;b;){g=0;for(h=b.children.length;g<h;g++)l=b.children[g],m=b.gb?e(l):l,v(a,m)&&(b.gb?d.push(l):r(a,m)?this.Sg(l,d):f.push(l));b=f.pop()}return d}, -load:function(a){if(!a||!a.length)return this;if(a.length<this.Xg){for(var b=0,d=a.length;b<d;b++)this.Ea(a[b]);return this}a=this.Ug(a.slice(),0,a.length-1,0);this.data.children.length?this.data.height===a.height?this.Zg(this.data,a):(this.data.height<a.height&&(b=this.data,this.data=a,a=b),this.Wg(a,this.data.height-a.height-1,!0)):this.data=a;return this},Ea:function(a){a&&this.Wg(a,this.data.height-1);return this},clear:function(){this.data=x([]);return this},remove:function(a,b){if(!a)return this; -for(var d=this.data,e=this.xb(a),f=[],g=[],h,l,m,p;d||f.length;){d||(d=f.pop(),l=f[f.length-1],h=g.pop(),p=!0);if(d.gb){a:{m=a;var n=d.children,q=b;if(q){for(var v=0;v<n.length;v++)if(q(m,n[v])){m=v;break a}m=-1}else m=n.indexOf(m)}if(-1!==m){d.children.splice(m,1);f.push(d);this.Zj(f);break}}p||d.gb||!r(d,e)?l?(h++,d=l.children[h],p=!1):d=null:(f.push(d),g.push(h),h=0,l=d,d=d.children[0])}return this},xb:function(a){return a},Hf:m,If:n,toJSON:function(){return this.data},Sg:function(a,b){for(var d= -[];a;)a.gb?b.push.apply(b,a.children):d.push.apply(d,a.children),a=d.pop();return b},Ug:function(a,b,d,f){var g=d-b+1,h=this.Df,l;if(g<=h)return l=x(a.slice(b,d+1)),e(l,this.xb),l;f||(f=Math.ceil(Math.log(g)/Math.log(h)),h=Math.ceil(g/Math.pow(h,f-1)));l=x([]);l.gb=!1;l.height=f;var g=Math.ceil(g/h),h=g*Math.ceil(Math.sqrt(h)),m,p,n;for(y(a,b,d,h,this.Hf);b<=d;b+=h)for(p=Math.min(b+h-1,d),y(a,b,p,g,this.If),m=b;m<=p;m+=g)n=Math.min(m+g-1,p),l.children.push(this.Ug(a,m,n,f-1));e(l,this.xb);return l}, -Yj:function(a,b,d,e){for(var f,g,h,l,m,n,q,r;;){e.push(b);if(b.gb||e.length-1===d)break;q=r=Infinity;f=0;for(g=b.children.length;f<g;f++)h=b.children[f],m=p(h),n=(Math.max(h.ba,a.ba)-Math.min(h.da,a.da))*(Math.max(h.ja,a.ja)-Math.min(h.ga,a.ga))-m,n<r?(r=n,q=m<q?m:q,l=h):n===r&&m<q&&(q=m,l=h);b=l||b.children[0]}return b},Wg:function(a,b,d){var e=this.xb;d=d?a:e(a);var e=[],f=this.Yj(d,this.data,b,e);f.children.push(a);for(l(f,d);0<=b;)if(e[b].children.length>this.Df)this.fk(e,b),b--;else break;this.Vj(d, -e,b)},fk:function(a,b){var d=a[b],f=d.children.length,g=this.Xg;this.Wj(d,g,f);f=this.Xj(d,g,f);f=x(d.children.splice(f,d.children.length-f));f.height=d.height;f.gb=d.gb;e(d,this.xb);e(f,this.xb);b?a[b-1].children.push(f):this.Zg(d,f)},Zg:function(a,b){this.data=x([a,b]);this.data.height=a.height+1;this.data.gb=!1;e(this.data,this.xb)},Xj:function(a,b,d){var e,f,g,l,m,n,q;m=n=Infinity;for(e=b;e<=d-b;e++)f=h(a,0,e,this.xb),g=h(a,e,d,this.xb),l=Math.max(0,Math.min(f.ba,g.ba)-Math.max(f.da,g.da))*Math.max(0, -Math.min(f.ja,g.ja)-Math.max(f.ga,g.ga)),f=p(f)+p(g),l<m?(m=l,q=e,n=f<n?f:n):l===m&&f<n&&(n=f,q=e);return q},Wj:function(a,b,d){var e=a.gb?this.Hf:m,f=a.gb?this.If:n,g=this.Tg(a,b,d,e);b=this.Tg(a,b,d,f);g<b&&a.children.sort(e)},Tg:function(a,b,d,e){a.children.sort(e);e=this.xb;var f=h(a,0,b,e),g=h(a,d-b,d,e),m=q(f)+q(g),n,p;for(n=b;n<d-b;n++)p=a.children[n],l(f,a.gb?e(p):p),m+=q(f);for(n=d-b-1;n>=b;n--)p=a.children[n],l(g,a.gb?e(p):p),m+=q(g);return m},Vj:function(a,b,d){for(;0<=d;d--)l(b[d],a)}, -Zj:function(a){for(var b=a.length-1,d;0<=b;b--)0===a[b].children.length?0<b?(d=a[b-1].children,d.splice(d.indexOf(a[b]),1)):this.clear():e(a[b],this.xb)},ak:function(a){var b=["return a"," - b",";"];this.Hf=new Function("a","b",b.join(a[0]));this.If=new Function("a","b",b.join(a[1]));this.xb=new Function("a","return {minX: a"+a[0]+", minY: a"+a[1]+", maxX: a"+a[2]+", maxY: a"+a[3]+"};")}}},{quickselect:1}]},{},[2])(2)});Cj=b.ma})();function Gj(a){this.b=Cj(a);this.a={}}k=Gj.prototype;k.Ea=function(a,b){var c={da:a[0],ga:a[1],ba:a[2],ja:a[3],value:b};this.b.Ea(c);this.a[w(b)]=c};k.load=function(a,b){for(var c=Array(b.length),d=0,e=b.length;d<e;d++){var f=a[d],g=b[d],f={da:f[0],ga:f[1],ba:f[2],ja:f[3],value:g};c[d]=f;this.a[w(g)]=f}this.b.load(c)};k.remove=function(a){a=w(a);var b=this.a[a];delete this.a[a];return null!==this.b.remove(b)}; -function Hj(a,b,c){var d=a.a[w(c)];$a([d.da,d.ga,d.ba,d.ja],b)||(a.remove(c),a.Ea(b,c))}function Ij(a){return a.b.all().map(function(a){return a.value})}function Jj(a,b){return a.b.search({da:b[0],ga:b[1],ba:b[2],ja:b[3]}).map(function(a){return a.value})}k.forEach=function(a,b){return Kj(Ij(this),a,b)};function Lj(a,b,c,d){return Kj(Jj(a,b),c,d)}function Kj(a,b,c){for(var d,e=0,f=a.length;e<f&&!(d=b.call(c,a[e]));e++);return d}k.clear=function(){this.b.clear();this.a={}}; -k.D=function(a){var b=this.b.data;return Wa(b.da,b.ga,b.ba,b.ja,a)};function Mj(a,b){si.call(this,0,b);this.j=new $i(0,b);this.v=null;this.O=[];this.c=[];this.l={fillColor:null,s:!1}}u(Mj,si);function Nj(a,b,c,d){var e=new uj,f=new Gj;b=Oj(a,b,d,e,f,!0);if(c.length){var g,h,l=[];g=0;for(h=c.length;g<h;++g){var m={list:new uj,ba:void 0};l.push(m);m.ba=Oj(a,c[g],d,m.list,f,!1)}l.sort(function(a,b){return b.ba-a.ba});for(g=0;g<l.length;++g)Pj(l[g].list,l[g].ba,e,b,f)}Qj(e,f,!1);Rj(a,e,f)} -function Oj(a,b,c,d,e,f){var g,h,l=a.a.length/2,m,n,p,q=[],r=[];if(f===Pf(b,0,b.length,c))for(n=m=Sj(a,b[0],b[1],l++),f=b[0],g=c,h=b.length;g<h;g+=c)p=Sj(a,b[g],b[g+1],l++),r.push(Tj(n,p,d)),q.push([Math.min(n.x,p.x),Math.min(n.y,p.y),Math.max(n.x,p.x),Math.max(n.y,p.y)]),f=b[g]>f?b[g]:f,n=p;else for(g=b.length-c,n=m=Sj(a,b[g],b[g+1],l++),f=b[g],g-=c,h=0;g>=h;g-=c)p=Sj(a,b[g],b[g+1],l++),r.push(Tj(n,p,d)),q.push([Math.min(n.x,p.x),Math.min(n.y,p.y),Math.max(n.x,p.x),Math.max(n.y,p.y)]),f=b[g]>f?b[g]: -f,n=p;r.push(Tj(p,m,d));q.push([Math.min(n.x,p.x),Math.min(n.y,p.y),Math.max(n.x,p.x),Math.max(n.y,p.y)]);e.load(q,r);return f}function Qj(a,b,c){var d=wj(a),e=d,f=xj(a),g=!1;do{var h=c?yi(f.X.x,f.X.y,e.X.x,e.X.y,e.aa.x,e.aa.y):yi(e.aa.x,e.aa.y,e.X.x,e.X.y,f.X.x,f.X.y);void 0===h?(Uj(e,f,a,b),g=!0,f===d&&(d=yj(a)),f=e,zj(a)):e.X.vb!==h&&(e.X.vb=h,g=!0);e=f;f=xj(a)}while(e!==d);return g} -function Pj(a,b,c,d,e){Qj(a,e,!0);for(var f=wj(a);f.X.x!==b;)f=xj(a);b=f.X;d={x:d,y:b.y,fb:-1};var g=Infinity,h,l,m,n;m=Vj({aa:b,X:d},e,!0);h=0;for(l=m.length;h<l;++h){var p=m[h];if(void 0===p.aa.vb){var q=Wj(b,d,p.aa,p.X,!0),r=Math.abs(b.x-q[0]);r<g&&(g=r,n={x:q[0],y:q[1],fb:-1},f=p)}}if(Infinity!==g){m=f.X;if(0<g&&(f=Xj(b,n,f.X,e),f.length))for(n=Infinity,h=0,l=f.length;h<l;++h)if(g=f[h],p=Math.atan2(b.y-g.y,d.x-g.x),p<n||p===n&&g.x<m.x)n=p,m=g;for(f=wj(c);f.X!==m;)f=xj(c);d={x:b.x,y:b.y,fb:b.fb, -vb:void 0};h={x:f.X.x,y:f.X.y,fb:f.X.fb,vb:void 0};yj(a).aa=d;Tj(b,f.X,a,e);Tj(h,d,a,e);f.X=h;a.i&&a.b&&(a.g=a.b,a.a=a.b.ub);c.concat(a)}} -function Rj(a,b,c){for(var d=!1,e=Yj(b,c);3<b.c;)if(e){if(!Zj(a,b,c,e,d)&&!Qj(b,c,d)&&!ak(a,b,c,!0))break}else if(!Zj(a,b,c,e,d)&&!Qj(b,c,d)&&!ak(a,b,c))if(e=Yj(b,c)){var d=b,f=2*d.c,g=Array(f),h=wj(d),l=h,m=0;do g[m++]=l.aa.x,g[m++]=l.aa.y,l=xj(d);while(l!==h);d=!Pf(g,0,f,2);Qj(b,c,d)}else{e=a;d=b;f=g=wj(d);do{h=Vj(f,c);if(h.length){g=h[0];h=Wj(f.aa,f.X,g.aa,g.X);h=Sj(e,h[0],h[1],e.a.length/2);l=new uj;m=new Gj;Tj(h,f.X,l,m);f.X=h;Hj(c,[Math.min(f.aa.x,h.x),Math.min(f.aa.y,h.y),Math.max(f.aa.x,h.x), -Math.max(f.aa.y,h.y)],f);for(f=xj(d);f!==g;)Tj(f.aa,f.X,l,m),c.remove(f),vj(d),f=Bj(d);Tj(g.aa,h,l,m);g.aa=h;Hj(c,[Math.min(g.X.x,h.x),Math.min(g.X.y,h.y),Math.max(g.X.x,h.x),Math.max(g.X.y,h.y)],g);Qj(d,c,!1);Rj(e,d,c);Qj(l,m,!1);Rj(e,l,m);break}f=xj(d)}while(f!==g);break}3===b.c&&(e=a.b.length,a.b[e++]=Aj(b).aa.fb,a.b[e++]=Bj(b).aa.fb,a.b[e++]=yj(b).aa.fb)} -function Zj(a,b,c,d,e){var f=a.b.length,g=wj(b),h=Aj(b),l=g,m=xj(b),n=yj(b),p,q,r,v=!1;do{p=l.aa;q=l.X;r=m.X;if(!1===q.vb){var x=e?bk(n.X,r,q,p,h.aa):bk(h.aa,p,q,r,n.X);!d&&Vj({aa:p,X:r},c).length||!x||Xj(p,q,r,c,!0).length||!d&&!1!==p.vb&&!1!==r.vb&&Pf([h.aa.x,h.aa.y,p.x,p.y,q.x,q.y,r.x,r.y,n.X.x,n.X.y],0,10,2)!==!e||(a.b[f++]=p.fb,a.b[f++]=q.fb,a.b[f++]=r.fb,Uj(l,m,b,c),m===g&&(g=n),v=!0)}h=Aj(b);l=Bj(b);m=xj(b);n=yj(b)}while(l!==g&&3<b.c);return v} -function ak(a,b,c,d){var e=wj(b);xj(b);var f=e,g=xj(b),h=!1;do{var l=Wj(f.aa,f.X,g.aa,g.X,d);if(l){var m,h=a.b.length,n=a.a.length/2,p=zj(b);vj(b);c.remove(p);m=p===e;d?(l[0]===f.aa.x&&l[1]===f.aa.y?(zj(b),l=f.aa,g.aa=l,c.remove(f),m=m||f===e):(l=g.X,f.X=l,c.remove(g),m=m||g===e),vj(b)):(l=Sj(a,l[0],l[1],n),f.X=l,g.aa=l,Hj(c,[Math.min(f.aa.x,f.X.x),Math.min(f.aa.y,f.X.y),Math.max(f.aa.x,f.X.x),Math.max(f.aa.y,f.X.y)],f),Hj(c,[Math.min(g.aa.x,g.X.x),Math.min(g.aa.y,g.X.y),Math.max(g.aa.x,g.X.x),Math.max(g.aa.y, -g.X.y)],g));a.b[h++]=p.aa.fb;a.b[h++]=p.X.fb;a.b[h++]=l.fb;h=!0;if(m)break}f=Aj(b);g=xj(b)}while(f!==e);return h}function Yj(a,b){var c=wj(a),d=c;do{if(Vj(d,b).length)return!1;d=xj(a)}while(d!==c);return!0}function Sj(a,b,c,d){var e=a.a.length;a.a[e++]=b;a.a[e++]=c;return{x:b,y:c,fb:d,vb:void 0}} -function Tj(a,b,c,d){var e={aa:a,X:b},f={ub:void 0,next:void 0,data:e},g=c.b;if(g){var h=g.next;f.ub=g;f.next=h;g.next=f;h&&(h.ub=f);g===c.a&&(c.a=f)}else c.g=f,c.a=f,c.i&&(f.next=f,f.ub=f);c.b=f;c.c++;d&&d.Ea([Math.min(a.x,b.x),Math.min(a.y,b.y),Math.max(a.x,b.x),Math.max(a.y,b.y)],e);return e}function Uj(a,b,c,d){Bj(c)===b&&(vj(c),a.X=b.X,d.remove(b),Hj(d,[Math.min(a.aa.x,a.X.x),Math.min(a.aa.y,a.X.y),Math.max(a.aa.x,a.X.x),Math.max(a.aa.y,a.X.y)],a))} -function Xj(a,b,c,d,e){var f,g,h,l=[],m=Jj(d,[Math.min(a.x,b.x,c.x),Math.min(a.y,b.y,c.y),Math.max(a.x,b.x,c.x),Math.max(a.y,b.y,c.y)]);d=0;for(f=m.length;d<f;++d)for(g in m[d])h=m[d][g],"object"!==typeof h||e&&!h.vb||h.x===a.x&&h.y===a.y||h.x===b.x&&h.y===b.y||h.x===c.x&&h.y===c.y||-1!==l.indexOf(h)||!Jf([a.x,a.y,b.x,b.y,c.x,c.y],0,6,2,h.x,h.y)||l.push(h);return l} -function Vj(a,b,c){var d=a.aa,e=a.X;b=Jj(b,[Math.min(d.x,e.x),Math.min(d.y,e.y),Math.max(d.x,e.x),Math.max(d.y,e.y)]);var f=[],g,h;g=0;for(h=b.length;g<h;++g){var l=b[g];a!==l&&(c||l.aa!==e||l.X!==d)&&Wj(d,e,l.aa,l.X,c)&&f.push(l)}return f} -function Wj(a,b,c,d,e){var f=(d.y-c.y)*(b.x-a.x)-(d.x-c.x)*(b.y-a.y);if(f&&(d=((d.x-c.x)*(a.y-c.y)-(d.y-c.y)*(a.x-c.x))/f,c=((b.x-a.x)*(a.y-c.y)-(b.y-a.y)*(a.x-c.x))/f,!e&&d>zi&&d<1-zi&&c>zi&&c<1-zi||e&&0<=d&&1>=d&&0<=c&&1>=c))return[a.x+d*(b.x-a.x),a.y+d*(b.y-a.y)]} -function bk(a,b,c,d,e){if(void 0===b.vb||void 0===d.vb)return!1;var f=(c.x-d.x)*(b.y-d.y)>(c.y-d.y)*(b.x-d.x);e=(e.x-d.x)*(b.y-d.y)<(e.y-d.y)*(b.x-d.x);a=(a.x-b.x)*(d.y-b.y)>(a.y-b.y)*(d.x-b.x);c=(c.x-b.x)*(d.y-b.y)<(c.y-b.y)*(d.x-b.x);b=b.vb?c||a:c&&a;return(d.vb?e||f:e&&f)&&b}k=Mj.prototype; -k.rc=function(a,b){var c=a.md(),d=a.sa(),e=this.b.length,f=this.j.b.length,g,h,l,m;g=0;for(h=c.length;g<h;++g){var n=c[g].Oc();if(0<n.length){var p=n[0].ia(),p=nf(p,p.length,d,-this.origin[0],-this.origin[1]),q=[],r;l=1;for(m=n.length;l<m;++l)r=n[l].ia(),r=nf(r,r.length,d,-this.origin[0],-this.origin[1]),q.push(r);lj(this.j,p,q,d);Nj(this,p,q,d)}}this.b.length>e&&(this.g.push(e),this.f.push(b),this.l.s&&(this.c.push(e),this.l.s=!1));this.j.b.length>f&&mj(this.j,b,f)}; -k.tc=function(a,b){var c=a.Oc(),d=a.sa();if(0<c.length){this.g.push(this.b.length);this.f.push(b);this.l.s&&(this.c.push(this.b.length),this.l.s=!1);mj(this.j,b);var e=c[0].ia(),e=nf(e,e.length,d,-this.origin[0],-this.origin[1]),f=[],g,h,l;g=1;for(h=c.length;g<h;++g)l=c[g].ia(),l=nf(l,l.length,d,-this.origin[0],-this.origin[1]),f.push(l);lj(this.j,e,f,d);Nj(this,e,f,d)}}; -k.Bb=function(a){this.u=new Ai(this.a);this.o=new Ai(this.b);this.g.push(this.b.length);this.j.Bb(a);!this.c.length&&0<this.O.length&&(this.O=[]);this.b=this.a=null};k.Cb=function(a){var b=this.u,c=this.o,d=this.j.Cb(a);return function(){Di(a,b);Di(a,c);d()}};k.qf=function(a,b){var c=Ei(b,pj,rj),d;this.v?d=this.v:this.v=d=new sj(a,c);b.Vc(c);a.enableVertexAttribArray(d.b);a.vertexAttribPointer(d.b,2,5126,!1,8,0);return d};k.rf=function(a,b){a.disableVertexAttribArray(b.b)}; -k.Pd=function(a,b,c,d){var e=a.getParameter(a.DEPTH_FUNC),f=a.getParameter(a.DEPTH_WRITEMASK);d||(a.enable(a.DEPTH_TEST),a.depthMask(!0),a.depthFunc(a.NOTEQUAL));if(tb(c)){var g,h,l;h=this.g[this.g.length-1];for(c=this.c.length-1;0<=c;--c)g=this.c[c],l=this.O[c],a.uniform4fv(this.v.G,l),ui(a,b,g,h),h=g}else{var m,n,p,q;p=this.g.length-2;l=h=this.g[p+1];for(g=this.c.length-1;0<=g;--g){m=this.O[g];a.uniform4fv(this.v.G,m);for(m=this.c[g];0<=p&&this.g[p]>=m;)q=this.g[p],n=this.f[p],n=w(n).toString(), -c[n]&&(h!==l&&(ui(a,b,h,l),a.clear(a.DEPTH_BUFFER_BIT)),l=q),p--,h=q;h!==l&&(ui(a,b,h,l),a.clear(a.DEPTH_BUFFER_BIT));h=l=m}}d||(a.disable(a.DEPTH_TEST),a.clear(a.DEPTH_BUFFER_BIT),a.depthMask(f),a.depthFunc(e))}; -k.ve=function(a,b,c,d,e){var f,g,h,l,m,n,p;p=this.g.length-2;h=this.g[p+1];for(f=this.c.length-1;0<=f;--f)for(g=this.O[f],a.uniform4fv(this.v.G,g),l=this.c[f];0<=p&&this.g[p]>=l;){g=this.g[p];m=this.f[p];n=w(m).toString();if(void 0===c[n]&&m.U()&&(void 0===e||nb(e,m.U().D()))&&(a.clear(a.COLOR_BUFFER_BIT|a.DEPTH_BUFFER_BIT),ui(a,b,g,h),h=d(m)))return h;p--;h=g}}; -k.Na=function(a,b){var c=a?a.b:[0,0,0,0];c instanceof CanvasGradient||c instanceof CanvasPattern?c=vi:c=bd(c).map(function(a,b){return 3!=b?a/255:a})||vi;this.l.fillColor&&ja(c,this.l.fillColor)||(this.l.fillColor=c,this.l.s=!0,this.O.push(c));b?this.j.Na(null,b):this.j.Na(null,new tj({color:[0,0,0,0],lineWidth:0}))};function ck(){}ck.prototype.i=function(){};function dk(a,b,c){this.f=b;this.j=a;this.c=c;this.a={}}u(dk,hi);function ek(a,b){var c=[],d;for(d in a.a){var e=a.a[d],f;for(f in e)c.push(e[f].Cb(b))}return function(){for(var a=c.length,b,d=0;d<a;d++)b=c[d].apply(this,arguments);return b}}function fk(a,b){for(var c in a.a){var d=a.a[c],e;for(e in d)d[e].Bb(b)}}dk.prototype.b=function(a,b){var c=void 0!==a?a.toString():"0",d=this.a[c];void 0===d&&(d={},this.a[c]=d);c=d[b];void 0===c&&(c=new gk[b](this.j,this.f),d[b]=c);return c}; -dk.prototype.g=function(){return tb(this.a)};dk.prototype.i=function(a,b,c,d,e,f,g,h){var l=Object.keys(this.a).map(Number);l.sort(ea);var m,n,p,q,r,v;m=0;for(n=l.length;m<n;++m)for(r=this.a[l[m].toString()],p=0,q=gi.length;p<q;++p)v=r[gi[p]],void 0!==v&&v.i(a,b,c,d,e,f,g,h,void 0,!1)}; -function hk(a,b,c,d,e,f,g,h,l,m,n){var p=ik,q=Object.keys(a.a).map(Number);q.sort(function(a,b){return b-a});var r,v,x,y,A;r=0;for(v=q.length;r<v;++r)for(y=a.a[q[r].toString()],x=gi.length-1;0<=x;--x)if(A=y[gi[x]],void 0!==A&&(A=A.i(b,c,d,e,p,f,g,h,l,m,n)))return A} -dk.prototype.Ba=function(a,b,c,d,e,f,g,h,l,m){var n=b.b;n.bindFramebuffer(n.FRAMEBUFFER,Mi(b));var p;void 0!==this.c&&(p=Ma(Xa(a),d*this.c));return hk(this,b,a,d,e,g,h,l,function(a){var b=new Uint8Array(4);n.readPixels(0,0,1,1,n.RGBA,n.UNSIGNED_BYTE,b);if(0<b[3]&&(a=m(a)))return a},!0,p)}; -function jk(a,b,c,d,e,f,g,h){var l=c.b;l.bindFramebuffer(l.FRAMEBUFFER,Mi(c));return void 0!==hk(a,c,b,d,e,f,g,h,function(){var a=new Uint8Array(4);l.readPixels(0,0,1,1,l.RGBA,l.UNSIGNED_BYTE,a);return 0<a[3]},!1)}var ik=[1,1],gk={Circle:Ci,Image:Ri,LineString:$i,Polygon:Mj,Text:ck};function kk(a,b,c,d,e,f,g){this.b=a;this.g=b;this.a=f;this.c=g;this.j=e;this.f=d;this.i=c;this.l=this.o=this.u=null}u(kk,Th);k=kk.prototype;k.td=function(a){this.Na(a.Ca(),a.Da());this.Wb(a.Y())}; -k.oc=function(a){switch(a.S()){case "Point":this.sc(a,null);break;case "LineString":this.Rb(a,null);break;case "Polygon":this.tc(a,null);break;case "MultiPoint":this.qc(a,null);break;case "MultiLineString":this.pc(a,null);break;case "MultiPolygon":this.rc(a,null);break;case "GeometryCollection":this.ue(a,null);break;case "Circle":this.ac(a,null)}};k.te=function(a,b){var c=(0,b.Qa)(a);c&&nb(this.a,c.D())&&(this.td(b),this.oc(c))};k.ue=function(a){a=a.a;var b,c;b=0;for(c=a.length;b<c;++b)this.oc(a[b])}; -k.sc=function(a,b){var c=this.b,d=(new dk(1,this.a)).b(0,"Image");d.Wb(this.u);d.sc(a,b);d.Bb(c);d.i(this.b,this.g,this.i,this.f,this.j,this.c,1,{},void 0,!1);d.Cb(c)()};k.qc=function(a,b){var c=this.b,d=(new dk(1,this.a)).b(0,"Image");d.Wb(this.u);d.qc(a,b);d.Bb(c);d.i(this.b,this.g,this.i,this.f,this.j,this.c,1,{},void 0,!1);d.Cb(c)()}; -k.Rb=function(a,b){var c=this.b,d=(new dk(1,this.a)).b(0,"LineString");d.Na(null,this.l);d.Rb(a,b);d.Bb(c);d.i(this.b,this.g,this.i,this.f,this.j,this.c,1,{},void 0,!1);d.Cb(c)()};k.pc=function(a,b){var c=this.b,d=(new dk(1,this.a)).b(0,"LineString");d.Na(null,this.l);d.pc(a,b);d.Bb(c);d.i(this.b,this.g,this.i,this.f,this.j,this.c,1,{},void 0,!1);d.Cb(c)()}; -k.tc=function(a,b){var c=this.b,d=(new dk(1,this.a)).b(0,"Polygon");d.Na(this.o,this.l);d.tc(a,b);d.Bb(c);d.i(this.b,this.g,this.i,this.f,this.j,this.c,1,{},void 0,!1);d.Cb(c)()};k.rc=function(a,b){var c=this.b,d=(new dk(1,this.a)).b(0,"Polygon");d.Na(this.o,this.l);d.rc(a,b);d.Bb(c);d.i(this.b,this.g,this.i,this.f,this.j,this.c,1,{},void 0,!1);d.Cb(c)()}; -k.ac=function(a,b){var c=this.b,d=(new dk(1,this.a)).b(0,"Circle");d.Na(this.o,this.l);d.ac(a,b);d.Bb(c);d.i(this.b,this.g,this.i,this.f,this.j,this.c,1,{},void 0,!1);d.Cb(c)()};k.Wb=function(a){this.u=a};k.Na=function(a,b){this.o=a;this.l=b};function lk(){this.c=0;this.b={};this.g=this.a=null}k=lk.prototype;k.clear=function(){this.c=0;this.b={};this.g=this.a=null};k.forEach=function(a,b){for(var c=this.a;c;)a.call(b,c.cd,c.wc,this),c=c.Mb};k.get=function(a){a=this.b[a];sa(!!a,15);if(a===this.g)return a.cd;a===this.a?(this.a=this.a.Mb,this.a.xd=null):(a.Mb.xd=a.xd,a.xd.Mb=a.Mb);a.Mb=null;a.xd=this.g;this.g=this.g.Mb=a;return a.cd}; -k.pop=function(){var a=this.a;delete this.b[a.wc];a.Mb&&(a.Mb.xd=null);this.a=a.Mb;this.a||(this.g=null);--this.c;return a.cd};k.replace=function(a,b){this.get(a);this.b[a].cd=b};k.set=function(a,b){sa(!(a in this.b),16);var c={wc:a,Mb:null,xd:this.g,cd:b};this.g?this.g.Mb=c:this.a=c;this.g=c;this.b[a]=c;++this.c};function mk(a,b){Jh.call(this,0,b);this.b=document.createElement("CANVAS");this.b.style.width="100%";this.b.style.height="100%";this.b.style.display="block";this.b.className="ol-unselectable";a.insertBefore(this.b,a.childNodes[0]||null);this.O=this.A=0;this.C=hd();this.o=!0;this.g=Md(this.b,{antialias:!0,depth:!0,failIfMajorPerformanceCaveat:!0,preserveDrawingBuffer:!1,stencil:!0});this.i=new Li(this.b,this.g);z(this.b,"webglcontextlost",this.On,this);z(this.b,"webglcontextrestored",this.Pn,this); -this.a=new lk;this.v=null;this.j=new Ie(function(a){var b=a[1];a=a[2];var c=b[0]-this.v[0],b=b[1]-this.v[1];return 65536*Math.log(a)+Math.sqrt(c*c+b*b)/a}.bind(this),function(a){return a[0].hb()});this.G=function(){if(this.j.b.length){Me(this.j);var a=Je(this.j);nk(this,a[0],a[3],a[4])}return!1}.bind(this);this.f=0;ok(this)}u(mk,Jh); -function nk(a,b,c,d){var e=a.g,f=b.hb();if(a.a.b.hasOwnProperty(f))a=a.a.get(f),e.bindTexture(3553,a.Fb),9729!=a.Ih&&(e.texParameteri(3553,10240,9729),a.Ih=9729),9729!=a.Kh&&(e.texParameteri(3553,10241,9729),a.Kh=9729);else{var g=e.createTexture();e.bindTexture(3553,g);if(0<d){var h=a.C.canvas,l=a.C;a.A!==c[0]||a.O!==c[1]?(h.width=c[0],h.height=c[1],a.A=c[0],a.O=c[1]):l.clearRect(0,0,c[0],c[1]);l.drawImage(b.Y(),d,d,c[0],c[1],0,0,c[0],c[1]);e.texImage2D(3553,0,6408,6408,5121,h)}else e.texImage2D(3553, -0,6408,6408,5121,b.Y());e.texParameteri(3553,10240,9729);e.texParameteri(3553,10241,9729);e.texParameteri(3553,10242,33071);e.texParameteri(3553,10243,33071);a.a.set(f,{Fb:g,Ih:9729,Kh:9729})}}function pk(a,b,c){var d=a.l;if(Oc(d,b)){a=a.i;var e=c.viewState;d.b(new Oh(b,new kk(a,e.center,e.resolution,e.rotation,c.size,c.extent,c.pixelRatio),c,null,a))}}k=mk.prototype;k.ra=function(){var a=this.g;a.isContextLost()||this.a.forEach(function(b){b&&a.deleteTexture(b.Fb)});Kc(this.i);Jh.prototype.ra.call(this)}; -k.tk=function(a,b){for(var c=this.g,d;1024<this.a.c-this.f;){if(d=this.a.a.cd)c.deleteTexture(d.Fb);else if(+this.a.a.wc==b.index)break;else--this.f;this.a.pop()}};k.S=function(){return"webgl"};k.On=function(a){a.preventDefault();this.a.clear();this.f=0;a=this.c;for(var b in a)a[b].hg()};k.Pn=function(){ok(this);this.l.render()};function ok(a){a=a.g;a.activeTexture(33984);a.blendFuncSeparate(770,771,1,771);a.disable(2884);a.disable(2929);a.disable(3089);a.disable(2960)} -k.Dg=function(a){var b=this.i,c=this.g;if(c.isContextLost())return!1;if(!a)return this.o&&(this.b.style.display="none",this.o=!1),!1;this.v=a.focus;this.a.set((-a.index).toString(),null);++this.f;pk(this,"precompose",a);var d=[],e=a.layerStatesArray;ka(e);var f=a.viewState.resolution,g,h,l,m;g=0;for(h=e.length;g<h;++g)m=e[g],uh(m,f)&&"ready"==m.uj&&(l=Mh(this,m.layer),l.ig(a,m,b)&&d.push(m));e=a.size[0]*a.pixelRatio;f=a.size[1]*a.pixelRatio;if(this.b.width!=e||this.b.height!=f)this.b.width=e,this.b.height= -f;c.bindFramebuffer(36160,null);c.clearColor(0,0,0,0);c.clear(16384);c.enable(3042);c.viewport(0,0,this.b.width,this.b.height);g=0;for(h=d.length;g<h;++g)m=d[g],l=Mh(this,m.layer),l.zi(a,m,b);this.o||(this.b.style.display="",this.o=!0);Kh(a);1024<this.a.c-this.f&&a.postRenderFunctions.push(this.tk.bind(this));this.j.b.length&&(a.postRenderFunctions.push(this.G),a.animate=!0);pk(this,"postcompose",a);Nh(this,a);a.postRenderFunctions.push(Lh)}; -k.Ba=function(a,b,c,d,e,f,g){var h;if(this.g.isContextLost())return!1;var l=b.viewState,m=b.layerStatesArray,n;for(n=m.length-1;0<=n;--n){h=m[n];var p=h.layer;if(uh(h,l.resolution)&&f.call(g,p)&&(h=Mh(this,p).Ba(a,b,c,d,e)))return h}};k.xi=function(a,b,c,d,e){c=!1;if(this.g.isContextLost())return!1;var f=b.viewState,g=b.layerStatesArray,h;for(h=g.length-1;0<=h;--h){var l=g[h],m=l.layer;if(uh(l,f.resolution)&&d.call(e,m)&&(c=Mh(this,m).Te(a,b)))return!0}return c}; -k.wi=function(a,b,c,d,e){if(this.g.isContextLost())return!1;var f=b.viewState,g,h=b.layerStatesArray,l;for(l=h.length-1;0<=l;--l){g=h[l];var m=g.layer;if(uh(g,f.resolution)&&e.call(d,m)&&(g=Mh(this,m).gg(a,b,c,d)))return g}};var qk=["canvas","webgl"]; -function H(a){Qc.call(this);var b=rk(a);this.yf=void 0!==a.loadTilesWhileAnimating?a.loadTilesWhileAnimating:!1;this.zf=void 0!==a.loadTilesWhileInteracting?a.loadTilesWhileInteracting:!1;this.Ef=void 0!==a.pixelRatio?a.pixelRatio:Td;this.wf=b.logos;this.fa=function(){this.f=void 0;this.Ip.call(this,Date.now())}.bind(this);this.Gb=yh();this.Ff=yh();this.le=0;this.a=null;this.yb=Ja();this.G=this.I=this.Z=null;this.c=document.createElement("DIV");this.c.className="ol-viewport"+(Yd?" ol-touch":"");this.c.style.position= -"relative";this.c.style.overflow="hidden";this.c.style.width="100%";this.c.style.height="100%";this.c.style.msTouchAction="none";this.c.style.touchAction="none";this.A=document.createElement("DIV");this.A.className="ol-overlaycontainer";this.c.appendChild(this.A);this.v=document.createElement("DIV");this.v.className="ol-overlaycontainer-stopevent";a="click dblclick mousedown touchstart MSPointerDown pointerdown mousewheel wheel".split(" ");for(var c=0,d=a.length;c<d;++c)z(this.v,a[c],Mc);this.c.appendChild(this.v); -this.Ja=new Fe(this);for(var e in Id)z(this.Ja,Id[e],this.Bh,this);this.na=b.keyboardEventTarget;this.u=null;z(this.c,"wheel",this.pd,this);z(this.c,"mousewheel",this.pd,this);this.l=b.controls;this.j=b.interactions;this.o=b.overlays;this.lg={};this.C=new b.Kp(this.c,this);this.T=null;this.Va=[];this.Ha=new Ne(this.ll.bind(this),this.Rl.bind(this));this.ea={};z(this,Sc("layergroup"),this.zl,this);z(this,Sc("view"),this.Sl,this);z(this,Sc("size"),this.Ol,this);z(this,Sc("target"),this.Ql,this);this.H(b.values); -this.l.forEach(function(a){a.setMap(this)},this);z(this.l,"add",function(a){a.element.setMap(this)},this);z(this.l,"remove",function(a){a.element.setMap(null)},this);this.j.forEach(function(a){a.setMap(this)},this);z(this.j,"add",function(a){a.element.setMap(this)},this);z(this.j,"remove",function(a){a.element.setMap(null)},this);this.o.forEach(this.bh,this);z(this.o,"add",function(a){this.bh(a.element)},this);z(this.o,"remove",function(a){var b=a.element.f;void 0!==b&&delete this.lg[b.toString()]; -a.element.setMap(null)},this)}u(H,Qc);k=H.prototype;k.gk=function(a){this.l.push(a)};k.hk=function(a){this.j.push(a)};k.$g=function(a){this.Mc().sd().push(a)};k.ah=function(a){this.o.push(a)};k.bh=function(a){var b=a.f;void 0!==b&&(this.lg[b.toString()]=a);a.setMap(this)}; -k.ra=function(){Kc(this.Ja);Kc(this.C);Hc(this.c,"wheel",this.pd,this);Hc(this.c,"mousewheel",this.pd,this);this.i&&(window.removeEventListener("resize",this.i,!1),this.i=void 0);this.f&&(cancelAnimationFrame(this.f),this.f=void 0);this.Ke(null);Qc.prototype.ra.call(this)};k.we=function(a,b,c){if(this.a)return a=this.Xa(a),c=c?c:{},this.C.Ba(a,this.a,void 0!==c.hitTolerance?c.hitTolerance*this.a.pixelRatio:0,b,null,c.layerFilter?c.layerFilter:jf,null)}; -k.Em=function(a,b,c,d,e){if(this.a)return this.C.wi(a,this.a,b,void 0!==c?c:null,d?d:jf,void 0!==e?e:null)};k.Tl=function(a,b){if(!this.a)return!1;var c=this.Xa(a);b=b?b:{};return this.C.xi(c,this.a,void 0!==b.hitTolerance?b.hitTolerance*this.a.pixelRatio:0,b.layerFilter?b.layerFilter:jf,null)};k.Of=function(a){return this.Xa(this.xe(a))};k.xe=function(a){var b=this.c.getBoundingClientRect();a=a.changedTouches?a.changedTouches[0]:a;return[a.clientX-b.left,a.clientY-b.top]};k.Wf=function(){return this.get("target")}; -k.vc=function(){var a=this.Wf();return void 0!==a?"string"===typeof a?document.getElementById(a):a:null};k.Xa=function(a){var b=this.a;return b?Dh(b.pixelToCoordinateTransform,a.slice()):null};k.Hk=function(){return this.l};k.al=function(){return this.o};k.$k=function(a){a=this.lg[a.toString()];return void 0!==a?a:null};k.Nk=function(){return this.j};k.Mc=function(){return this.get("layergroup")};k.Qh=function(){return this.Mc().sd()}; -k.Ka=function(a){var b=this.a;return b?Dh(b.coordinateToPixelTransform,a.slice(0,2)):null};k.Nb=function(){return this.get("size")};k.$=function(){return this.get("view")};k.nl=function(){return this.c};k.ll=function(a,b,c,d){var e=this.a;if(!(e&&b in e.wantedTiles&&e.wantedTiles[b][a.hb()]))return Infinity;a=c[0]-e.focus[0];c=c[1]-e.focus[1];return 65536*Math.log(d)+Math.sqrt(a*a+c*c)/d};k.pd=function(a,b){var c=new Hd(b||a.type,this,a);this.Bh(c)}; -k.Bh=function(a){if(this.a){this.T=a.coordinate;a.frameState=this.a;var b=this.j.a,c;if(!1!==this.b(a))for(c=b.length-1;0<=c;c--){var d=b[c];if(d.c()&&!d.handleEvent(a))break}}};k.Ml=function(){var a=this.a,b=this.Ha;if(b.b.length){var c=16,d=c;if(a){var e=a.viewHints;e[0]&&(c=this.yf?8:0,d=2);e[1]&&(c=this.zf?8:0,d=2)}b.j<c&&(Me(b),Oe(b,c,d))}b=this.Va;c=0;for(d=b.length;c<d;++c)b[c](this,a);b.length=0};k.Ol=function(){this.render()}; -k.Ql=function(){var a;this.Wf()&&(a=this.vc());if(this.u){for(var b=0,c=this.u.length;b<c;++b)Bc(this.u[b]);this.u=null}a?(a.appendChild(this.c),a=this.na?this.na:a,this.u=[z(a,"keydown",this.pd,this),z(a,"keypress",this.pd,this)],this.i||(this.i=this.Cd.bind(this),window.addEventListener("resize",this.i,!1))):(jd(this.c),this.i&&(window.removeEventListener("resize",this.i,!1),this.i=void 0));this.Cd()};k.Rl=function(){this.render()};k.Eh=function(){this.render()}; -k.Sl=function(){this.Z&&(Bc(this.Z),this.Z=null);this.I&&(Bc(this.I),this.I=null);var a=this.$();a&&(this.c.setAttribute("data-view",w(a)),this.Z=z(a,"propertychange",this.Eh,this),this.I=z(a,"change",this.Eh,this));this.render()};k.zl=function(){this.G&&(this.G.forEach(Bc),this.G=null);var a=this.Mc();a&&(this.G=[z(a,"propertychange",this.render,this),z(a,"change",this.render,this)]);this.render()};k.Jp=function(){this.f&&cancelAnimationFrame(this.f);this.fa()}; -k.render=function(){void 0===this.f&&(this.f=requestAnimationFrame(this.fa))};k.Cp=function(a){return this.l.remove(a)};k.Dp=function(a){return this.j.remove(a)};k.Fp=function(a){return this.Mc().sd().remove(a)};k.Gp=function(a){return this.o.remove(a)}; -k.Ip=function(a){var b,c,d=this.Nb(),e=this.$(),f=Ja(),g=null;if(void 0!==d&&0<d[0]&&0<d[1]&&e&&hg(e)){var g=ag(e,this.a?this.a.viewHints:void 0),h=this.Mc().Tf(),l={};b=0;for(c=h.length;b<c;++b)l[w(h[b].layer)]=h[b];b=e.V();g={animate:!1,attributions:{},coordinateToPixelTransform:this.Gb,extent:f,focus:this.T?this.T:b.center,index:this.le++,layerStates:l,layerStatesArray:h,logos:qb({},this.wf),pixelRatio:this.Ef,pixelToCoordinateTransform:this.Ff,postRenderFunctions:[],size:d,skippedFeatureUids:this.ea, -tileQueue:this.Ha,time:a,usedTiles:{},viewState:b,viewHints:g,wantedTiles:{}}}g&&(g.extent=lb(b.center,b.resolution,b.rotation,g.size,f));this.a=g;this.C.Dg(g);g&&(g.animate&&this.render(),Array.prototype.push.apply(this.Va,g.postRenderFunctions),g.viewHints[0]||g.viewHints[1]||$a(g.extent,this.yb)||(this.b(new Gd("moveend",this,g)),Oa(g.extent,this.yb)));this.b(new Gd("postrender",this,g));setTimeout(this.Ml.bind(this),0)};k.lj=function(a){this.set("layergroup",a)}; -k.Ig=function(a){this.set("size",a)};k.Ke=function(a){this.set("target",a)};k.Yp=function(a){this.set("view",a)};k.tj=function(a){a=w(a).toString();this.ea[a]=!0;this.render()};k.Cd=function(){var a=this.vc();if(a){var b=getComputedStyle(a);this.Ig([a.offsetWidth-parseFloat(b.borderLeftWidth)-parseFloat(b.paddingLeft)-parseFloat(b.paddingRight)-parseFloat(b.borderRightWidth),a.offsetHeight-parseFloat(b.borderTopWidth)-parseFloat(b.paddingTop)-parseFloat(b.paddingBottom)-parseFloat(b.borderBottomWidth)])}else this.Ig(void 0)}; -k.yj=function(a){a=w(a).toString();delete this.ea[a];this.render()}; -function rk(a){var b=null;void 0!==a.keyboardEventTarget&&(b="string"===typeof a.keyboardEventTarget?document.getElementById(a.keyboardEventTarget):a.keyboardEventTarget);var c={},d={};if(void 0===a.logo||"boolean"===typeof a.logo&&a.logo)d["data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAMAAABEpIrGAAAAA3NCSVQICAjb4U/gAAAACXBIWXMAAAHGAAABxgEXwfpGAAAAGXRFWHRTb2Z0d2FyZQB3d3cuaW5rc2NhcGUub3Jnm+48GgAAAhNQTFRF////AP//AICAgP//AFVVQECA////K1VVSbbbYL/fJ05idsTYJFtbbcjbJllmZszWWMTOIFhoHlNiZszTa9DdUcHNHlNlV8XRIVdiasrUHlZjIVZjaMnVH1RlIFRkH1RkH1ZlasvYasvXVsPQH1VkacnVa8vWIVZjIFRjVMPQa8rXIVVkXsXRsNveIFVkIFZlIVVj3eDeh6GmbMvXH1ZkIFRka8rWbMvXIFVkIFVjIFVkbMvWH1VjbMvWIFVlbcvWIFVla8vVIFVkbMvWbMvVH1VkbMvWIFVlbcvWIFVkbcvVbMvWjNPbIFVkU8LPwMzNIFVkbczWIFVkbsvWbMvXIFVkRnB8bcvW2+TkW8XRIFVkIlZlJVloJlpoKlxrLl9tMmJwOWd0Omh1RXF8TneCT3iDUHiDU8LPVMLPVcLPVcPQVsPPVsPQV8PQWMTQWsTQW8TQXMXSXsXRX4SNX8bSYMfTYcfTYsfTY8jUZcfSZsnUaIqTacrVasrVa8jTa8rWbI2VbMvWbcvWdJObdcvUdszUd8vVeJaee87Yfc3WgJyjhqGnitDYjaarldPZnrK2oNbborW5o9bbo9fbpLa6q9ndrL3ArtndscDDutzfu8fJwN7gwt7gxc/QyuHhy+HizeHi0NfX0+Pj19zb1+Tj2uXk29/e3uLg3+Lh3+bl4uXj4ufl4+fl5Ofl5ufl5ujm5+jmySDnBAAAAFp0Uk5TAAECAgMEBAYHCA0NDg4UGRogIiMmKSssLzU7PkJJT1JTVFliY2hrdHZ3foSFhYeJjY2QkpugqbG1tre5w8zQ09XY3uXn6+zx8vT09vf4+Pj5+fr6/P39/f3+gz7SsAAAAVVJREFUOMtjYKA7EBDnwCPLrObS1BRiLoJLnte6CQy8FLHLCzs2QUG4FjZ5GbcmBDDjxJBXDWxCBrb8aM4zbkIDzpLYnAcE9VXlJSWlZRU13koIeW57mGx5XjoMZEUqwxWYQaQbSzLSkYGfKFSe0QMsX5WbjgY0YS4MBplemI4BdGBW+DQ11eZiymfqQuXZIjqwyadPNoSZ4L+0FVM6e+oGI6g8a9iKNT3o8kVzNkzRg5lgl7p4wyRUL9Yt2jAxVh6mQCogae6GmflI8p0r13VFWTHBQ0rWPW7ahgWVcPm+9cuLoyy4kCJDzCm6d8PSFoh0zvQNC5OjDJhQopPPJqph1doJBUD5tnkbZiUEqaCnB3bTqLTFG1bPn71kw4b+GFdpLElKIzRxxgYgWNYc5SCENVHKeUaltHdXx0dZ8uBI1hJ2UUDgq82CM2MwKeibqAvSO7MCABq0wXEPiqWEAAAAAElFTkSuQmCC"]="https://openlayers.org/"; -else{var e=a.logo;"string"===typeof e?d[e]="":e instanceof HTMLElement?d[w(e).toString()]=e:e&&(sa("string"==typeof e.href,44),sa("string"==typeof e.src,45),d[e.src]=e.href)}e=a.layers instanceof rh?a.layers:new rh({layers:a.layers});c.layergroup=e;c.target=a.target;c.view=void 0!==a.view?a.view:new G;var e=Jh,f;void 0!==a.renderer?(Array.isArray(a.renderer)?f=a.renderer:"string"===typeof a.renderer?f=[a.renderer]:sa(!1,46),0<=f.indexOf("dom")&&(f=f.concat(qk))):f=qk;var g,h;g=0;for(h=f.length;g< -h;++g){var l=f[g];if("canvas"==l){if(Vd){e=ei;break}}else if("webgl"==l&&Nd){e=mk;break}}void 0!==a.controls?Array.isArray(a.controls)?f=new D(a.controls.slice()):(sa(a.controls instanceof D,47),f=a.controls):f=vd();void 0!==a.interactions?Array.isArray(a.interactions)?g=new D(a.interactions.slice()):(sa(a.interactions instanceof D,48),g=a.interactions):g=oh();void 0!==a.overlays?Array.isArray(a.overlays)?a=new D(a.overlays.slice()):(sa(a.overlays instanceof D,49),a=a.overlays):a=new D;return{controls:f, -interactions:g,keyboardEventTarget:b,logos:d,overlays:a,Kp:e,values:c}};function sk(a){Qc.call(this);this.f=a.id;this.o=void 0!==a.insertFirst?a.insertFirst:!0;this.u=void 0!==a.stopEvent?a.stopEvent:!0;this.c=document.createElement("DIV");this.c.className="ol-overlay-container ol-selectable";this.c.style.position="absolute";this.autoPan=void 0!==a.autoPan?a.autoPan:!1;this.j=a.autoPanAnimation||{};this.l=void 0!==a.autoPanMargin?a.autoPanMargin:20;this.a={re:"",He:"",lf:"",uf:"",visible:!0};this.i=null;z(this,Sc(tk),this.ul,this);z(this,Sc(uk),this.El,this);z(this,Sc(vk), -this.Il,this);z(this,Sc(wk),this.Kl,this);z(this,Sc(xk),this.Ll,this);void 0!==a.element&&this.gj(a.element);this.nj(void 0!==a.offset?a.offset:[0,0]);this.qj(void 0!==a.positioning?a.positioning:"top-left");void 0!==a.position&&this.Me(a.position)}u(sk,Qc);k=sk.prototype;k.Rd=function(){return this.get(tk)};k.Fm=function(){return this.f};k.Le=function(){return this.get(uk)};k.wh=function(){return this.get(vk)};k.Rh=function(){return this.get(wk)};k.xh=function(){return this.get(xk)}; -k.ul=function(){for(var a=this.c;a.lastChild;)a.removeChild(a.lastChild);(a=this.Rd())&&this.c.appendChild(a)};k.El=function(){this.i&&(jd(this.c),Bc(this.i),this.i=null);var a=this.Le();a&&(this.i=z(a,"postrender",this.render,this),yk(this),a=this.u?a.v:a.A,this.o?a.insertBefore(this.c,a.childNodes[0]||null):a.appendChild(this.c))};k.render=function(){yk(this)};k.Il=function(){yk(this)}; -k.Kl=function(){yk(this);if(this.get(wk)&&this.autoPan){var a=this.Le();if(a&&a.vc()){var b=zk(a.vc(),a.Nb()),c=this.Rd(),d=c.offsetWidth,e=getComputedStyle(c),d=d+(parseInt(e.marginLeft,10)+parseInt(e.marginRight,10)),e=c.offsetHeight,f=getComputedStyle(c),e=e+(parseInt(f.marginTop,10)+parseInt(f.marginBottom,10)),g=zk(c,[d,e]),c=this.l;Ua(b,g)||(d=g[0]-b[0],e=b[2]-g[2],f=g[1]-b[1],g=b[3]-g[3],b=[0,0],0>d?b[0]=d-c:0>e&&(b[0]=Math.abs(e)+c),0>f?b[1]=f-c:0>g&&(b[1]=Math.abs(g)+c),0===b[0]&&0===b[1])|| -(c=a.$().za(),c=a.Ka(c),b=[c[0]+b[0],c[1]+b[1]],a.$().animate({center:a.Xa(b),duration:this.j.duration,easing:this.j.easing}))}}};k.Ll=function(){yk(this)};k.gj=function(a){this.set(tk,a)};k.setMap=function(a){this.set(uk,a)};k.nj=function(a){this.set(vk,a)};k.Me=function(a){this.set(wk,a)};function zk(a,b){var c=a.getBoundingClientRect(),d=c.left+window.pageXOffset,c=c.top+window.pageYOffset;return[d,c,d+b[0],c+b[1]]}k.qj=function(a){this.set(xk,a)}; -function Ak(a,b){a.a.visible!==b&&(a.c.style.display=b?"":"none",a.a.visible=b)} -function yk(a){var b=a.Le(),c=a.Rh();if(b&&b.a&&c){var c=b.Ka(c),d=b.Nb(),b=a.c.style,e=a.wh(),f=a.xh();Ak(a,!0);var g=e[0],e=e[1];if("bottom-right"==f||"center-right"==f||"top-right"==f)""!==a.a.He&&(a.a.He=b.left=""),g=Math.round(d[0]-c[0]-g)+"px",a.a.lf!=g&&(a.a.lf=b.right=g);else{""!==a.a.lf&&(a.a.lf=b.right="");if("bottom-center"==f||"center-center"==f||"top-center"==f)g-=a.c.offsetWidth/2;g=Math.round(c[0]+g)+"px";a.a.He!=g&&(a.a.He=b.left=g)}if("bottom-left"==f||"bottom-center"==f||"bottom-right"== -f)""!==a.a.uf&&(a.a.uf=b.top=""),c=Math.round(d[1]-c[1]-e)+"px",a.a.re!=c&&(a.a.re=b.bottom=c);else{""!==a.a.re&&(a.a.re=b.bottom="");if("center-left"==f||"center-center"==f||"center-right"==f)e-=a.c.offsetHeight/2;c=Math.round(c[1]+e)+"px";a.a.uf!=c&&(a.a.uf=b.top=c)}}else Ak(a,!1)}var tk="element",uk="map",vk="offset",wk="position",xk="positioning";function Bk(a){function b(a){a=h.Of(a);l.a.$().lb(a);window.removeEventListener("mousemove",c);window.removeEventListener("mouseup",b)}function c(a){a=h.Of({clientX:a.clientX-n.offsetWidth/2,clientY:a.clientY+n.offsetHeight/2});m.Me(a)}a=a?a:{};this.j=void 0!==a.collapsed?a.collapsed:!0;this.l=void 0!==a.collapsible?a.collapsible:!0;this.l||(this.j=!1);var d=void 0!==a.className?a.className:"ol-overviewmap",e=void 0!==a.tipLabel?a.tipLabel:"Overview map",f=void 0!==a.collapseLabel?a.collapseLabel: -"\u00ab";"string"===typeof f?(this.v=document.createElement("span"),this.v.textContent=f):this.v=f;f=void 0!==a.label?a.label:"\u00bb";"string"===typeof f?(this.A=document.createElement("span"),this.A.textContent=f):this.A=f;var g=this.l&&!this.j?this.v:this.A,f=document.createElement("button");f.setAttribute("type","button");f.title=e;f.appendChild(g);z(f,"click",this.Vm,this);this.C=document.createElement("DIV");this.C.className="ol-overviewmap-map";var h=this.c=new H({controls:new D,interactions:new D, -view:a.view});a.layers&&a.layers.forEach(function(a){h.$g(a)},this);e=document.createElement("DIV");e.className="ol-overviewmap-box";e.style.boxSizing="border-box";this.o=new sk({position:[0,0],positioning:"bottom-left",element:e});this.c.ah(this.o);e=document.createElement("div");e.className=d+" ol-unselectable ol-control"+(this.j&&this.l?" ol-collapsed":"")+(this.l?"":" ol-uncollapsible");e.appendChild(this.C);e.appendChild(f);kd.call(this,{element:e,render:a.render?a.render:Ck,target:a.target}); -var l=this,m=this.o,n=this.o.Rd();n.addEventListener("mousedown",function(){window.addEventListener("mousemove",c);window.addEventListener("mouseup",b)})}u(Bk,kd);k=Bk.prototype;k.setMap=function(a){var b=this.a;a!==b&&(b&&((b=b.$())&&Hc(b,Sc("rotation"),this.Fe,this),this.c.Ke(null)),kd.prototype.setMap.call(this,a),a&&(this.c.Ke(this.C),this.u.push(z(a,"propertychange",this.Fl,this)),this.c.Qh().fc()||this.c.lj(a.Mc()),a=a.$()))&&(z(a,Sc("rotation"),this.Fe,this),hg(a)&&(this.c.Cd(),Dk(this)))}; -k.Fl=function(a){"view"===a.key&&((a=a.oldValue)&&Hc(a,Sc("rotation"),this.Fe,this),a=this.a.$(),z(a,Sc("rotation"),this.Fe,this))};k.Fe=function(){this.c.$().Ne(this.a.$().Sa())};function Ck(){var a=this.a,b=this.c;if(a.a&&b.a){var c=a.Nb(),a=a.$().hd(c),d=b.Nb(),c=b.$().hd(d),e=b.Ka(fb(a)),f=b.Ka(db(a)),b=Math.abs(e[0]-f[0]),e=Math.abs(e[1]-f[1]),f=d[0],d=d[1];b<.1*f||e<.1*d||b>.75*f||e>.75*d?Dk(this):Ua(c,a)||(a=this.c,c=this.a.$(),a.$().lb(c.za()))}Ek(this)} -function Dk(a){var b=a.a;a=a.c;var c=b.Nb(),b=b.$().hd(c);a=a.$();ob(b,1/(.1*Math.pow(2,Math.log(7.5)/Math.LN2/2)));a.Mf(b)}function Ek(a){var b=a.a,c=a.c;if(b.a&&c.a){var d=b.Nb(),e=b.$(),f=c.$(),c=e.Sa(),b=a.o,g=a.o.Rd(),h=e.hd(d),d=f.Ra(),e=cb(h),f=eb(h),l;if(a=a.a.$().za())l=[e[0]-a[0],e[1]-a[1]],cf(l,c),Xe(l,a);b.Me(l);g&&(g.style.width=Math.abs((e[0]-f[0])/d)+"px",g.style.height=Math.abs((f[1]-e[1])/d)+"px")}}k.Vm=function(a){a.preventDefault();Fk(this)}; -function Fk(a){a.element.classList.toggle("ol-collapsed");a.j?id(a.v,a.A):id(a.A,a.v);a.j=!a.j;var b=a.c;a.j||b.a||(b.Cd(),Dk(a),Gc(b,"postrender",function(){Ek(this)},a))}k.Um=function(){return this.l};k.Xm=function(a){this.l!==a&&(this.l=a,this.element.classList.toggle("ol-uncollapsible"),!a&&this.j&&Fk(this))};k.Wm=function(a){this.l&&this.j!==a&&Fk(this)};k.Tm=function(){return this.j};k.bl=function(){return this.c};function Gk(a){a=a?a:{};var b=void 0!==a.className?a.className:"ol-scale-line";this.l=document.createElement("DIV");this.l.className=b+"-inner";this.c=document.createElement("DIV");this.c.className=b+" ol-unselectable";this.c.appendChild(this.l);this.v=null;this.o=void 0!==a.minWidth?a.minWidth:64;this.j=!1;this.C=void 0;this.A="";kd.call(this,{element:this.c,render:a.render?a.render:Hk,target:a.target});z(this,Sc(Ik),this.I,this);this.G(a.units||"metric")}u(Gk,kd);var Jk=[1,2,5]; -Gk.prototype.Kb=function(){return this.get(Ik)};function Hk(a){(a=a.frameState)?this.v=a.viewState:this.v=null;Kk(this)}Gk.prototype.I=function(){Kk(this)};Gk.prototype.G=function(a){this.set(Ik,a)}; -function Kk(a){var b=a.v;if(b){var c=b.projection,d=c.uc(),b=Rb(c,b.resolution,b.center)*d,d=a.o*b,c="",e=a.Kb();"degrees"==e?(c=xb.degrees,b/=c,d<c/60?(c="\u2033",b*=3600):d<c?(c="\u2032",b*=60):c="\u00b0"):"imperial"==e?.9144>d?(c="in",b/=.0254):1609.344>d?(c="ft",b/=.3048):(c="mi",b/=1609.344):"nautical"==e?(b/=1852,c="nm"):"metric"==e?.001>d?(c="\u03bcm",b*=1E6):1>d?(c="mm",b*=1E3):1E3>d?c="m":(c="km",b/=1E3):"us"==e?.9144>d?(c="in",b*=39.37):1609.344>d?(c="ft",b/=.30480061):(c="mi",b/=1609.3472): -sa(!1,33);for(var e=3*Math.floor(Math.log(a.o*b)/Math.log(10)),f;;){f=Jk[(e%3+3)%3]*Math.pow(10,Math.floor(e/3));d=Math.round(f/b);if(isNaN(d)){a.c.style.display="none";a.j=!1;return}if(d>=a.o)break;++e}b=f+" "+c;a.A!=b&&(a.l.innerHTML=b,a.A=b);a.C!=d&&(a.l.style.width=d+"px",a.C=d);a.j||(a.c.style.display="",a.j=!0)}else a.j&&(a.c.style.display="none",a.j=!1)}var Ik="units";function Lk(a){a=a?a:{};this.c=void 0;this.j=Mk;this.A=this.o=0;this.I=null;this.ea=!1;this.T=void 0!==a.duration?a.duration:200;var b=void 0!==a.className?a.className:"ol-zoomslider",c=document.createElement("button");c.setAttribute("type","button");c.className=b+"-thumb ol-unselectable";var d=document.createElement("div");d.className=b+" ol-unselectable ol-control";d.appendChild(c);this.l=new Ae(d);z(this.l,"pointerdown",this.tl,this);z(this.l,"pointermove",this.rl,this);z(this.l,"pointerup",this.sl, -this);z(d,"click",this.ql,this);z(c,"click",Mc);kd.call(this,{element:d,render:a.render?a.render:Nk})}u(Lk,kd);Lk.prototype.ra=function(){Kc(this.l);kd.prototype.ra.call(this)};var Mk=0;k=Lk.prototype;k.setMap=function(a){kd.prototype.setMap.call(this,a);a&&a.render()}; -function Nk(a){if(a.frameState){if(!this.ea){var b=this.element,c=b.offsetWidth,d=b.offsetHeight,e=b.firstElementChild,f=getComputedStyle(e),b=e.offsetWidth+parseFloat(f.marginRight)+parseFloat(f.marginLeft),e=e.offsetHeight+parseFloat(f.marginTop)+parseFloat(f.marginBottom);this.I=[b,e];c>d?(this.j=1,this.A=c-b):(this.j=Mk,this.o=d-e);this.ea=!0}a=a.frameState.viewState.resolution;a!==this.c&&(this.c=a,Ok(this,a))}} -k.ql=function(a){var b=this.a.$();a=Pk(this,xa(1===this.j?(a.offsetX-this.I[0]/2)/this.A:(a.offsetY-this.I[1]/2)/this.o,0,1));b.animate({resolution:b.constrainResolution(a),duration:this.T,easing:pd})};k.tl=function(a){this.v||a.b.target!==this.element.firstElementChild||($f(this.a.$(),1,1),this.C=a.clientX,this.G=a.clientY,this.v=!0)}; -k.rl=function(a){if(this.v){var b=this.element.firstElementChild;this.c=Pk(this,xa(1===this.j?(a.clientX-this.C+parseInt(b.style.left,10))/this.A:(a.clientY-this.G+parseInt(b.style.top,10))/this.o,0,1));this.a.$().$c(this.c);Ok(this,this.c);this.C=a.clientX;this.G=a.clientY}};k.sl=function(){if(this.v){var a=this.a.$();$f(a,1,-1);a.animate({resolution:a.constrainResolution(this.c),duration:this.T,easing:pd});this.v=!1;this.G=this.C=void 0}}; -function Ok(a,b){var c;c=1-gg(a.a.$())(b);var d=a.element.firstElementChild;1==a.j?d.style.left=a.A*c+"px":d.style.top=a.o*c+"px"}function Pk(a,b){return fg(a.a.$())(1-b)};function Qk(a){a=a?a:{};this.c=a.extent?a.extent:null;var b=void 0!==a.className?a.className:"ol-zoom-extent",c=void 0!==a.label?a.label:"E",d=void 0!==a.tipLabel?a.tipLabel:"Fit to extent",e=document.createElement("button");e.setAttribute("type","button");e.title=d;e.appendChild("string"===typeof c?document.createTextNode(c):c);z(e,"click",this.j,this);c=document.createElement("div");c.className=b+" ol-unselectable ol-control";c.appendChild(e);kd.call(this,{element:c,target:a.target})}u(Qk,kd); -Qk.prototype.j=function(a){a.preventDefault();a=this.a.$();var b=this.c?this.c:a.o.D();a.Mf(b)};function Rk(a){Qc.call(this);a=a?a:{};this.a=null;z(this,Sc(Sk),this.rm,this);this.bg(void 0!==a.tracking?a.tracking:!1)}u(Rk,Qc);k=Rk.prototype;k.ra=function(){this.bg(!1);Qc.prototype.ra.call(this)}; -k.Ro=function(a){if(null!==a.alpha){var b=Ca(a.alpha);this.set(Tk,b);"boolean"===typeof a.absolute&&a.absolute?this.set(Uk,b):"number"===typeof a.webkitCompassHeading&&-1!=a.webkitCompassAccuracy&&this.set(Uk,Ca(a.webkitCompassHeading))}null!==a.beta&&this.set(Vk,Ca(a.beta));null!==a.gamma&&this.set(Wk,Ca(a.gamma));this.s()};k.Bk=function(){return this.get(Tk)};k.Ek=function(){return this.get(Vk)};k.Kk=function(){return this.get(Wk)};k.qm=function(){return this.get(Uk)};k.Mh=function(){return this.get(Sk)}; -k.rm=function(){if(Wd){var a=this.Mh();a&&!this.a?this.a=z(window,"deviceorientation",this.Ro,this):a||null===this.a||(Bc(this.a),this.a=null)}};k.bg=function(a){this.set(Sk,a)};var Tk="alpha",Vk="beta",Wk="gamma",Uk="heading",Sk="tracking";function Xk(a){this.f=a.opacity;this.o=a.rotateWithView;this.j=a.rotation;this.c=a.scale;this.u=a.snapToPixel}k=Xk.prototype;k.Ye=function(){return this.f};k.Ze=function(){return this.o};k.$e=function(){return this.j};k.af=function(){return this.c};k.ze=function(){return this.u};k.vd=function(a){this.f=a};k.bf=function(a){this.j=a};k.wd=function(a){this.c=a};function Yk(a){this.A=this.v=this.i=null;this.Wa=void 0!==a.fill?a.fill:null;this.qa=[0,0];this.b=a.points;this.a=void 0!==a.radius?a.radius:a.radius1;this.g=void 0!==a.radius2?a.radius2:this.a;this.l=void 0!==a.angle?a.angle:0;this.Za=void 0!==a.stroke?a.stroke:null;this.G=this.ta=this.C=null;this.O=a.atlasManager;Zk(this,this.O);Xk.call(this,{opacity:1,rotateWithView:void 0!==a.rotateWithView?a.rotateWithView:!1,rotation:void 0!==a.rotation?a.rotation:0,scale:1,snapToPixel:void 0!==a.snapToPixel? -a.snapToPixel:!0})}u(Yk,Xk);k=Yk.prototype;k.clone=function(){var a=new Yk({fill:this.Ca()?this.Ca().clone():void 0,points:this.g!==this.a?this.b/2:this.b,radius:this.a,radius2:this.g,angle:this.l,snapToPixel:this.u,stroke:this.Da()?this.Da().clone():void 0,rotation:this.j,rotateWithView:this.o,atlasManager:this.O});a.vd(this.f);a.wd(this.c);return a};k.Jc=function(){return this.C};k.Ji=function(){return this.l};k.Ca=function(){return this.Wa};k.kg=function(){return this.A};k.Y=function(){return this.v}; -k.ye=function(){return this.G};k.Xe=function(){return 2};k.Tc=function(){return this.qa};k.Ki=function(){return this.b};k.Li=function(){return this.a};k.yh=function(){return this.g};k.kc=function(){return this.ta};k.Da=function(){return this.Za};k.Gh=function(){};k.load=function(){};k.xj=function(){}; -function Zk(a,b){var c,d="",e="",f=0,g=null,h,l=0;a.Za&&(h=a.Za.a,null===h&&(h=Rh),h=fd(h),l=a.Za.c,void 0===l&&(l=1),g=a.Za.g,Ud||(g=null),e=a.Za.j,void 0===e&&(e="round"),d=a.Za.i,void 0===d&&(d="round"),f=a.Za.l,void 0===f&&(f=10));var m=2*(a.a+l)+1,d={strokeStyle:h,vj:l,size:m,lineCap:d,lineDash:g,lineJoin:e,miterLimit:f};void 0===b?(e=hd(m,m),a.v=e.canvas,c=m=a.v.width,a.jh(d,e,0,0),a.Wa?a.A=a.v:(e=hd(d.size,d.size),a.A=e.canvas,a.ih(d,e,0,0))):(m=Math.round(m),(e=!a.Wa)&&(c=a.ih.bind(a,d)), -a.Za?(f=a.Za,void 0===f.b&&(f.b="s",f.b=f.a?"string"===typeof f.a?f.b+f.a:f.b+w(f.a).toString():f.b+"-",f.b+=","+(void 0!==f.i?f.i.toString():"-")+","+(f.g?f.g.toString():"-")+","+(void 0!==f.f?f.f:"-")+","+(void 0!==f.j?f.j:"-")+","+(void 0!==f.l?f.l.toString():"-")+","+(void 0!==f.c?f.c.toString():"-")),f=f.b):f="-",a.Wa?(g=a.Wa,void 0===g.a&&(g.a=g.b instanceof CanvasPattern||g.b instanceof CanvasGradient?w(g.b).toString():"f"+(g.b?dd(g.b):"-")),g=g.a):g="-",a.i&&f==a.i[1]&&g==a.i[2]&&a.a==a.i[3]&& -a.g==a.i[4]&&a.l==a.i[5]&&a.b==a.i[6]||(a.i=["r"+f+g+(void 0!==a.a?a.a.toString():"-")+(void 0!==a.g?a.g.toString():"-")+(void 0!==a.l?a.l.toString():"-")+(void 0!==a.b?a.b.toString():"-"),f,g,a.a,a.g,a.l,a.b]),d=b.add(a.i[0],m,m,a.jh.bind(a,d),c),a.v=d.image,a.qa=[d.offsetX,d.offsetY],c=d.image.width,a.A=e?d.Ul:a.v);a.C=[m/2,m/2];a.ta=[m,m];a.G=[c,c]} -k.jh=function(a,b,c,d){var e;b.setTransform(1,0,0,1,0,0);b.translate(c,d);b.beginPath();if(Infinity===this.b)b.arc(a.size/2,a.size/2,this.a,0,2*Math.PI,!0);else for(this.g!==this.a&&(this.b*=2),c=0;c<=this.b;c++)d=2*c*Math.PI/this.b-Math.PI/2+this.l,e=c%2?this.g:this.a,b.lineTo(a.size/2+e*Math.cos(d),a.size/2+e*Math.sin(d));this.Wa&&(c=this.Wa.b,null===c&&(c=Ph),b.fillStyle=fd(c),b.fill());this.Za&&(b.strokeStyle=a.strokeStyle,b.lineWidth=a.vj,a.lineDash&&b.setLineDash(a.lineDash),b.lineCap=a.lineCap, -b.lineJoin=a.lineJoin,b.miterLimit=a.miterLimit,b.stroke());b.closePath()}; -k.ih=function(a,b,c,d){b.setTransform(1,0,0,1,0,0);b.translate(c,d);b.beginPath();if(Infinity===this.b)b.arc(a.size/2,a.size/2,this.a,0,2*Math.PI,!0);else{this.g!==this.a&&(this.b*=2);var e;for(c=0;c<=this.b;c++)e=2*c*Math.PI/this.b-Math.PI/2+this.l,d=c%2?this.g:this.a,b.lineTo(a.size/2+d*Math.cos(e),a.size/2+d*Math.sin(e))}b.fillStyle=Ph;b.fill();this.Za&&(b.strokeStyle=a.strokeStyle,b.lineWidth=a.vj,a.lineDash&&b.setLineDash(a.lineDash),b.stroke());b.closePath()};function $k(a){a=a||{};Yk.call(this,{points:Infinity,fill:a.fill,radius:a.radius,snapToPixel:a.snapToPixel,stroke:a.stroke,atlasManager:a.atlasManager})}u($k,Yk);$k.prototype.clone=function(){var a=new $k({fill:this.Ca()?this.Ca().clone():void 0,stroke:this.Da()?this.Da().clone():void 0,radius:this.a,snapToPixel:this.u,atlasManager:this.O});a.vd(this.f);a.wd(this.c);return a};$k.prototype.Zc=function(a){this.a=a;Zk(this,this.O)};function al(a){a=a||{};this.b=void 0!==a.color?a.color:null;this.a=void 0}al.prototype.clone=function(){var a=this.b;return new al({color:a&&a.slice?a.slice():a||void 0})};al.prototype.g=function(){return this.b};al.prototype.c=function(a){this.b=a;this.a=void 0};function bl(a){a=a||{};this.Ic=null;this.Qa=cl;void 0!==a.geometry&&this.Ta(a.geometry);this.Wa=void 0!==a.fill?a.fill:null;this.N=void 0!==a.image?a.image:null;this.Za=void 0!==a.stroke?a.stroke:null;this.Fa=void 0!==a.text?a.text:null;this.Bj=a.zIndex}k=bl.prototype; -k.clone=function(){var a=this.U();a&&a.clone&&(a=a.clone());return new bl({geometry:a,fill:this.Ca()?this.Ca().clone():void 0,image:this.Y()?this.Y().clone():void 0,stroke:this.Da()?this.Da().clone():void 0,text:this.Oa()?this.Oa().clone():void 0,zIndex:this.Aa()})};k.U=function(){return this.Ic};k.Lk=function(){return this.Qa};k.Ca=function(){return this.Wa};k.mf=function(a){this.Wa=a};k.Y=function(){return this.N};k.Hg=function(a){this.N=a};k.Da=function(){return this.Za}; -k.nf=function(a){this.Za=a};k.Oa=function(){return this.Fa};k.pf=function(a){this.Fa=a};k.Aa=function(){return this.Bj};k.Ta=function(a){"function"===typeof a?this.Qa=a:"string"===typeof a?this.Qa=function(b){return b.get(a)}:a?a&&(this.Qa=function(){return a}):this.Qa=cl;this.Ic=a};k.Xb=function(a){this.Bj=a};function dl(a){if("function"!==typeof a){var b;Array.isArray(a)?b=a:(sa(a instanceof bl,41),b=[a]);a=function(){return b}}return a}var el=null; -function fl(){if(!el){var a=new al({color:"rgba(255,255,255,0.4)"}),b=new tj({color:"#3399CC",width:1.25});el=[new bl({image:new $k({fill:a,stroke:b,radius:5}),fill:a,stroke:b})]}return el} -function gl(){var a={},b=[255,255,255,1],c=[0,153,255,1];a.Polygon=[new bl({fill:new al({color:[255,255,255,.5]})})];a.MultiPolygon=a.Polygon;a.LineString=[new bl({stroke:new tj({color:b,width:5})}),new bl({stroke:new tj({color:c,width:3})})];a.MultiLineString=a.LineString;a.Circle=a.Polygon.concat(a.LineString);a.Point=[new bl({image:new $k({radius:6,fill:new al({color:c}),stroke:new tj({color:b,width:1.5})}),zIndex:Infinity})];a.MultiPoint=a.Point;a.GeometryCollection=a.Polygon.concat(a.LineString, -a.Point);return a}function cl(a){return a.U()};function I(a){Qc.call(this);this.a=void 0;this.c="geometry";this.f=null;this.j=void 0;this.i=null;z(this,Sc(this.c),this.De,this);void 0!==a&&(a instanceof lf||!a?this.Ta(a):this.H(a))}u(I,Qc);k=I.prototype;k.clone=function(){var a=new I(this.M());a.Yc(this.c);var b=this.U();b&&a.Ta(b.clone());(b=this.f)&&a.cg(b);return a};k.U=function(){return this.get(this.c)};k.sm=function(){return this.a};k.Mk=function(){return this.c};k.tm=function(){return this.f};k.Rc=function(){return this.j};k.vl=function(){this.s()}; -k.De=function(){this.i&&(Bc(this.i),this.i=null);var a=this.U();a&&(this.i=z(a,"change",this.vl,this));this.s()};k.Ta=function(a){this.set(this.c,a)};k.cg=function(a){this.j=(this.f=a)?hl(a):void 0;this.s()};k.lc=function(a){this.a=a;this.s()};k.Yc=function(a){Hc(this,Sc(this.c),this.De,this);this.c=a;z(this,Sc(this.c),this.De,this);this.De()}; -function hl(a){var b;if("function"===typeof a)2==a.length?b=function(b){return a(this,b)}:b=a;else{var c;Array.isArray(a)?c=a:(sa(a instanceof bl,41),c=[a]);b=function(){return c}}return b};var il=document.implementation.createDocument("","",null);function kl(a,b){return il.createElementNS(a,b)}function ll(a,b){return ml(a,b,[]).join("")}function ml(a,b,c){if(a.nodeType==Node.CDATA_SECTION_NODE||a.nodeType==Node.TEXT_NODE)b?c.push(String(a.nodeValue).replace(/(\r\n|\r|\n)/g,"")):c.push(a.nodeValue);else for(a=a.firstChild;a;a=a.nextSibling)ml(a,b,c);return c}function nl(a){return a instanceof Document}function pl(a){return a instanceof Node} -function ql(a){return(new DOMParser).parseFromString(a,"application/xml")}function rl(a,b){return function(c,d){var e=a.call(b,c,d);void 0!==e&&ha(d[d.length-1],e)}}function sl(a,b){return function(c,d){var e=a.call(void 0!==b?b:this,c,d);void 0!==e&&d[d.length-1].push(e)}}function tl(a,b){return function(c,d){var e=a.call(void 0!==b?b:this,c,d);void 0!==e&&(d[d.length-1]=e)}} -function ul(a){return function(b,c){var d=a.call(this,b,c);if(void 0!==d){var e=c[c.length-1],f=b.localName,g;f in e?g=e[f]:g=e[f]=[];g.push(d)}}}function J(a,b){return function(c,d){var e=a.call(this,c,d);void 0!==e&&(d[d.length-1][void 0!==b?b:c.localName]=e)}}function K(a,b){return function(c,d,e){a.call(void 0!==b?b:this,c,d,e);e[e.length-1].node.appendChild(c)}} -function vl(a){var b,c;return function(d,e,f){if(!b){b={};var g={};g[d.localName]=a;b[d.namespaceURI]=g;c=wl(d.localName)}xl(b,c,e,f)}}function wl(a,b){return function(c,d,e){c=d[d.length-1].node;d=a;void 0===d&&(d=e);e=b;void 0===b&&(e=c.namespaceURI);return kl(e,d)}}var yl=wl();function zl(a,b){for(var c=b.length,d=Array(c),e=0;e<c;++e)d[e]=a[b[e]];return d}function L(a,b,c){c=void 0!==c?c:{};var d,e;d=0;for(e=a.length;d<e;++d)c[a[d]]=b;return c} -function Al(a,b,c,d){for(b=b.firstElementChild;b;b=b.nextElementSibling){var e=a[b.namespaceURI];void 0!==e&&(e=e[b.localName])&&e.call(d,b,c)}}function M(a,b,c,d,e){d.push(a);Al(b,c,d,e);return d.pop()}function xl(a,b,c,d,e,f){for(var g=(void 0!==e?e:c).length,h,l,m=0;m<g;++m)h=c[m],void 0!==h&&(l=b.call(f,h,d,void 0!==e?e[m]:void 0),void 0!==l&&a[l.namespaceURI][l.localName].call(f,l,h,d))}function Bl(a,b,c,d,e,f,g){e.push(a);xl(b,c,d,e,f,g);e.pop()};function Cl(a,b,c,d){return function(e,f,g){var h=new XMLHttpRequest;h.open("GET","function"===typeof a?a(e,f,g):a,!0);"arraybuffer"==b.S()&&(h.responseType="arraybuffer");h.onload=function(){if(!h.status||200<=h.status&&300>h.status){var a=b.S(),e;"json"==a||"text"==a?e=h.responseText:"xml"==a?(e=h.responseXML)||(e=ql(h.responseText)):"arraybuffer"==a&&(e=h.response);e?c.call(this,b.Pa(e,{featureProjection:g}),b.jb(e)):d.call(this)}else d.call(this)}.bind(this);h.onerror=function(){d.call(this)}.bind(this); -h.send()}}function Dl(a,b){return Cl(a,b,function(a){this.gd(a)},oa)};function El(){this.i=this.defaultDataProjection=null}function Fl(a,b,c){var d;c&&(d={dataProjection:c.dataProjection?c.dataProjection:a.jb(b),featureProjection:c.featureProjection});return Gl(a,d)}function Gl(a,b){return qb({dataProjection:a.defaultDataProjection,featureProjection:a.i},b)} -function Hl(a,b,c){var d=c?Tb(c.featureProjection):null,e=c?Tb(c.dataProjection):null,f;d&&e&&!bc(d,e)?a instanceof lf?f=(b?a.clone():a).tb(b?d:e,b?e:d):f=gc(b?a.slice():a,b?d:e,b?e:d):f=a;if(b&&c&&c.decimals){var g=Math.pow(10,c.decimals);a=function(a){for(var b=0,c=a.length;b<c;++b)a[b]=Math.round(a[b]*g)/g;return a};Array.isArray(f)?a(f):f.Fc(a)}return f};function Il(){El.call(this)}u(Il,El);function Jl(a){return"string"===typeof a?(a=JSON.parse(a))?a:null:null!==a?a:null}k=Il.prototype;k.S=function(){return"json"};k.Vb=function(a,b){return this.Wc(Jl(a),Fl(this,a,b))};k.Pa=function(a,b){return this.sg(Jl(a),Fl(this,a,b))};k.Xc=function(a,b){return this.wg(Jl(a),Fl(this,a,b))};k.jb=function(a){return this.zg(Jl(a))};k.Dd=function(a,b){return JSON.stringify(this.dd(a,b))};k.Yb=function(a,b){return JSON.stringify(this.ge(a,b))}; -k.ed=function(a,b){return JSON.stringify(this.ie(a,b))};function Kl(a,b,c,d,e,f){var g=NaN,h=NaN,l=(c-b)/d;if(1===l)g=a[b],h=a[b+1];else if(2==l)g=(1-e)*a[b]+e*a[b+d],h=(1-e)*a[b+1]+e*a[b+d+1];else if(l){var h=a[b],l=a[b+1],m=0,g=[0],n;for(n=b+d;n<c;n+=d){var p=a[n],q=a[n+1],m=m+Math.sqrt((p-h)*(p-h)+(q-l)*(q-l));g.push(m);h=p;l=q}c=e*m;l=0;m=g.length;for(n=!1;l<m;)e=l+(m-l>>1),h=+ea(g[e],c),0>h?l=e+1:(m=e,n=!h);e=n?l:~l;0>e?(c=(c-g[-e-2])/(g[-e-1]-g[-e-2]),b+=(-e-2)*d,g=Ea(a[b],a[b+d],c),h=Ea(a[b+1],a[b+d+1],c)):(g=a[b+e*d],h=a[b+e*d+1])}return f?(f[0]= -g,f[1]=h,f):[g,h]}function Ll(a,b,c,d,e,f){if(c==b)return null;if(e<a[b+d-1])return f?(c=a.slice(b,b+d),c[d-1]=e,c):null;if(a[c-1]<e)return f?(c=a.slice(c-d,c),c[d-1]=e,c):null;if(e==a[b+d-1])return a.slice(b,b+d);b/=d;for(c/=d;b<c;)f=b+c>>1,e<a[(f+1)*d-1]?c=f:b=f+1;c=a[b*d-1];if(e==c)return a.slice((b-1)*d,(b-1)*d+d);f=(e-c)/(a[(b+1)*d-1]-c);c=[];var g;for(g=0;g<d-1;++g)c.push(Ea(a[(b-1)*d+g],a[b*d+g],f));c.push(e);return c} -function Ml(a,b,c,d,e,f){var g=0;if(f)return Ll(a,g,b[b.length-1],c,d,e);if(d<a[c-1])return e?(a=a.slice(0,c),a[c-1]=d,a):null;if(a[a.length-1]<d)return e?(a=a.slice(a.length-c),a[c-1]=d,a):null;e=0;for(f=b.length;e<f;++e){var h=b[e];if(g!=h){if(d<a[g+c-1])break;else if(d<=a[h-1])return Ll(a,g,h,c,d,!1);g=h}}return null};function N(a,b){of.call(this);this.c=null;this.v=this.A=this.j=-1;this.pa(a,b)}u(N,of);k=N.prototype;k.ik=function(a){this.B?ha(this.B,a):this.B=a.slice();this.s()};k.clone=function(){var a=new N(null);a.ca(this.la,this.B.slice());return a};k.Hb=function(a,b,c,d){if(d<Pa(this.D(),a,b))return d;this.v!=this.g&&(this.A=Math.sqrt(vf(this.B,0,this.B.length,this.a,0)),this.v=this.g);return xf(this.B,0,this.B.length,this.a,this.A,!1,a,b,c,d)}; -k.yk=function(a,b){return Mf(this.B,0,this.B.length,this.a,a,b)};k.gn=function(a,b){return"XYM"!=this.la&&"XYZM"!=this.la?null:Ll(this.B,0,this.B.length,this.a,a,void 0!==b?b:!1)};k.W=function(){return Cf(this.B,0,this.B.length,this.a)};k.ph=function(a,b){return Kl(this.B,0,this.B.length,this.a,a,b)};k.hn=function(){var a=this.B,b=this.a,c=a[0],d=a[1],e=0,f;for(f=0+b;f<this.B.length;f+=b)var g=a[f],h=a[f+1],e=e+Math.sqrt((g-c)*(g-c)+(h-d)*(h-d)),c=g,d=h;return e}; -function ai(a){a.j!=a.g&&(a.c=a.ph(.5,a.c),a.j=a.g);return a.c}k.od=function(a){var b=[];b.length=Ef(this.B,0,this.B.length,this.a,a,b,0);a=new N(null);a.ca("XY",b);return a};k.S=function(){return"LineString"};k.Ya=function(a){return Nf(this.B,0,this.B.length,this.a,a)};k.pa=function(a,b){a?(rf(this,b,a,1),this.B||(this.B=[]),this.B.length=Af(this.B,0,a,this.a),this.s()):this.ca("XY",null)};k.ca=function(a,b){qf(this,a,b);this.s()};function O(a,b){of.call(this);this.c=[];this.j=this.v=-1;this.pa(a,b)}u(O,of);k=O.prototype;k.jk=function(a){this.B?ha(this.B,a.ia().slice()):this.B=a.ia().slice();this.c.push(this.B.length);this.s()};k.clone=function(){var a=new O(null);a.ca(this.la,this.B.slice(),this.c.slice());return a};k.Hb=function(a,b,c,d){if(d<Pa(this.D(),a,b))return d;this.j!=this.g&&(this.v=Math.sqrt(wf(this.B,0,this.c,this.a,0)),this.j=this.g);return yf(this.B,0,this.c,this.a,this.v,!1,a,b,c,d)}; -k.kn=function(a,b,c){return"XYM"!=this.la&&"XYZM"!=this.la||!this.B.length?null:Ml(this.B,this.c,this.a,a,void 0!==b?b:!1,void 0!==c?c:!1)};k.W=function(){return Df(this.B,0,this.c,this.a)};k.Sb=function(){return this.c};k.Tk=function(a){if(0>a||this.c.length<=a)return null;var b=new N(null);b.ca(this.la,this.B.slice(a?this.c[a-1]:0,this.c[a]));return b}; -k.Nc=function(){var a=this.B,b=this.c,c=this.la,d=[],e=0,f,g;f=0;for(g=b.length;f<g;++f){var h=b[f],l=new N(null);l.ca(c,a.slice(e,h));d.push(l);e=h}return d};function bi(a){var b=[],c=a.B,d=0,e=a.c;a=a.a;var f,g;f=0;for(g=e.length;f<g;++f){var h=e[f],d=Kl(c,d,h,a,.5);ha(b,d);d=h}return b}k.od=function(a){var b=[],c=[],d=this.B,e=this.c,f=this.a,g=0,h=0,l,m;l=0;for(m=e.length;l<m;++l){var n=e[l],h=Ef(d,g,n,f,a,b,h);c.push(h);g=n}b.length=h;a=new O(null);a.ca("XY",b,c);return a};k.S=function(){return"MultiLineString"}; -k.Ya=function(a){a:{var b=this.B,c=this.c,d=this.a,e=0,f,g;f=0;for(g=c.length;f<g;++f){if(Nf(b,e,c[f],d,a)){a=!0;break a}e=c[f]}a=!1}return a};k.pa=function(a,b){if(a){rf(this,b,a,2);this.B||(this.B=[]);var c=Bf(this.B,0,a,this.a,this.c);this.B.length=c.length?c[c.length-1]:0;this.s()}else this.ca("XY",null,this.c)};k.ca=function(a,b,c){qf(this,a,b);this.c=c;this.s()}; -function Nl(a,b){var c=a.la,d=[],e=[],f,g;f=0;for(g=b.length;f<g;++f){var h=b[f];f||(c=h.la);ha(d,h.ia());e.push(d.length)}a.ca(c,d,e)};function P(a,b){of.call(this);this.pa(a,b)}u(P,of);k=P.prototype;k.lk=function(a){this.B?ha(this.B,a.ia()):this.B=a.ia().slice();this.s()};k.clone=function(){var a=new P(null);a.ca(this.la,this.B.slice());return a};k.Hb=function(a,b,c,d){if(d<Pa(this.D(),a,b))return d;var e=this.B,f=this.a,g,h,l;g=0;for(h=e.length;g<h;g+=f)if(l=Ba(a,b,e[g],e[g+1]),l<d){d=l;for(l=0;l<f;++l)c[l]=e[g+l];c.length=f}return d};k.W=function(){return Cf(this.B,0,this.B.length,this.a)}; -k.dl=function(a){var b=this.B?this.B.length/this.a:0;if(0>a||b<=a)return null;b=new E(null);b.ca(this.la,this.B.slice(a*this.a,(a+1)*this.a));return b};k.Zd=function(){var a=this.B,b=this.la,c=this.a,d=[],e,f;e=0;for(f=a.length;e<f;e+=c){var g=new E(null);g.ca(b,a.slice(e,e+c));d.push(g)}return d};k.S=function(){return"MultiPoint"};k.Ya=function(a){var b=this.B,c=this.a,d,e,f,g;d=0;for(e=b.length;d<e;d+=c)if(f=b[d],g=b[d+1],Sa(a,f,g))return!0;return!1}; -k.pa=function(a,b){a?(rf(this,b,a,1),this.B||(this.B=[]),this.B.length=Af(this.B,0,a,this.a),this.s()):this.ca("XY",null)};k.ca=function(a,b){qf(this,a,b);this.s()};function Q(a,b){of.call(this);this.c=[];this.v=-1;this.A=null;this.I=this.C=this.G=-1;this.j=null;this.pa(a,b)}u(Q,of);k=Q.prototype;k.mk=function(a){if(this.B){var b=this.B.length;ha(this.B,a.ia());a=a.Sb().slice();var c,d;c=0;for(d=a.length;c<d;++c)a[c]+=b}else this.B=a.ia().slice(),a=a.Sb().slice(),this.c.push();this.c.push(a);this.s()};k.clone=function(){for(var a=new Q(null),b=this.c.length,c=Array(b),d=0;d<b;++d)c[d]=this.c[d].slice();Ol(a,this.la,this.B.slice(),c);return a}; -k.Hb=function(a,b,c,d){if(d<Pa(this.D(),a,b))return d;if(this.C!=this.g){var e=this.c,f=0,g=0,h,l;h=0;for(l=e.length;h<l;++h)var m=e[h],g=wf(this.B,f,m,this.a,g),f=m[m.length-1];this.G=Math.sqrt(g);this.C=this.g}e=ci(this);f=this.c;g=this.a;h=this.G;l=0;var m=[NaN,NaN],n,p;n=0;for(p=f.length;n<p;++n){var q=f[n];d=yf(e,l,q,g,h,!0,a,b,c,d,m);l=q[q.length-1]}return d}; -k.Sc=function(a,b){var c;a:{c=ci(this);var d=this.c,e=0;if(d.length){var f,g;f=0;for(g=d.length;f<g;++f){var h=d[f];if(Kf(c,e,h,this.a,a,b)){c=!0;break a}e=h[h.length-1]}}c=!1}return c};k.ln=function(){var a=ci(this),b=this.c,c=0,d=0,e,f;e=0;for(f=b.length;e<f;++e)var g=b[e],d=d+tf(a,c,g,this.a),c=g[g.length-1];return d}; -k.W=function(a){var b;void 0!==a?(b=ci(this).slice(),Sf(b,this.c,this.a,a)):b=this.B;a=b;b=this.c;var c=this.a,d=0,e=[],f=0,g,h;g=0;for(h=b.length;g<h;++g){var l=b[g];e[f++]=Df(a,d,l,c,e[f]);d=l[l.length-1]}e.length=f;return e}; -function di(a){if(a.v!=a.g){var b=a.B,c=a.c,d=a.a,e=0,f=[],g,h;g=0;for(h=c.length;g<h;++g){var l=c[g],e=Ya(b,e,l[0],d);f.push((e[0]+e[2])/2,(e[1]+e[3])/2);e=l[l.length-1]}b=ci(a);c=a.c;d=a.a;g=0;h=[];l=0;for(e=c.length;l<e;++l){var m=c[l];h=Lf(b,g,m,d,f,2*l,h);g=m[m.length-1]}a.A=h;a.v=a.g}return a.A}k.Pk=function(){var a=new P(null);a.ca("XY",di(this).slice());return a}; -function ci(a){if(a.I!=a.g){var b=a.B,c;a:{c=a.c;var d,e;d=0;for(e=c.length;d<e;++d)if(!Qf(b,c[d],a.a,void 0)){c=!1;break a}c=!0}c?a.j=b:(a.j=b.slice(),a.j.length=Sf(a.j,a.c,a.a));a.I=a.g}return a.j}k.od=function(a){var b=[],c=[],d=this.B,e=this.c,f=this.a;a=Math.sqrt(a);var g=0,h=0,l,m;l=0;for(m=e.length;l<m;++l){var n=e[l],p=[],h=Ff(d,g,n,f,a,b,h,p);c.push(p);g=n[n.length-1]}b.length=h;d=new Q(null);Ol(d,"XY",b,c);return d}; -k.el=function(a){if(0>a||this.c.length<=a)return null;var b;a?(b=this.c[a-1],b=b[b.length-1]):b=0;a=this.c[a].slice();var c=a[a.length-1];if(b){var d,e;d=0;for(e=a.length;d<e;++d)a[d]-=b}d=new F(null);d.ca(this.la,this.B.slice(b,c),a);return d};k.md=function(){var a=this.la,b=this.B,c=this.c,d=[],e=0,f,g,h,l;f=0;for(g=c.length;f<g;++f){var m=c[f].slice(),n=m[m.length-1];if(e)for(h=0,l=m.length;h<l;++h)m[h]-=e;h=new F(null);h.ca(a,b.slice(e,n),m);d.push(h);e=n}return d};k.S=function(){return"MultiPolygon"}; -k.Ya=function(a){a:{var b=ci(this),c=this.c,d=this.a,e=0,f,g;f=0;for(g=c.length;f<g;++f){var h=c[f];if(Of(b,e,h,d,a)){a=!0;break a}e=h[h.length-1]}a=!1}return a};k.pa=function(a,b){if(a){rf(this,b,a,3);this.B||(this.B=[]);var c=this.B,d=this.a,e=this.c,f=0,e=e?e:[],g=0,h,l;h=0;for(l=a.length;h<l;++h)f=Bf(c,f,a[h],d,e[g]),e[g++]=f,f=f[f.length-1];e.length=g;e.length?(c=e[e.length-1],this.B.length=c.length?c[c.length-1]:0):this.B.length=0;this.s()}else Ol(this,"XY",null,this.c)}; -function Ol(a,b,c,d){qf(a,b,c);a.c=d;a.s()}function Pl(a,b){var c=a.la,d=[],e=[],f,g,h;f=0;for(g=b.length;f<g;++f){var l=b[f];f||(c=l.la);var m=d.length;h=l.Sb();var n,p;n=0;for(p=h.length;n<p;++n)h[n]+=m;ha(d,l.ia());e.push(h)}Ol(a,c,d,e)};function Ql(a){a=a?a:{};El.call(this);this.b=a.geometryName}u(Ql,Il); -function Rl(a,b){if(!a)return null;var c;if("number"===typeof a.x&&"number"===typeof a.y)c="Point";else if(a.points)c="MultiPoint";else if(a.paths)c=1===a.paths.length?"LineString":"MultiLineString";else if(a.rings){var d=a.rings,e=Sl(a),f=[],g=[];c=[];var h,l;h=0;for(l=d.length;h<l;++h)f.length=0,Af(f,0,d[h],e.length),Pf(f,0,f.length,e.length)?g.push([d[h]]):c.push(d[h]);for(;c.length;){d=c.shift();e=!1;for(h=g.length-1;0<=h;h--)if(Ua((new Gf(g[h][0])).D(),(new Gf(d)).D())){g[h].push(d);e=!0;break}e|| -g.push([d.reverse()])}a=qb({},a);1===g.length?(c="Polygon",a.rings=g[0]):(c="MultiPolygon",a.rings=g)}return Hl((0,Tl[c])(a),!1,b)}function Sl(a){var b="XY";!0===a.hasZ&&!0===a.hasM?b="XYZM":!0===a.hasZ?b="XYZ":!0===a.hasM&&(b="XYM");return b}function Ul(a){a=a.la;return{hasZ:"XYZ"===a||"XYZM"===a,hasM:"XYM"===a||"XYZM"===a}} -var Tl={Point:function(a){return void 0!==a.m&&void 0!==a.z?new E([a.x,a.y,a.z,a.m],"XYZM"):void 0!==a.z?new E([a.x,a.y,a.z],"XYZ"):void 0!==a.m?new E([a.x,a.y,a.m],"XYM"):new E([a.x,a.y])},LineString:function(a){return new N(a.paths[0],Sl(a))},Polygon:function(a){return new F(a.rings,Sl(a))},MultiPoint:function(a){return new P(a.points,Sl(a))},MultiLineString:function(a){return new O(a.paths,Sl(a))},MultiPolygon:function(a){return new Q(a.rings,Sl(a))}},Vl={Point:function(a){var b=a.W(),c;a=a.la; -"XYZ"===a?c={x:b[0],y:b[1],z:b[2]}:"XYM"===a?c={x:b[0],y:b[1],m:b[2]}:"XYZM"===a?c={x:b[0],y:b[1],z:b[2],m:b[3]}:"XY"===a?c={x:b[0],y:b[1]}:sa(!1,34);return c},LineString:function(a){var b=Ul(a);return{hasZ:b.hasZ,hasM:b.hasM,paths:[a.W()]}},Polygon:function(a){var b=Ul(a);return{hasZ:b.hasZ,hasM:b.hasM,rings:a.W(!1)}},MultiPoint:function(a){var b=Ul(a);return{hasZ:b.hasZ,hasM:b.hasM,points:a.W()}},MultiLineString:function(a){var b=Ul(a);return{hasZ:b.hasZ,hasM:b.hasM,paths:a.W()}},MultiPolygon:function(a){var b= -Ul(a);a=a.W(!1);for(var c=[],d=0;d<a.length;d++)for(var e=a[d].length-1;0<=e;e--)c.push(a[d][e]);return{hasZ:b.hasZ,hasM:b.hasM,rings:c}}};k=Ql.prototype;k.Wc=function(a,b){var c=Rl(a.geometry,b),d=new I;this.b&&d.Yc(this.b);d.Ta(c);b&&b.Zf&&a.attributes[b.Zf]&&d.lc(a.attributes[b.Zf]);a.attributes&&d.H(a.attributes);return d}; -k.sg=function(a,b){var c=b?b:{};if(a.features){var d=[],e=a.features,f,g;c.Zf=a.objectIdFieldName;f=0;for(g=e.length;f<g;++f)d.push(this.Wc(e[f],c));return d}return[this.Wc(a,c)]};k.wg=function(a,b){return Rl(a,b)};k.zg=function(a){return a.spatialReference&&a.spatialReference.wkid?Tb("EPSG:"+a.spatialReference.wkid):null};function Wl(a,b){return(0,Vl[a.S()])(Hl(a,!0,b),b)}k.ie=function(a,b){return Wl(a,Gl(this,b))}; -k.dd=function(a,b){b=Gl(this,b);var c={},d=a.U();d&&(c.geometry=Wl(d,b));d=a.M();delete d[a.c];c.attributes=tb(d)?{}:d;b&&b.featureProjection&&(c.spatialReference={wkid:Tb(b.featureProjection).nb.split(":").pop()});return c};k.ge=function(a,b){b=Gl(this,b);var c=[],d,e;d=0;for(e=a.length;d<e;++d)c.push(this.dd(a[d],b));return{features:c}};function Xl(a){this.mc=a};function Yl(a,b){this.mc=a;this.b=Array.prototype.slice.call(arguments,1);sa(2<=this.b.length,57)}u(Yl,Xl);function Zl(a){var b=["And"].concat(Array.prototype.slice.call(arguments));Yl.apply(this,b)}u(Zl,Yl);function $l(a,b,c){this.mc="BBOX";this.geometryName=a;this.extent=b;this.srsName=c}u($l,Xl);function am(a,b){this.mc=a;this.b=b}u(am,Xl);function bm(a,b,c,d){am.call(this,a,b);this.g=c;this.a=d}u(bm,am);function cm(a,b,c){bm.call(this,"PropertyIsEqualTo",a,b,c)}u(cm,bm);function dm(a,b){bm.call(this,"PropertyIsGreaterThan",a,b)}u(dm,bm);function em(a,b){bm.call(this,"PropertyIsGreaterThanOrEqualTo",a,b)}u(em,bm);function fm(a,b,c,d){this.mc=a;this.geometryName=b||"the_geom";this.geometry=c;this.srsName=d}u(fm,Xl);function gm(a,b,c){fm.call(this,"Intersects",a,b,c)}u(gm,fm);function hm(a,b,c){am.call(this,"PropertyIsBetween",a);this.a=b;this.g=c}u(hm,am);function im(a,b,c,d,e,f){am.call(this,"PropertyIsLike",a);this.c=b;this.f=void 0!==c?c:"*";this.i=void 0!==d?d:".";this.g=void 0!==e?e:"!";this.a=f}u(im,am);function jm(a){am.call(this,"PropertyIsNull",a)}u(jm,am);function km(a,b){bm.call(this,"PropertyIsLessThan",a,b)}u(km,bm);function lm(a,b){bm.call(this,"PropertyIsLessThanOrEqualTo",a,b)}u(lm,bm);function mm(a){this.mc="Not";this.condition=a}u(mm,Xl);function nm(a,b,c){bm.call(this,"PropertyIsNotEqualTo",a,b,c)}u(nm,bm);function om(a){var b=["Or"].concat(Array.prototype.slice.call(arguments));Yl.apply(this,b)}u(om,Yl);function pm(a,b,c){fm.call(this,"Within",a,b,c)}u(pm,fm);function qm(a){var b=[null].concat(Array.prototype.slice.call(arguments));return new (Function.prototype.bind.apply(Zl,b))}function rm(a,b,c){return new $l(a,b,c)};function sm(a){lf.call(this);this.a=a?a:null;tm(this)}u(sm,lf);function um(a){var b=[],c,d;c=0;for(d=a.length;c<d;++c)b.push(a[c].clone());return b}function vm(a){var b,c;if(a.a)for(b=0,c=a.a.length;b<c;++b)Hc(a.a[b],"change",a.s,a)}function tm(a){var b,c;if(a.a)for(b=0,c=a.a.length;b<c;++b)z(a.a[b],"change",a.s,a)}k=sm.prototype;k.clone=function(){var a=new sm(null);a.jj(this.a);return a}; -k.Hb=function(a,b,c,d){if(d<Pa(this.D(),a,b))return d;var e=this.a,f,g;f=0;for(g=e.length;f<g;++f)d=e[f].Hb(a,b,c,d);return d};k.Sc=function(a,b){var c=this.a,d,e;d=0;for(e=c.length;d<e;++d)if(c[d].Sc(a,b))return!0;return!1};k.se=function(a){Wa(Infinity,Infinity,-Infinity,-Infinity,a);for(var b=this.a,c=0,d=b.length;c<d;++c)ab(a,b[c].D());return a};k.Qf=function(){return um(this.a)}; -k.Td=function(a){this.l!=this.g&&(rb(this.i),this.f=0,this.l=this.g);if(0>a||this.f&&a<this.f)return this;var b=a.toString();if(this.i.hasOwnProperty(b))return this.i[b];var c=[],d=this.a,e=!1,f,g;f=0;for(g=d.length;f<g;++f){var h=d[f],l=h.Td(a);c.push(l);l!==h&&(e=!0)}if(e)return a=new sm(null),vm(a),a.a=c,tm(a),a.s(),this.i[b]=a;this.f=a;return this};k.S=function(){return"GeometryCollection"};k.Ya=function(a){var b=this.a,c,d;c=0;for(d=b.length;c<d;++c)if(b[c].Ya(a))return!0;return!1}; -k.rotate=function(a,b){for(var c=this.a,d=0,e=c.length;d<e;++d)c[d].rotate(a,b);this.s()};k.scale=function(a,b,c){c||(c=kb(this.D()));for(var d=this.a,e=0,f=d.length;e<f;++e)d[e].scale(a,b,c);this.s()};k.jj=function(a){a=um(a);vm(this);this.a=a;tm(this);this.s()};k.Fc=function(a){var b=this.a,c,d;c=0;for(d=b.length;c<d;++c)b[c].Fc(a);this.s()};k.translate=function(a,b){var c=this.a,d,e;d=0;for(e=c.length;d<e;++d)c[d].translate(a,b);this.s()};k.ra=function(){vm(this);lf.prototype.ra.call(this)};function wm(a){a=a?a:{};El.call(this);this.defaultDataProjection=Tb(a.defaultDataProjection?a.defaultDataProjection:"EPSG:4326");a.featureProjection&&(this.i=Tb(a.featureProjection));this.b=a.geometryName}u(wm,Il);function xm(a,b){return a?Hl((0,ym[a.type])(a),!1,b):null}function zm(a,b){return(0,Am[a.S()])(Hl(a,!0,b),b)} -var ym={Point:function(a){return new E(a.coordinates)},LineString:function(a){return new N(a.coordinates)},Polygon:function(a){return new F(a.coordinates)},MultiPoint:function(a){return new P(a.coordinates)},MultiLineString:function(a){return new O(a.coordinates)},MultiPolygon:function(a){return new Q(a.coordinates)},GeometryCollection:function(a,b){var c=a.geometries.map(function(a){return xm(a,b)});return new sm(c)}},Am={Point:function(a){return{type:"Point",coordinates:a.W()}},LineString:function(a){return{type:"LineString", -coordinates:a.W()}},Polygon:function(a,b){var c;b&&(c=b.rightHanded);return{type:"Polygon",coordinates:a.W(c)}},MultiPoint:function(a){return{type:"MultiPoint",coordinates:a.W()}},MultiLineString:function(a){return{type:"MultiLineString",coordinates:a.W()}},MultiPolygon:function(a,b){var c;b&&(c=b.rightHanded);return{type:"MultiPolygon",coordinates:a.W(c)}},GeometryCollection:function(a,b){return{type:"GeometryCollection",geometries:a.a.map(function(a){var c=qb({},b);delete c.featureProjection;return zm(a, -c)})}},Circle:function(){return{type:"GeometryCollection",geometries:[]}}};k=wm.prototype;k.Wc=function(a,b){var c;c="Feature"===a.type?a:{type:"Feature",geometry:a};var d=xm(c.geometry,b),e=new I;this.b&&e.Yc(this.b);e.Ta(d);void 0!==c.id&&e.lc(c.id);c.properties&&e.H(c.properties);return e};k.sg=function(a,b){var c;if("FeatureCollection"===a.type){c=[];var d=a.features,e,f;e=0;for(f=d.length;e<f;++e)c.push(this.Wc(d[e],b))}else c=[this.Wc(a,b)];return c};k.wg=function(a,b){return xm(a,b)}; -k.zg=function(a){a=a.crs;var b;a?"name"==a.type?b=Tb(a.properties.name):"EPSG"==a.type?b=Tb("EPSG:"+a.properties.code):sa(!1,36):b=this.defaultDataProjection;return b};k.dd=function(a,b){b=Gl(this,b);var c={type:"Feature"},d=a.a;void 0!==d&&(c.id=d);(d=a.U())?c.geometry=zm(d,b):c.geometry=null;d=a.M();delete d[a.c];tb(d)?c.properties=null:c.properties=d;return c};k.ge=function(a,b){b=Gl(this,b);var c=[],d,e;d=0;for(e=a.length;d<e;++d)c.push(this.dd(a[d],b));return{type:"FeatureCollection",features:c}}; -k.ie=function(a,b){return zm(a,Gl(this,b))};function Bm(){this.g=new XMLSerializer;El.call(this)}u(Bm,El);k=Bm.prototype;k.S=function(){return"xml"};k.Vb=function(a,b){if(nl(a))return Cm(this,a,b);if(pl(a))return this.rg(a,b);if("string"===typeof a){var c=ql(a);return Cm(this,c,b)}return null};function Cm(a,b,c){a=Dm(a,b,c);return 0<a.length?a[0]:null}k.rg=function(){return null};k.Pa=function(a,b){if(nl(a))return Dm(this,a,b);if(pl(a))return this.Bc(a,b);if("string"===typeof a){var c=ql(a);return Dm(this,c,b)}return[]}; -function Dm(a,b,c){var d=[];for(b=b.firstChild;b;b=b.nextSibling)b.nodeType==Node.ELEMENT_NODE&&ha(d,a.Bc(b,c));return d}k.Xc=function(a,b){if(nl(a))return null;if(pl(a))return this.Vi(a,b);"string"===typeof a&&ql(a);return null};k.Vi=function(){return null};k.jb=function(a){return nl(a)?this.yg(a):pl(a)?this.hf(a):"string"===typeof a?(a=ql(a),this.yg(a)):null};k.yg=function(){return this.defaultDataProjection};k.hf=function(){return this.defaultDataProjection}; -k.Dd=function(a,b){return this.g.serializeToString(this.Ng(a,b))};k.Ng=function(){return null};k.Yb=function(a,b){var c=this.Zb(a,b);return this.g.serializeToString(c)};k.Zb=function(){return null};k.ed=function(a,b){var c=this.he(a,b);return this.g.serializeToString(c)};k.he=function(){return null};function Em(a){a=a?a:{};this.featureType=a.featureType;this.featureNS=a.featureNS;this.srsName=a.srsName;this.schemaLocation="";this.b={};this.b["http://www.opengis.net/gml"]={featureMember:tl(Em.prototype.ae),featureMembers:tl(Em.prototype.ae)};Bm.call(this)}u(Em,Bm);var Fm=/^[\s\xa0]*$/;k=Em.prototype; -k.ae=function(a,b){var c=a.localName,d=null;if("FeatureCollection"==c)"http://www.opengis.net/wfs"===a.namespaceURI?d=M([],this.b,a,b,this):d=M(null,this.b,a,b,this);else if("featureMembers"==c||"featureMember"==c){var e=b[0],f=e.featureType,g=e.featureNS,h,l;if(!f&&a.childNodes){f=[];g={};h=0;for(l=a.childNodes.length;h<l;++h){var m=a.childNodes[h];if(1===m.nodeType){var n=m.nodeName.split(":").pop();if(-1===f.indexOf(n)){var p="",q=0,m=m.namespaceURI,r;for(r in g){if(g[r]===m){p=r;break}++q}p|| -(p="p"+q,g[p]=m);f.push(p+":"+n)}}}"featureMember"!=c&&(e.featureType=f,e.featureNS=g)}"string"===typeof g&&(h=g,g={},g.p0=h);var e={},f=Array.isArray(f)?f:[f],v;for(v in g){n={};h=0;for(l=f.length;h<l;++h)(-1===f[h].indexOf(":")?"p0":f[h].split(":")[0])===v&&(n[f[h].split(":").pop()]="featureMembers"==c?sl(this.qg,this):tl(this.qg,this));e[g[v]]=n}"featureMember"==c?d=M(void 0,e,a,b):d=M([],e,a,b)}null===d&&(d=[]);return d}; -k.ef=function(a,b){var c=b[0];c.srsName=a.firstElementChild.getAttribute("srsName");var d=M(null,this.Rg,a,b,this);if(d)return Hl(d,!1,c)}; -k.qg=function(a,b){var c,d;(d=a.getAttribute("fid"))||(d=a.getAttributeNS("http://www.opengis.net/gml","id")||"");var e={},f;for(c=a.firstElementChild;c;c=c.nextElementSibling){var g=c.localName;if(0===c.childNodes.length||1===c.childNodes.length&&(3===c.firstChild.nodeType||4===c.firstChild.nodeType)){var h=ll(c,!1);Fm.test(h)&&(h=void 0);e[g]=h}else"boundedBy"!==g&&(f=g),e[g]=this.ef(c,b)}c=new I(e);f&&c.Yc(f);d&&c.lc(d);return c}; -k.$i=function(a,b){var c=this.df(a,b);if(c){var d=new E(null);d.ca("XYZ",c);return d}};k.Yi=function(a,b){var c=M([],this.Jj,a,b,this);if(c)return new P(c)};k.Xi=function(a,b){var c=M([],this.Ij,a,b,this);if(c){var d=new O(null);Nl(d,c);return d}};k.Zi=function(a,b){var c=M([],this.Kj,a,b,this);if(c){var d=new Q(null);Pl(d,c);return d}};k.Ri=function(a,b){Al(this.Nj,a,b,this)};k.Fh=function(a,b){Al(this.Gj,a,b,this)};k.Si=function(a,b){Al(this.Oj,a,b,this)}; -k.ff=function(a,b){var c=this.df(a,b);if(c){var d=new N(null);d.ca("XYZ",c);return d}};k.mp=function(a,b){var c=M(null,this.je,a,b,this);if(c)return c};k.Wi=function(a,b){var c=this.df(a,b);if(c){var d=new Gf(null);Hf(d,"XYZ",c);return d}};k.gf=function(a,b){var c=M([null],this.xf,a,b,this);if(c&&c[0]){var d=new F(null),e=c[0],f=[e.length],g,h;g=1;for(h=c.length;g<h;++g)ha(e,c[g]),f.push(e.length);d.ca("XYZ",e,f);return d}};k.df=function(a,b){return M(null,this.je,a,b,this)}; -k.Jj={"http://www.opengis.net/gml":{pointMember:sl(Em.prototype.Ri),pointMembers:sl(Em.prototype.Ri)}};k.Ij={"http://www.opengis.net/gml":{lineStringMember:sl(Em.prototype.Fh),lineStringMembers:sl(Em.prototype.Fh)}};k.Kj={"http://www.opengis.net/gml":{polygonMember:sl(Em.prototype.Si),polygonMembers:sl(Em.prototype.Si)}};k.Nj={"http://www.opengis.net/gml":{Point:sl(Em.prototype.df)}};k.Gj={"http://www.opengis.net/gml":{LineString:sl(Em.prototype.ff)}};k.Oj={"http://www.opengis.net/gml":{Polygon:sl(Em.prototype.gf)}}; -k.ke={"http://www.opengis.net/gml":{LinearRing:tl(Em.prototype.mp)}};k.Vi=function(a,b){var c=this.ef(a,[Fl(this,a,b?b:{})]);return c?c:null};k.Bc=function(a,b){var c={featureType:this.featureType,featureNS:this.featureNS};b&&qb(c,Fl(this,a,b));return this.ae(a,[c])||[]};k.hf=function(a){return Tb(this.srsName?this.srsName:a.firstElementChild.getAttribute("srsName"))};function Gm(a){a=ll(a,!1);return Hm(a)}function Hm(a){if(a=/^\s*(true|1)|(false|0)\s*$/.exec(a))return void 0!==a[1]||!1}function Im(a){a=ll(a,!1);a=Date.parse(a);return isNaN(a)?void 0:a/1E3}function Jm(a){a=ll(a,!1);return Km(a)}function Km(a){if(a=/^\s*([+\-]?\d*\.?\d+(?:e[+\-]?\d+)?)\s*$/i.exec(a))return parseFloat(a[1])}function Lm(a){a=ll(a,!1);return Mm(a)}function Mm(a){if(a=/^\s*(\d+)\s*$/.exec(a))return parseInt(a[1],10)}function R(a){return ll(a,!1).trim()} -function Nm(a,b){Om(a,b?"1":"0")}function Pm(a,b){a.appendChild(il.createTextNode(b.toPrecision()))}function Qm(a,b){a.appendChild(il.createTextNode(b.toString()))}function Om(a,b){a.appendChild(il.createTextNode(b))};function Rm(a){a=a?a:{};Em.call(this,a);this.o=void 0!==a.surface?a.surface:!1;this.c=void 0!==a.curve?a.curve:!1;this.f=void 0!==a.multiCurve?a.multiCurve:!0;this.j=void 0!==a.multiSurface?a.multiSurface:!0;this.schemaLocation=a.schemaLocation?a.schemaLocation:"http://www.opengis.net/gml http://schemas.opengis.net/gml/3.1.1/profiles/gmlsfProfile/1.0.0/gmlsf.xsd"}u(Rm,Em);k=Rm.prototype;k.qp=function(a,b){var c=M([],this.Hj,a,b,this);if(c){var d=new O(null);Nl(d,c);return d}}; -k.rp=function(a,b){var c=M([],this.Lj,a,b,this);if(c){var d=new Q(null);Pl(d,c);return d}};k.hh=function(a,b){Al(this.Dj,a,b,this)};k.wj=function(a,b){Al(this.Rj,a,b,this)};k.up=function(a,b){return M([null],this.Mj,a,b,this)};k.xp=function(a,b){return M([null],this.Qj,a,b,this)};k.vp=function(a,b){return M([null],this.xf,a,b,this)};k.pp=function(a,b){return M([null],this.je,a,b,this)};k.Yl=function(a,b){var c=M(void 0,this.ke,a,b,this);c&&b[b.length-1].push(c)}; -k.uk=function(a,b){var c=M(void 0,this.ke,a,b,this);c&&(b[b.length-1][0]=c)};k.aj=function(a,b){var c=M([null],this.Sj,a,b,this);if(c&&c[0]){var d=new F(null),e=c[0],f=[e.length],g,h;g=1;for(h=c.length;g<h;++g)ha(e,c[g]),f.push(e.length);d.ca("XYZ",e,f);return d}};k.Ti=function(a,b){var c=M([null],this.Ej,a,b,this);if(c){var d=new N(null);d.ca("XYZ",c);return d}};k.lp=function(a,b){var c=M([null],this.Fj,a,b,this);return Wa(c[1][0],c[1][1],c[2][0],c[2][1])}; -k.np=function(a,b){for(var c=ll(a,!1),d=/^\s*([+\-]?\d*\.?\d+(?:[eE][+\-]?\d+)?)\s*/,e=[],f;f=d.exec(c);)e.push(parseFloat(f[1])),c=c.substr(f[0].length);if(""===c){c=b[0].srsName;d="enu";c&&(d=Tb(c).b);if("neu"===d)for(c=0,d=e.length;c<d;c+=3)f=e[c],e[c]=e[c+1],e[c+1]=f;c=e.length;2==c&&e.push(0);if(c)return e}}; -k.vg=function(a,b){var c=ll(a,!1).replace(/^\s*|\s*$/g,""),d=b[0].srsName,e=a.parentNode.getAttribute("srsDimension"),f="enu";d&&(f=Tb(d).b);c=c.split(/\s+/);d=2;a.getAttribute("srsDimension")?d=Mm(a.getAttribute("srsDimension")):a.getAttribute("dimension")?d=Mm(a.getAttribute("dimension")):e&&(d=Mm(e));for(var g,h,l=[],m=0,n=c.length;m<n;m+=d)e=parseFloat(c[m]),g=parseFloat(c[m+1]),h=3===d?parseFloat(c[m+2]):0,"en"===f.substr(0,2)?l.push(e,g,h):l.push(g,e,h);return l}; -k.je={"http://www.opengis.net/gml":{pos:tl(Rm.prototype.np),posList:tl(Rm.prototype.vg)}};k.xf={"http://www.opengis.net/gml":{interior:Rm.prototype.Yl,exterior:Rm.prototype.uk}}; -k.Rg={"http://www.opengis.net/gml":{Point:tl(Em.prototype.$i),MultiPoint:tl(Em.prototype.Yi),LineString:tl(Em.prototype.ff),MultiLineString:tl(Em.prototype.Xi),LinearRing:tl(Em.prototype.Wi),Polygon:tl(Em.prototype.gf),MultiPolygon:tl(Em.prototype.Zi),Surface:tl(Rm.prototype.aj),MultiSurface:tl(Rm.prototype.rp),Curve:tl(Rm.prototype.Ti),MultiCurve:tl(Rm.prototype.qp),Envelope:tl(Rm.prototype.lp)}};k.Hj={"http://www.opengis.net/gml":{curveMember:sl(Rm.prototype.hh),curveMembers:sl(Rm.prototype.hh)}}; -k.Lj={"http://www.opengis.net/gml":{surfaceMember:sl(Rm.prototype.wj),surfaceMembers:sl(Rm.prototype.wj)}};k.Dj={"http://www.opengis.net/gml":{LineString:sl(Em.prototype.ff),Curve:sl(Rm.prototype.Ti)}};k.Rj={"http://www.opengis.net/gml":{Polygon:sl(Em.prototype.gf),Surface:sl(Rm.prototype.aj)}};k.Sj={"http://www.opengis.net/gml":{patches:tl(Rm.prototype.up)}};k.Ej={"http://www.opengis.net/gml":{segments:tl(Rm.prototype.xp)}};k.Fj={"http://www.opengis.net/gml":{lowerCorner:sl(Rm.prototype.vg),upperCorner:sl(Rm.prototype.vg)}}; -k.Mj={"http://www.opengis.net/gml":{PolygonPatch:tl(Rm.prototype.vp)}};k.Qj={"http://www.opengis.net/gml":{LineStringSegment:tl(Rm.prototype.pp)}};function Sm(a,b,c){c=c[c.length-1].srsName;b=b.W();for(var d=b.length,e=Array(d),f,g=0;g<d;++g){f=b[g];var h=g,l="enu";c&&(l=Tb(c).b);e[h]="en"===l.substr(0,2)?f[0]+" "+f[1]:f[1]+" "+f[0]}Om(a,e.join(" "))} -k.gi=function(a,b,c){var d=c[c.length-1].srsName;d&&a.setAttribute("srsName",d);d=kl(a.namespaceURI,"pos");a.appendChild(d);c=c[c.length-1].srsName;a="enu";c&&(a=Tb(c).b);b=b.W();Om(d,"en"===a.substr(0,2)?b[0]+" "+b[1]:b[1]+" "+b[0])};var Tm={"http://www.opengis.net/gml":{lowerCorner:K(Om),upperCorner:K(Om)}};k=Rm.prototype;k.cn=function(a,b,c){var d=c[c.length-1].srsName;d&&a.setAttribute("srsName",d);Bl({node:a},Tm,yl,[b[0]+" "+b[1],b[2]+" "+b[3]],c,["lowerCorner","upperCorner"],this)}; -k.di=function(a,b,c){var d=c[c.length-1].srsName;d&&a.setAttribute("srsName",d);d=kl(a.namespaceURI,"posList");a.appendChild(d);Sm(d,b,c)};k.bn=function(a,b){var c=b[b.length-1],d=c.node,e=c.exteriorWritten;void 0===e&&(c.exteriorWritten=!0);return kl(d.namespaceURI,void 0!==e?"interior":"exterior")}; -k.Re=function(a,b,c){var d=c[c.length-1].srsName;"PolygonPatch"!==a.nodeName&&d&&a.setAttribute("srsName",d);"Polygon"===a.nodeName||"PolygonPatch"===a.nodeName?(b=b.Oc(),Bl({node:a,srsName:d},Um,this.bn,b,c,void 0,this)):"Surface"===a.nodeName&&(d=kl(a.namespaceURI,"patches"),a.appendChild(d),a=kl(d.namespaceURI,"PolygonPatch"),d.appendChild(a),this.Re(a,b,c))}; -k.Qe=function(a,b,c){var d=c[c.length-1].srsName;"LineStringSegment"!==a.nodeName&&d&&a.setAttribute("srsName",d);"LineString"===a.nodeName||"LineStringSegment"===a.nodeName?(d=kl(a.namespaceURI,"posList"),a.appendChild(d),Sm(d,b,c)):"Curve"===a.nodeName&&(d=kl(a.namespaceURI,"segments"),a.appendChild(d),a=kl(d.namespaceURI,"LineStringSegment"),d.appendChild(a),this.Qe(a,b,c))}; -k.fi=function(a,b,c){var d=c[c.length-1],e=d.srsName,d=d.surface;e&&a.setAttribute("srsName",e);b=b.md();Bl({node:a,srsName:e,surface:d},Vm,this.l,b,c,void 0,this)};k.dn=function(a,b,c){var d=c[c.length-1].srsName;d&&a.setAttribute("srsName",d);b=b.Zd();Bl({node:a,srsName:d},Wm,wl("pointMember"),b,c,void 0,this)};k.ei=function(a,b,c){var d=c[c.length-1],e=d.srsName,d=d.curve;e&&a.setAttribute("srsName",e);b=b.Nc();Bl({node:a,srsName:e,curve:d},Xm,this.l,b,c,void 0,this)}; -k.hi=function(a,b,c){var d=kl(a.namespaceURI,"LinearRing");a.appendChild(d);this.di(d,b,c)};k.ii=function(a,b,c){var d=this.a(b,c);d&&(a.appendChild(d),this.Re(d,b,c))};k.en=function(a,b,c){var d=kl(a.namespaceURI,"Point");a.appendChild(d);this.gi(d,b,c)};k.ci=function(a,b,c){var d=this.a(b,c);d&&(a.appendChild(d),this.Qe(d,b,c))}; -k.rd=function(a,b,c){var d=c[c.length-1],e=qb({},d);e.node=a;var f;Array.isArray(b)?d.dataProjection?f=gc(b,d.featureProjection,d.dataProjection):f=b:f=Hl(b,!0,d);Bl(e,Ym,this.a,[f],c,void 0,this)}; -k.bi=function(a,b,c){var d=b.a;d&&a.setAttribute("fid",d);var d=c[c.length-1],e=d.featureNS,f=b.c;d.kb||(d.kb={},d.kb[e]={});var g=b.M();b=[];var h=[],l;for(l in g){var m=g[l];null!==m&&(b.push(l),h.push(m),l==f||m instanceof lf?l in d.kb[e]||(d.kb[e][l]=K(this.rd,this)):l in d.kb[e]||(d.kb[e][l]=K(Om)))}l=qb({},d);l.node=a;Bl(l,d.kb,wl(void 0,e),h,c,b)}; -var Vm={"http://www.opengis.net/gml":{surfaceMember:K(Rm.prototype.ii),polygonMember:K(Rm.prototype.ii)}},Wm={"http://www.opengis.net/gml":{pointMember:K(Rm.prototype.en)}},Xm={"http://www.opengis.net/gml":{lineStringMember:K(Rm.prototype.ci),curveMember:K(Rm.prototype.ci)}},Um={"http://www.opengis.net/gml":{exterior:K(Rm.prototype.hi),interior:K(Rm.prototype.hi)}},Ym={"http://www.opengis.net/gml":{Curve:K(Rm.prototype.Qe),MultiCurve:K(Rm.prototype.ei),Point:K(Rm.prototype.gi),MultiPoint:K(Rm.prototype.dn), -LineString:K(Rm.prototype.Qe),MultiLineString:K(Rm.prototype.ei),LinearRing:K(Rm.prototype.di),Polygon:K(Rm.prototype.Re),MultiPolygon:K(Rm.prototype.fi),Surface:K(Rm.prototype.Re),MultiSurface:K(Rm.prototype.fi),Envelope:K(Rm.prototype.cn)}},Zm={MultiLineString:"lineStringMember",MultiCurve:"curveMember",MultiPolygon:"polygonMember",MultiSurface:"surfaceMember"};Rm.prototype.l=function(a,b){return kl("http://www.opengis.net/gml",Zm[b[b.length-1].node.nodeName])}; -Rm.prototype.a=function(a,b){var c=b[b.length-1],d=c.multiSurface,e=c.surface,f=c.curve,c=c.multiCurve,g;Array.isArray(a)?g="Envelope":(g=a.S(),"MultiPolygon"===g&&!0===d?g="MultiSurface":"Polygon"===g&&!0===e?g="Surface":"LineString"===g&&!0===f?g="Curve":"MultiLineString"===g&&!0===c&&(g="MultiCurve"));return kl("http://www.opengis.net/gml",g)}; -Rm.prototype.he=function(a,b){b=Gl(this,b);var c=kl("http://www.opengis.net/gml","geom"),d={node:c,srsName:this.srsName,curve:this.c,surface:this.o,multiSurface:this.j,multiCurve:this.f};b&&qb(d,b);this.rd(c,a,[d]);return c}; -Rm.prototype.Zb=function(a,b){b=Gl(this,b);var c=kl("http://www.opengis.net/gml","featureMembers");c.setAttributeNS("http://www.w3.org/2001/XMLSchema-instance","xsi:schemaLocation",this.schemaLocation);var d={srsName:this.srsName,curve:this.c,surface:this.o,multiSurface:this.j,multiCurve:this.f,featureNS:this.featureNS,featureType:this.featureType};b&&qb(d,b);var d=[d],e=d[d.length-1],f=e.featureType,g=e.featureNS,h={};h[g]={};h[g][f]=K(this.bi,this);e=qb({},e);e.node=c;Bl(e,h,wl(f,g),a,d);return c};function $m(a){a=a?a:{};Em.call(this,a);this.b["http://www.opengis.net/gml"].featureMember=sl(Em.prototype.ae);this.schemaLocation=a.schemaLocation?a.schemaLocation:"http://www.opengis.net/gml http://schemas.opengis.net/gml/2.1.2/feature.xsd"}u($m,Em);k=$m.prototype; -k.Ui=function(a,b){var c=ll(a,!1).replace(/^\s*|\s*$/g,""),d=b[0].srsName,e="enu";d&&(d=Tb(d))&&(e=d.b);for(var c=c.trim().split(/\s+/),f,g,h=[],l=0,m=c.length;l<m;l++)g=c[l].split(/,+/),d=parseFloat(g[0]),f=parseFloat(g[1]),g=3===g.length?parseFloat(g[2]):0,"en"===e.substr(0,2)?h.push(d,f,g):h.push(f,d,g);return h};k.jp=function(a,b){var c=M([null],this.Cj,a,b,this);return Wa(c[1][0],c[1][1],c[1][3],c[1][4])};k.Wl=function(a,b){var c=M(void 0,this.ke,a,b,this);c&&b[b.length-1].push(c)}; -k.So=function(a,b){var c=M(void 0,this.ke,a,b,this);c&&(b[b.length-1][0]=c)};k.je={"http://www.opengis.net/gml":{coordinates:tl($m.prototype.Ui)}};k.xf={"http://www.opengis.net/gml":{innerBoundaryIs:$m.prototype.Wl,outerBoundaryIs:$m.prototype.So}};k.Cj={"http://www.opengis.net/gml":{coordinates:sl($m.prototype.Ui)}}; -k.Rg={"http://www.opengis.net/gml":{Point:tl(Em.prototype.$i),MultiPoint:tl(Em.prototype.Yi),LineString:tl(Em.prototype.ff),MultiLineString:tl(Em.prototype.Xi),LinearRing:tl(Em.prototype.Wi),Polygon:tl(Em.prototype.gf),MultiPolygon:tl(Em.prototype.Zi),Box:tl($m.prototype.jp)}}; -k.eg=function(a,b){var c=b[b.length-1],d=c.multiSurface,e=c.surface,c=c.multiCurve,f;Array.isArray(a)?f="Envelope":(f=a.S(),"MultiPolygon"===f&&!0===d?f="MultiSurface":"Polygon"===f&&!0===e?f="Surface":"MultiLineString"===f&&!0===c&&(f="MultiCurve"));return kl("http://www.opengis.net/gml",f)};k.Uh=function(a,b,c){var d=c[c.length-1],e=qb({},d);e.node=a;var f;Array.isArray(b)?d.dataProjection?f=gc(b,d.featureProjection,d.dataProjection):f=b:f=Hl(b,!0,d);Bl(e,an,this.eg,[f],c,void 0,this)}; -k.Oe=function(a,b,c){var d=c[c.length-1].srsName;"LineStringSegment"!==a.nodeName&&d&&a.setAttribute("srsName",d);"LineString"===a.nodeName||"LineStringSegment"===a.nodeName?(d=bn(a.namespaceURI),a.appendChild(d),cn(d,b,c)):"Curve"===a.nodeName&&(d=kl(a.namespaceURI,"segments"),a.appendChild(d),a=kl(d.namespaceURI,"LineStringSegment"),d.appendChild(a),this.Oe(a,b,c))};function bn(a){a=kl(a,"coordinates");a.setAttribute("decimal",".");a.setAttribute("cs",",");a.setAttribute("ts"," ");return a} -function cn(a,b,c){c=c[c.length-1].srsName;b=b.W();for(var d=b.length,e=Array(d),f,g=0;g<d;++g)f=b[g],e[g]=dn(f,c);Om(a,e.join(" "))}k.Pe=function(a,b,c){var d=c[c.length-1].srsName;"PolygonPatch"!==a.nodeName&&d&&a.setAttribute("srsName",d);"Polygon"===a.nodeName||"PolygonPatch"===a.nodeName?(b=b.Oc(),Bl({node:a,srsName:d},en,this.Ym,b,c,void 0,this)):"Surface"===a.nodeName&&(d=kl(a.namespaceURI,"patches"),a.appendChild(d),a=kl(d.namespaceURI,"PolygonPatch"),d.appendChild(a),this.Pe(a,b,c))}; -k.Ym=function(a,b){var c=b[b.length-1],d=c.node,e=c.exteriorWritten;void 0===e&&(c.exteriorWritten=!0);return kl(d.namespaceURI,void 0!==e?"innerBoundaryIs":"outerBoundaryIs")};k.$h=function(a,b,c){var d=kl(a.namespaceURI,"LinearRing");a.appendChild(d);this.Wh(d,b,c)};function dn(a,b){var c="enu";b&&(c=Tb(b).b);return"en"===c.substr(0,2)?a[0]+","+a[1]:a[1]+","+a[0]} -k.Xh=function(a,b,c){var d=c[c.length-1],e=d.srsName,d=d.curve;e&&a.setAttribute("srsName",e);b=b.Nc();Bl({node:a,srsName:e,curve:d},fn,this.a,b,c,void 0,this)};k.Zh=function(a,b,c){var d=c[c.length-1].srsName;d&&a.setAttribute("srsName",d);c=bn(a.namespaceURI);a.appendChild(c);a=b.W();a=dn(a,d);Om(c,a)};k.$m=function(a,b,c){var d=c[c.length-1].srsName;d&&a.setAttribute("srsName",d);b=b.Zd();Bl({node:a,srsName:d},gn,wl("pointMember"),b,c,void 0,this)}; -k.an=function(a,b,c){var d=kl(a.namespaceURI,"Point");a.appendChild(d);this.Zh(d,b,c)};k.Vh=function(a,b,c){var d=this.eg(b,c);d&&(a.appendChild(d),this.Oe(d,b,c))};k.Wh=function(a,b,c){var d=c[c.length-1].srsName;d&&a.setAttribute("srsName",d);d=bn(a.namespaceURI);a.appendChild(d);cn(d,b,c)};k.Yh=function(a,b,c){var d=c[c.length-1],e=d.srsName,d=d.surface;e&&a.setAttribute("srsName",e);b=b.md();Bl({node:a,srsName:e,surface:d},hn,this.a,b,c,void 0,this)}; -k.ai=function(a,b,c){var d=this.eg(b,c);d&&(a.appendChild(d),this.Pe(d,b,c))};k.Zm=function(a,b,c){var d=c[c.length-1].srsName;d&&a.setAttribute("srsName",d);Bl({node:a},jn,yl,[b[0]+" "+b[1],b[2]+" "+b[3]],c,["lowerCorner","upperCorner"],this)}; -var an={"http://www.opengis.net/gml":{Curve:K($m.prototype.Oe),MultiCurve:K($m.prototype.Xh),Point:K($m.prototype.Zh),MultiPoint:K($m.prototype.$m),LineString:K($m.prototype.Oe),MultiLineString:K($m.prototype.Xh),LinearRing:K($m.prototype.Wh),Polygon:K($m.prototype.Pe),MultiPolygon:K($m.prototype.Yh),Surface:K($m.prototype.Pe),MultiSurface:K($m.prototype.Yh),Envelope:K($m.prototype.Zm)}},en={"http://www.opengis.net/gml":{outerBoundaryIs:K($m.prototype.$h),innerBoundaryIs:K($m.prototype.$h)}},gn={"http://www.opengis.net/gml":{pointMember:K($m.prototype.an)}}, -fn={"http://www.opengis.net/gml":{lineStringMember:K($m.prototype.Vh),curveMember:K($m.prototype.Vh)}};$m.prototype.a=function(a,b){return kl("http://www.opengis.net/gml",kn[b[b.length-1].node.nodeName])};var kn={MultiLineString:"lineStringMember",MultiCurve:"curveMember",MultiPolygon:"polygonMember",MultiSurface:"surfaceMember"},hn={"http://www.opengis.net/gml":{surfaceMember:K($m.prototype.ai),polygonMember:K($m.prototype.ai)}},jn={"http://www.opengis.net/gml":{lowerCorner:K(Om),upperCorner:K(Om)}};function ln(a){a=a?a:{};Bm.call(this);this.defaultDataProjection=Tb("EPSG:4326");this.b=a.readExtensions}u(ln,Bm);var mn=[null,"http://www.topografix.com/GPX/1/0","http://www.topografix.com/GPX/1/1"];function nn(a,b,c,d){a.push(parseFloat(c.getAttribute("lon")),parseFloat(c.getAttribute("lat")));"ele"in d?(a.push(d.ele),delete d.ele,b.hasZ=!0):a.push(0);"time"in d?(a.push(d.time),delete d.time,b.hasM=!0):a.push(0);return a} -function on(a,b,c){var d="XY",e=2;a.hasZ&&a.hasM?(d="XYZM",e=4):a.hasZ?(d="XYZ",e=3):a.hasM&&(d="XYM",e=3);if(4!==e){var f,g;f=0;for(g=b.length/4;f<g;f++)b[f*e]=b[4*f],b[f*e+1]=b[4*f+1],a.hasZ&&(b[f*e+2]=b[4*f+2]),a.hasM&&(b[f*e+2]=b[4*f+3]);b.length=b.length/4*e;if(c)for(f=0,g=c.length;f<g;f++)c[f]=c[f]/4*e}return d}function pn(a,b){var c=b[b.length-1],d=a.getAttribute("href");null!==d&&(c.link=d);Al(qn,a,b)}function rn(a,b){b[b.length-1].extensionsNode_=a} -function sn(a,b){var c=b[0],d=M({flatCoordinates:[],layoutOptions:{}},tn,a,b);if(d){var e=d.flatCoordinates;delete d.flatCoordinates;var f=d.layoutOptions;delete d.layoutOptions;var f=on(f,e),g=new N(null);g.ca(f,e);Hl(g,!1,c);c=new I(g);c.H(d);return c}} -function un(a,b){var c=b[0],d=M({flatCoordinates:[],ends:[],layoutOptions:{}},vn,a,b);if(d){var e=d.flatCoordinates;delete d.flatCoordinates;var f=d.ends;delete d.ends;var g=d.layoutOptions;delete d.layoutOptions;var g=on(g,e,f),h=new O(null);h.ca(g,e,f);Hl(h,!1,c);c=new I(h);c.H(d);return c}}function wn(a,b){var c=b[0],d=M({},xn,a,b);if(d){var e={},f=nn([],e,a,d),e=on(e,f),f=new E(f,e);Hl(f,!1,c);c=new I(f);c.H(d);return c}} -var yn={rte:sn,trk:un,wpt:wn},zn=L(mn,{rte:sl(sn),trk:sl(un),wpt:sl(wn)}),qn=L(mn,{text:J(R,"linkText"),type:J(R,"linkType")}),tn=L(mn,{name:J(R),cmt:J(R),desc:J(R),src:J(R),link:pn,number:J(Lm),extensions:rn,type:J(R),rtept:function(a,b){var c=M({},An,a,b);if(c){var d=b[b.length-1];nn(d.flatCoordinates,d.layoutOptions,a,c)}}}),An=L(mn,{ele:J(Jm),time:J(Im)}),vn=L(mn,{name:J(R),cmt:J(R),desc:J(R),src:J(R),link:pn,number:J(Lm),type:J(R),extensions:rn,trkseg:function(a,b){var c=b[b.length-1];Al(Bn, -a,b);c.ends.push(c.flatCoordinates.length)}}),Bn=L(mn,{trkpt:function(a,b){var c=M({},Cn,a,b);if(c){var d=b[b.length-1];nn(d.flatCoordinates,d.layoutOptions,a,c)}}}),Cn=L(mn,{ele:J(Jm),time:J(Im)}),xn=L(mn,{ele:J(Jm),time:J(Im),magvar:J(Jm),geoidheight:J(Jm),name:J(R),cmt:J(R),desc:J(R),src:J(R),link:pn,sym:J(R),type:J(R),fix:J(R),sat:J(Lm),hdop:J(Jm),vdop:J(Jm),pdop:J(Jm),ageofdgpsdata:J(Jm),dgpsid:J(Lm),extensions:rn}); -function Dn(a,b){b||(b=[]);for(var c=0,d=b.length;c<d;++c){var e=b[c];if(a.b){var f=e.get("extensionsNode_")||null;a.b(e,f)}e.set("extensionsNode_",void 0)}}ln.prototype.rg=function(a,b){if(!fa(mn,a.namespaceURI))return null;var c=yn[a.localName];if(!c)return null;c=c(a,[Fl(this,a,b)]);if(!c)return null;Dn(this,[c]);return c};ln.prototype.Bc=function(a,b){if(!fa(mn,a.namespaceURI))return[];if("gpx"==a.localName){var c=M([],zn,a,[Fl(this,a,b)]);if(c)return Dn(this,c),c}return[]}; -function En(a,b,c){a.setAttribute("href",b);b=c[c.length-1].properties;Bl({node:a},Fn,yl,[b.linkText,b.linkType],c,Gn)}function Hn(a,b,c){var d=c[c.length-1],e=d.node.namespaceURI,f=d.properties;a.setAttributeNS(null,"lat",b[1]);a.setAttributeNS(null,"lon",b[0]);switch(d.geometryLayout){case "XYZM":b[3]&&(f.time=b[3]);case "XYZ":b[2]&&(f.ele=b[2]);break;case "XYM":b[2]&&(f.time=b[2])}b="rtept"==a.nodeName?In[e]:Jn[e];d=zl(f,b);Bl({node:a,properties:f},Kn,yl,d,c,b)} -var Gn=["text","type"],Fn=L(mn,{text:K(Om),type:K(Om)}),Ln=L(mn,"name cmt desc src link number type rtept".split(" ")),Mn=L(mn,{name:K(Om),cmt:K(Om),desc:K(Om),src:K(Om),link:K(En),number:K(Qm),type:K(Om),rtept:vl(K(Hn))}),In=L(mn,["ele","time"]),Nn=L(mn,"name cmt desc src link number type trkseg".split(" ")),Qn=L(mn,{name:K(Om),cmt:K(Om),desc:K(Om),src:K(Om),link:K(En),number:K(Qm),type:K(Om),trkseg:vl(K(function(a,b,c){Bl({node:a,geometryLayout:b.la,properties:{}},On,Pn,b.W(),c)}))}),Pn=wl("trkpt"), -On=L(mn,{trkpt:K(Hn)}),Jn=L(mn,"ele time magvar geoidheight name cmt desc src link sym type fix sat hdop vdop pdop ageofdgpsdata dgpsid".split(" ")),Kn=L(mn,{ele:K(Pm),time:K(function(a,b){var c=new Date(1E3*b);a.appendChild(il.createTextNode(c.getUTCFullYear()+"-"+Ve(c.getUTCMonth()+1)+"-"+Ve(c.getUTCDate())+"T"+Ve(c.getUTCHours())+":"+Ve(c.getUTCMinutes())+":"+Ve(c.getUTCSeconds())+"Z"))}),magvar:K(Pm),geoidheight:K(Pm),name:K(Om),cmt:K(Om),desc:K(Om),src:K(Om),link:K(En),sym:K(Om),type:K(Om),fix:K(Om), -sat:K(Qm),hdop:K(Pm),vdop:K(Pm),pdop:K(Pm),ageofdgpsdata:K(Pm),dgpsid:K(Qm)}),Rn={Point:"wpt",LineString:"rte",MultiLineString:"trk"};function Sn(a,b){var c=a.U();if(c&&(c=Rn[c.S()]))return kl(b[b.length-1].node.namespaceURI,c)} -var Tn=L(mn,{rte:K(function(a,b,c){var d=c[0],e=b.M();a={node:a,properties:e};if(b=b.U())b=Hl(b,!0,d),a.geometryLayout=b.la,e.rtept=b.W();d=Ln[c[c.length-1].node.namespaceURI];e=zl(e,d);Bl(a,Mn,yl,e,c,d)}),trk:K(function(a,b,c){var d=c[0],e=b.M();a={node:a,properties:e};if(b=b.U())b=Hl(b,!0,d),e.trkseg=b.Nc();d=Nn[c[c.length-1].node.namespaceURI];e=zl(e,d);Bl(a,Qn,yl,e,c,d)}),wpt:K(function(a,b,c){var d=c[0],e=c[c.length-1];e.properties=b.M();if(b=b.U())b=Hl(b,!0,d),e.geometryLayout=b.la,Hn(a,b.W(), -c)})});ln.prototype.Zb=function(a,b){b=Gl(this,b);var c=kl("http://www.topografix.com/GPX/1/1","gpx");c.setAttributeNS("http://www.w3.org/2000/xmlns/","xmlns:xsi","http://www.w3.org/2001/XMLSchema-instance");c.setAttributeNS("http://www.w3.org/2001/XMLSchema-instance","xsi:schemaLocation","http://www.topografix.com/GPX/1/1 http://www.topografix.com/GPX/1/1/gpx.xsd");c.setAttribute("version","1.1");c.setAttribute("creator","OpenLayers");Bl({node:c},Tn,Sn,a,[b]);return c};function Un(){El.call(this)}u(Un,El);function Vn(a){return"string"===typeof a?a:""}k=Un.prototype;k.S=function(){return"text"};k.Vb=function(a,b){return this.$d(Vn(a),Gl(this,b))};k.Pa=function(a,b){return this.tg(Vn(a),Gl(this,b))};k.Xc=function(a,b){return this.yd(Vn(a),Gl(this,b))};k.jb=function(){return this.defaultDataProjection};k.Dd=function(a,b){return this.fe(a,Gl(this,b))};k.Yb=function(a,b){return this.Og(a,Gl(this,b))};k.ed=function(a,b){return this.Ed(a,Gl(this,b))};function Wn(a){a=a?a:{};El.call(this);this.defaultDataProjection=Tb("EPSG:4326");this.b=a.altitudeMode?a.altitudeMode:"none"}u(Wn,Un);var Xn=/^B(\d{2})(\d{2})(\d{2})(\d{2})(\d{5})([NS])(\d{3})(\d{5})([EW])([AV])(\d{5})(\d{5})/,Yn=/^H.([A-Z]{3}).*?:(.*)/,Zn=/^HFDTE(\d{2})(\d{2})(\d{2})/,$n=/\r\n|\r|\n/;k=Wn.prototype; -k.$d=function(a,b){var c=this.b,d=a.split($n),e={},f=[],g=2E3,h=0,l=1,m=-1,n,p;n=0;for(p=d.length;n<p;++n){var q=d[n],r;if("B"==q.charAt(0)){if(r=Xn.exec(q)){var q=parseInt(r[1],10),v=parseInt(r[2],10),x=parseInt(r[3],10),y=parseInt(r[4],10)+parseInt(r[5],10)/6E4;"S"==r[6]&&(y=-y);var A=parseInt(r[7],10)+parseInt(r[8],10)/6E4;"W"==r[9]&&(A=-A);f.push(A,y);"none"!=c&&f.push("gps"==c?parseInt(r[11],10):"barometric"==c?parseInt(r[12],10):0);r=Date.UTC(g,h,l,q,v,x);r<m&&(r=Date.UTC(g,h,l+1,q,v,x));f.push(r/ -1E3);m=r}}else"H"==q.charAt(0)&&((r=Zn.exec(q))?(l=parseInt(r[1],10),h=parseInt(r[2],10)-1,g=2E3+parseInt(r[3],10)):(r=Yn.exec(q))&&(e[r[1]]=r[2].trim()))}if(!f.length)return null;d=new N(null);d.ca("none"==c?"XYM":"XYZM",f);c=new I(Hl(d,!1,b));c.H(e);return c};k.tg=function(a,b){var c=this.$d(a,b);return c?[c]:[]};k.fe=function(){};k.Og=function(){};k.Ed=function(){};k.yd=function(){};function ao(a,b,c,d,e,f){Nc.call(this);this.j=null;this.N=a?a:new Image;null!==d&&(this.N.crossOrigin=d);this.c=f?document.createElement("CANVAS"):null;this.f=f;this.i=null;this.g=e;this.a=c;this.l=b;this.o=!1;2==this.g&&bo(this)}u(ao,Nc);function bo(a){var b=hd(1,1);try{b.drawImage(a.N,0,0),b.getImageData(0,0,1,1)}catch(c){a.o=!0}}ao.prototype.u=function(){this.g=3;this.i.forEach(Bc);this.i=null;this.b("change")}; -ao.prototype.v=function(){this.g=2;this.a&&(this.N.width=this.a[0],this.N.height=this.a[1]);this.a=[this.N.width,this.N.height];this.i.forEach(Bc);this.i=null;bo(this);if(!this.o&&null!==this.f){this.c.width=this.N.width;this.c.height=this.N.height;var a=this.c.getContext("2d");a.drawImage(this.N,0,0);for(var b=a.getImageData(0,0,this.N.width,this.N.height),c=b.data,d=this.f[0]/255,e=this.f[1]/255,f=this.f[2]/255,g=0,h=c.length;g<h;g+=4)c[g]*=d,c[g+1]*=e,c[g+2]*=f;a.putImageData(b,0,0)}this.b("change")}; -ao.prototype.Y=function(){return this.c?this.c:this.N};ao.prototype.load=function(){if(0==this.g){this.g=1;this.i=[Gc(this.N,"error",this.u,this),Gc(this.N,"load",this.v,this)];try{this.N.src=this.l}catch(a){this.u()}}};function co(a){a=a||{};this.l=void 0!==a.anchor?a.anchor:[.5,.5];this.v=null;this.a=void 0!==a.anchorOrigin?a.anchorOrigin:"top-left";this.C=void 0!==a.anchorXUnits?a.anchorXUnits:"fraction";this.G=void 0!==a.anchorYUnits?a.anchorYUnits:"fraction";this.ta=void 0!==a.crossOrigin?a.crossOrigin:null;var b=void 0!==a.img?a.img:null,c=void 0!==a.imgSize?a.imgSize:null,d=a.src;sa(!(void 0!==d&&b),4);sa(!b||b&&c,5);void 0!==d&&d.length||!b||(d=b.src||w(b).toString());sa(void 0!==d&&0<d.length,6);var e=void 0!== -a.src?0:2;this.i=void 0!==a.color?bd(a.color):null;var f=this.ta,g=this.i,h=wh.get(d,f,g);h||(h=new ao(b,d,c,f,e,g),wh.set(d,f,g,h));this.b=h;this.qa=void 0!==a.offset?a.offset:[0,0];this.g=void 0!==a.offsetOrigin?a.offsetOrigin:"top-left";this.O=null;this.A=void 0!==a.size?a.size:null;Xk.call(this,{opacity:void 0!==a.opacity?a.opacity:1,rotation:void 0!==a.rotation?a.rotation:0,scale:void 0!==a.scale?a.scale:1,snapToPixel:void 0!==a.snapToPixel?a.snapToPixel:!0,rotateWithView:void 0!==a.rotateWithView? -a.rotateWithView:!1})}u(co,Xk);k=co.prototype; -k.clone=function(){var a=this.Y(1),b;if(2===this.b.g)if("IMG"===a.tagName.toUpperCase())b=a.cloneNode(!0);else{b=document.createElement("canvas");var c=b.getContext("2d");b.width=a.width;b.height=a.height;c.drawImage(a,0,0)}return new co({anchor:this.l.slice(),anchorOrigin:this.a,anchorXUnits:this.C,anchorYUnits:this.G,crossOrigin:this.ta,color:this.i&&this.i.slice?this.i.slice():this.i||void 0,img:b?b:void 0,imgSize:b?this.b.a.slice():void 0,src:b?void 0:this.b.l,offset:this.qa.slice(),offsetOrigin:this.g, -size:null!==this.A?this.A.slice():void 0,opacity:this.f,scale:this.c,snapToPixel:this.u,rotation:this.j,rotateWithView:this.o})}; -k.Jc=function(){if(this.v)return this.v;var a=this.l,b=this.kc();if("fraction"==this.C||"fraction"==this.G){if(!b)return null;a=this.l.slice();"fraction"==this.C&&(a[0]*=b[0]);"fraction"==this.G&&(a[1]*=b[1])}if("top-left"!=this.a){if(!b)return null;a===this.l&&(a=this.l.slice());if("top-right"==this.a||"bottom-right"==this.a)a[0]=-a[0]+b[0];if("bottom-left"==this.a||"bottom-right"==this.a)a[1]=-a[1]+b[1]}return this.v=a};k.Bo=function(){return this.i};k.Y=function(a){return this.b.Y(a)};k.ye=function(){return this.b.a}; -k.Xe=function(){return this.b.g};k.kg=function(){var a=this.b;if(!a.j)if(a.o){var b=a.a[0],c=a.a[1],d=hd(b,c);d.fillRect(0,0,b,c);a.j=d.canvas}else a.j=a.N;return a.j};k.Tc=function(){if(this.O)return this.O;var a=this.qa;if("top-left"!=this.g){var b=this.kc(),c=this.b.a;if(!b||!c)return null;a=a.slice();if("top-right"==this.g||"bottom-right"==this.g)a[0]=c[0]-b[0]-a[0];if("bottom-left"==this.g||"bottom-right"==this.g)a[1]=c[1]-b[1]-a[1]}return this.O=a};k.Co=function(){return this.b.l}; -k.kc=function(){return this.A?this.A:this.b.a};k.Gh=function(a,b){return z(this.b,"change",a,b)};k.load=function(){this.b.load()};k.xj=function(a,b){Hc(this.b,"change",a,b)};function eo(a){a=a||{};this.a=a.font;this.i=a.rotation;this.l=a.rotateWithView;this.b=a.scale;this.Fa=a.text;this.f=a.textAlign;this.j=a.textBaseline;this.Wa=void 0!==a.fill?a.fill:new al({color:"#333"});this.Za=void 0!==a.stroke?a.stroke:null;this.g=void 0!==a.offsetX?a.offsetX:0;this.c=void 0!==a.offsetY?a.offsetY:0}k=eo.prototype; -k.clone=function(){return new eo({font:this.a,rotation:this.i,rotateWithView:this.l,scale:this.b,text:this.Oa(),textAlign:this.f,textBaseline:this.j,fill:this.Ca()?this.Ca().clone():void 0,stroke:this.Da()?this.Da().clone():void 0,offsetX:this.g,offsetY:this.c})};k.Jk=function(){return this.a};k.Yk=function(){return this.g};k.Zk=function(){return this.c};k.Ca=function(){return this.Wa};k.Ho=function(){return this.l};k.Io=function(){return this.i};k.Jo=function(){return this.b};k.Da=function(){return this.Za}; -k.Oa=function(){return this.Fa};k.il=function(){return this.f};k.jl=function(){return this.j};k.ij=function(a){this.a=a};k.oj=function(a){this.g=a};k.pj=function(a){this.c=a};k.mf=function(a){this.Wa=a};k.Ko=function(a){this.i=a};k.Mi=function(a){this.b=a};k.nf=function(a){this.Za=a};k.pf=function(a){this.Fa=a};k.rj=function(a){this.f=a};k.Xp=function(a){this.j=a};function fo(a){a=a?a:{};Bm.call(this);go||(ho=[255,255,255,1],io=new al({color:ho}),jo=[20,2],ko=lo="pixels",mo=[64,64],no="https://maps.google.com/mapfiles/kml/pushpin/ylw-pushpin.png",oo=.5,po=new co({anchor:jo,anchorOrigin:"bottom-left",anchorXUnits:lo,anchorYUnits:ko,crossOrigin:"anonymous",rotation:0,scale:oo,size:mo,src:no}),qo="NO_IMAGE",ro=new tj({color:ho,width:1}),so=new tj({color:[51,51,51,1],width:2}),to=new eo({font:"bold 16px Helvetica",fill:io,stroke:so,scale:.8}),uo=new bl({fill:io, -image:po,text:to,stroke:ro,zIndex:0}),go=[uo]);this.defaultDataProjection=Tb("EPSG:4326");this.a=a.defaultStyle?a.defaultStyle:go;this.c=void 0!==a.extractStyles?a.extractStyles:!0;this.j=void 0!==a.writeStyles?a.writeStyles:!0;this.b={};this.f=void 0!==a.showPointNames?a.showPointNames:!0}var go,ho,io,jo,lo,ko,mo,no,oo,po,qo,ro,so,to,uo;u(fo,Bm); -var vo=["http://www.google.com/kml/ext/2.2"],wo=[null,"http://earth.google.com/kml/2.0","http://earth.google.com/kml/2.1","http://earth.google.com/kml/2.2","http://www.opengis.net/kml/2.2"],xo={fraction:"fraction",pixels:"pixels"}; -function yo(a,b){var c,d=[0,0],e="start";a.Y()&&(c=a.Y().ye(),null===c&&(c=mo),2==c.length&&(e=a.Y().c,d[0]=e*c[0]/2,d[1]=-e*c[1]/2,e="left"));if(null!==a.Oa()){var f=a.Oa();c=f.clone();c.ij(f.a||to.a);c.Mi(f.b||to.b);c.mf(f.Ca()||to.Ca());c.nf(f.Da()||so)}else c=to.clone();c.pf(b);c.oj(d[0]);c.pj(d[1]);c.rj(e);return new bl({text:c})} -function zo(a,b,c,d,e){return function(){var f=e,g="";f&&this.U()&&(f="Point"===this.U().S());f&&(g=this.get("name"),f=f&&g);if(a)return f?(f=yo(a[0],g),a.concat(f)):a;if(b){var h=Ao(b,c,d);return f?(f=yo(h[0],g),h.concat(f)):h}return f?(f=yo(c[0],g),c.concat(f)):c}}function Ao(a,b,c){return Array.isArray(a)?a:"string"===typeof a?(!(a in c)&&"#"+a in c&&(a="#"+a),Ao(c[a],b,c)):b} -function Bo(a){a=ll(a,!1);if(a=/^\s*#?\s*([0-9A-Fa-f]{8})\s*$/.exec(a))return a=a[1],[parseInt(a.substr(6,2),16),parseInt(a.substr(4,2),16),parseInt(a.substr(2,2),16),parseInt(a.substr(0,2),16)/255]}function Co(a){a=ll(a,!1);for(var b=[],c=/^\s*([+\-]?\d*\.?\d+(?:e[+\-]?\d+)?)\s*,\s*([+\-]?\d*\.?\d+(?:e[+\-]?\d+)?)(?:\s*,\s*([+\-]?\d*\.?\d+(?:e[+\-]?\d+)?))?\s*/i,d;d=c.exec(a);)b.push(parseFloat(d[1]),parseFloat(d[2]),d[3]?parseFloat(d[3]):0),a=a.substr(d[0].length);if(""===a)return b} -function Do(a){var b=ll(a,!1).trim();return a.baseURI?(new URL(b,a.baseURI)).href:b}function Eo(a){return Jm(a)}function Fo(a,b){return M(null,Go,a,b)}function Ho(a,b){var c=M({B:[],Aj:[]},Io,a,b);if(c){var d=c.B,c=c.Aj,e,f;e=0;for(f=Math.min(d.length,c.length);e<f;++e)d[4*e+3]=c[e];c=new N(null);c.ca("XYZM",d);return c}}function Jo(a,b){var c=M({},Ko,a,b),d=M(null,Lo,a,b);if(d){var e=new N(null);e.ca("XYZ",d);e.H(c);return e}} -function Mo(a,b){var c=M({},Ko,a,b),d=M(null,Lo,a,b);if(d){var e=new F(null);e.ca("XYZ",d,[d.length]);e.H(c);return e}} -function No(a,b){var c=M([],Oo,a,b);if(!c)return null;if(!c.length)return new sm(c);var d,e=!0,f=c[0].S(),g,h,l;h=1;for(l=c.length;h<l;++h)if(g=c[h],g.S()!=f){e=!1;break}if(e)if("Point"==f){d=c[0];e=d.la;f=d.ia();h=1;for(l=c.length;h<l;++h)g=c[h],ha(f,g.ia());d=new P(null);d.ca(e,f);Po(d,c)}else"LineString"==f?(d=new O(null),Nl(d,c),Po(d,c)):"Polygon"==f?(d=new Q(null),Pl(d,c),Po(d,c)):"GeometryCollection"==f?d=new sm(c):sa(!1,37);else d=new sm(c);return d} -function Qo(a,b){var c=M({},Ko,a,b),d=M(null,Lo,a,b);if(d){var e=new E(null);e.ca("XYZ",d);e.H(c);return e}}function Ro(a,b){var c=M({},Ko,a,b),d=M([null],So,a,b);if(d&&d[0]){var e=new F(null),f=d[0],g=[f.length],h,l;h=1;for(l=d.length;h<l;++h)ha(f,d[h]),g.push(f.length);e.ca("XYZ",f,g);e.H(c);return e}} -function To(a,b){var c=M({},Uo,a,b);if(!c)return null;var d="fillStyle"in c?c.fillStyle:io,e=c.fill;void 0===e||e||(d=null);e="imageStyle"in c?c.imageStyle:po;e==qo&&(e=void 0);var f="textStyle"in c?c.textStyle:to,g="strokeStyle"in c?c.strokeStyle:ro,c=c.outline;void 0===c||c||(g=null);return[new bl({fill:d,image:e,stroke:g,text:f,zIndex:void 0})]} -function Po(a,b){var c=b.length,d=Array(b.length),e=Array(b.length),f,g,h,l;h=l=!1;for(g=0;g<c;++g)f=b[g],d[g]=f.get("extrude"),e[g]=f.get("altitudeMode"),h=h||void 0!==d[g],l=l||e[g];h&&a.set("extrude",d);l&&a.set("altitudeMode",e)}function Vo(a,b){Al(Wo,a,b)}function Xo(a,b){Al(Yo,a,b)} -var Zo=L(wo,{displayName:J(R),value:J(R)}),Wo=L(wo,{Data:function(a,b){var c=a.getAttribute("name");Al(Zo,a,b);var d=b[b.length-1];null!==c?d[c]=d.value:null!==d.displayName&&(d[d.displayName]=d.value)},SchemaData:function(a,b){Al($o,a,b)}}),Yo=L(wo,{LatLonAltBox:function(a,b){var c=M({},ap,a,b);if(c){var d=b[b.length-1];d.extent=[parseFloat(c.west),parseFloat(c.south),parseFloat(c.east),parseFloat(c.north)];d.altitudeMode=c.altitudeMode;d.minAltitude=parseFloat(c.minAltitude);d.maxAltitude=parseFloat(c.maxAltitude)}}, -Lod:function(a,b){var c=M({},bp,a,b);if(c){var d=b[b.length-1];d.minLodPixels=parseFloat(c.minLodPixels);d.maxLodPixels=parseFloat(c.maxLodPixels);d.minFadeExtent=parseFloat(c.minFadeExtent);d.maxFadeExtent=parseFloat(c.maxFadeExtent)}}}),ap=L(wo,{altitudeMode:J(R),minAltitude:J(Jm),maxAltitude:J(Jm),north:J(Jm),south:J(Jm),east:J(Jm),west:J(Jm)}),bp=L(wo,{minLodPixels:J(Jm),maxLodPixels:J(Jm),minFadeExtent:J(Jm),maxFadeExtent:J(Jm)}),Ko=L(wo,{extrude:J(Gm),altitudeMode:J(R)}),Go=L(wo,{coordinates:tl(Co)}), -So=L(wo,{innerBoundaryIs:function(a,b){var c=M(void 0,cp,a,b);c&&b[b.length-1].push(c)},outerBoundaryIs:function(a,b){var c=M(void 0,dp,a,b);c&&(b[b.length-1][0]=c)}}),Io=L(wo,{when:function(a,b){var c=b[b.length-1].Aj,d=ll(a,!1),d=Date.parse(d);c.push(isNaN(d)?0:d)}},L(vo,{coord:function(a,b){var c=b[b.length-1].B,d=ll(a,!1);(d=/^\s*([+\-]?\d+(?:\.\d*)?(?:e[+\-]?\d*)?)\s+([+\-]?\d+(?:\.\d*)?(?:e[+\-]?\d*)?)\s+([+\-]?\d+(?:\.\d*)?(?:e[+\-]?\d*)?)\s*$/i.exec(d))?c.push(parseFloat(d[1]),parseFloat(d[2]), -parseFloat(d[3]),0):c.push(0,0,0,0)}})),Lo=L(wo,{coordinates:tl(Co)}),ep=L(wo,{href:J(Do)},L(vo,{x:J(Jm),y:J(Jm),w:J(Jm),h:J(Jm)})),fp=L(wo,{Icon:J(function(a,b){var c=M({},ep,a,b);return c?c:null}),heading:J(Jm),hotSpot:J(function(a){var b=a.getAttribute("xunits"),c=a.getAttribute("yunits");return{x:parseFloat(a.getAttribute("x")),Pg:xo[b],y:parseFloat(a.getAttribute("y")),Qg:xo[c]}}),scale:J(Eo)}),cp=L(wo,{LinearRing:tl(Fo)}),gp=L(wo,{color:J(Bo),scale:J(Eo)}),hp=L(wo,{color:J(Bo),width:J(Jm)}), -Oo=L(wo,{LineString:sl(Jo),LinearRing:sl(Mo),MultiGeometry:sl(No),Point:sl(Qo),Polygon:sl(Ro)}),ip=L(vo,{Track:sl(Ho)}),kp=L(wo,{ExtendedData:Vo,Region:Xo,Link:function(a,b){Al(jp,a,b)},address:J(R),description:J(R),name:J(R),open:J(Gm),phoneNumber:J(R),visibility:J(Gm)}),jp=L(wo,{href:J(Do)}),dp=L(wo,{LinearRing:tl(Fo)}),lp=L(wo,{Style:J(To),key:J(R),styleUrl:J(Do)}),np=L(wo,{ExtendedData:Vo,Region:Xo,MultiGeometry:J(No,"geometry"),LineString:J(Jo,"geometry"),LinearRing:J(Mo,"geometry"),Point:J(Qo, -"geometry"),Polygon:J(Ro,"geometry"),Style:J(To),StyleMap:function(a,b){var c=M(void 0,mp,a,b);if(c){var d=b[b.length-1];Array.isArray(c)?d.Style=c:"string"===typeof c?d.styleUrl=c:sa(!1,38)}},address:J(R),description:J(R),name:J(R),open:J(Gm),phoneNumber:J(R),styleUrl:J(Do),visibility:J(Gm)},L(vo,{MultiTrack:J(function(a,b){var c=M([],ip,a,b);if(c){var d=new O(null);Nl(d,c);return d}},"geometry"),Track:J(Ho,"geometry")})),op=L(wo,{color:J(Bo),fill:J(Gm),outline:J(Gm)}),$o=L(wo,{SimpleData:function(a, -b){var c=a.getAttribute("name");if(null!==c){var d=R(a);b[b.length-1][c]=d}}}),Uo=L(wo,{IconStyle:function(a,b){var c=M({},fp,a,b);if(c){var d=b[b.length-1],e="Icon"in c?c.Icon:{},f=!("Icon"in c)||0<Object.keys(e).length,g,h=e.href;h?g=h:f&&(g=no);var l,m,n;(h=c.hotSpot)?(l=[h.x,h.y],m=h.Pg,n=h.Qg):g===no?(l=jo,m=lo,n=ko):/^http:\/\/maps\.(?:google|gstatic)\.com\//.test(g)&&(l=[.5,0],n=m="fraction");var p,h=e.x,q=e.y;void 0!==h&&void 0!==q&&(p=[h,q]);var r,h=e.w,e=e.h;void 0!==h&&void 0!==e&&(r=[h, -e]);var v,e=c.heading;void 0!==e&&(v=Ca(e));c=c.scale;f?(g==no&&(r=mo,void 0===c&&(c=oo)),f=new co({anchor:l,anchorOrigin:"bottom-left",anchorXUnits:m,anchorYUnits:n,crossOrigin:"anonymous",offset:p,offsetOrigin:"bottom-left",rotation:v,scale:c,size:r,src:g}),d.imageStyle=f):d.imageStyle=qo}},LabelStyle:function(a,b){var c=M({},gp,a,b);c&&(b[b.length-1].textStyle=new eo({fill:new al({color:"color"in c?c.color:ho}),scale:c.scale}))},LineStyle:function(a,b){var c=M({},hp,a,b);c&&(b[b.length-1].strokeStyle= -new tj({color:"color"in c?c.color:ho,width:"width"in c?c.width:1}))},PolyStyle:function(a,b){var c=M({},op,a,b);if(c){var d=b[b.length-1];d.fillStyle=new al({color:"color"in c?c.color:ho});var e=c.fill;void 0!==e&&(d.fill=e);c=c.outline;void 0!==c&&(d.outline=c)}}}),mp=L(wo,{Pair:function(a,b){var c=M({},lp,a,b);if(c){var d=c.key;d&&"normal"==d&&((d=c.styleUrl)&&(b[b.length-1]=d),(c=c.Style)&&(b[b.length-1]=c))}}});k=fo.prototype; -k.pg=function(a,b){var c=L(wo,{Document:rl(this.pg,this),Folder:rl(this.pg,this),Placemark:sl(this.xg,this),Style:this.zp.bind(this),StyleMap:this.yp.bind(this)});if(c=M([],c,a,b,this))return c};k.xg=function(a,b){var c=M({geometry:null},np,a,b);if(c){var d=new I,e=a.getAttribute("id");null!==e&&d.lc(e);var e=b[0],f=c.geometry;f&&Hl(f,!1,e);d.Ta(f);delete c.geometry;this.c&&d.cg(zo(c.Style,c.styleUrl,this.a,this.b,this.f));delete c.Style;d.H(c);return d}}; -k.zp=function(a,b){var c=a.getAttribute("id");if(null!==c){var d=To(a,b);d&&(c=a.baseURI?(new URL("#"+c,a.baseURI)).href:"#"+c,this.b[c]=d)}};k.yp=function(a,b){var c=a.getAttribute("id");if(null!==c){var d=M(void 0,mp,a,b);d&&(c=a.baseURI?(new URL("#"+c,a.baseURI)).href:"#"+c,this.b[c]=d)}};k.rg=function(a,b){if(!fa(wo,a.namespaceURI))return null;var c=this.xg(a,[Fl(this,a,b)]);return c?c:null}; -k.Bc=function(a,b){if(!fa(wo,a.namespaceURI))return[];var c;c=a.localName;if("Document"==c||"Folder"==c)return(c=this.pg(a,[Fl(this,a,b)]))?c:[];if("Placemark"==c)return(c=this.xg(a,[Fl(this,a,b)]))?[c]:[];if("kml"==c){c=[];var d;for(d=a.firstElementChild;d;d=d.nextElementSibling){var e=this.Bc(d,b);e&&ha(c,e)}return c}return[]};k.sp=function(a){if(nl(a))return pp(this,a);if(pl(a))return qp(this,a);if("string"===typeof a)return a=ql(a),pp(this,a)}; -function pp(a,b){var c;for(c=b.firstChild;c;c=c.nextSibling)if(c.nodeType==Node.ELEMENT_NODE){var d=qp(a,c);if(d)return d}}function qp(a,b){var c;for(c=b.firstElementChild;c;c=c.nextElementSibling)if(fa(wo,c.namespaceURI)&&"name"==c.localName)return R(c);for(c=b.firstElementChild;c;c=c.nextElementSibling){var d=c.localName;if(fa(wo,c.namespaceURI)&&("Document"==d||"Folder"==d||"Placemark"==d||"kml"==d)&&(d=qp(a,c)))return d}} -k.tp=function(a){var b=[];nl(a)?ha(b,rp(this,a)):pl(a)?ha(b,sp(this,a)):"string"===typeof a&&(a=ql(a),ha(b,rp(this,a)));return b};function rp(a,b){var c,d=[];for(c=b.firstChild;c;c=c.nextSibling)c.nodeType==Node.ELEMENT_NODE&&ha(d,sp(a,c));return d} -function sp(a,b){var c,d=[];for(c=b.firstElementChild;c;c=c.nextElementSibling)if(fa(wo,c.namespaceURI)&&"NetworkLink"==c.localName){var e=M({},kp,c,[]);d.push(e)}for(c=b.firstElementChild;c;c=c.nextElementSibling)e=c.localName,!fa(wo,c.namespaceURI)||"Document"!=e&&"Folder"!=e&&"kml"!=e||ha(d,sp(a,c));return d}k.wp=function(a){var b=[];nl(a)?ha(b,tp(this,a)):pl(a)?ha(b,this.jf(a)):"string"===typeof a&&(a=ql(a),ha(b,tp(this,a)));return b}; -function tp(a,b){var c,d=[];for(c=b.firstChild;c;c=c.nextSibling)c.nodeType==Node.ELEMENT_NODE&&ha(d,a.jf(c));return d}k.jf=function(a){var b,c=[];for(b=a.firstElementChild;b;b=b.nextElementSibling)if(fa(wo,b.namespaceURI)&&"Region"==b.localName){var d=M({},Yo,b,[]);c.push(d)}for(b=a.firstElementChild;b;b=b.nextElementSibling)a=b.localName,!fa(wo,b.namespaceURI)||"Document"!=a&&"Folder"!=a&&"kml"!=a||ha(c,this.jf(b));return c}; -function up(a,b){var c=bd(b),c=[255*(4==c.length?c[3]:1),c[2],c[1],c[0]],d;for(d=0;4>d;++d){var e=parseInt(c[d],10).toString(16);c[d]=1==e.length?"0"+e:e}Om(a,c.join(""))}function vp(a,b,c){a={node:a};var d=b.S(),e,f;"GeometryCollection"==d?(e=b.Qf(),f=wp):"MultiPoint"==d?(e=b.Zd(),f=xp):"MultiLineString"==d?(e=b.Nc(),f=yp):"MultiPolygon"==d?(e=b.md(),f=zp):sa(!1,39);Bl(a,Ap,f,e,c)}function Bp(a,b,c){Bl({node:a},Cp,Dp,[b],c)} -function Ep(a,b,c){var d={node:a};b.a&&a.setAttribute("id",b.a);a=b.M();var e={address:1,description:1,name:1,open:1,phoneNumber:1,styleUrl:1,visibility:1};e[b.c]=1;var f=Object.keys(a||{}).sort().filter(function(a){return!e[a]});if(0<f.length){var g=zl(a,f);Bl(d,Fp,Gp,[{names:f,values:g}],c)}if(f=b.Rc())if(f=f.call(b,0))f=Array.isArray(f)?f[0]:f,this.j&&(a.Style=f),(f=f.Oa())&&(a.name=f.Oa());f=Hp[c[c.length-1].node.namespaceURI];a=zl(a,f);Bl(d,Fp,yl,a,c,f);a=c[0];(b=b.U())&&(b=Hl(b,!0,a));Bl(d, -Fp,wp,[b],c)}function Ip(a,b,c){var d=b.ia();a={node:a};a.layout=b.la;a.stride=b.sa();Bl(a,Jp,Kp,[d],c)}function Lp(a,b,c){b=b.Oc();var d=b.shift();a={node:a};Bl(a,Mp,Np,b,c);Bl(a,Mp,Op,[d],c)}function Pp(a,b){Pm(a,Math.round(1E6*b)/1E6)} -var Qp=L(wo,["Document","Placemark"]),Tp=L(wo,{Document:K(function(a,b,c){Bl({node:a},Rp,Sp,b,c,void 0,this)}),Placemark:K(Ep)}),Rp=L(wo,{Placemark:K(Ep)}),Up=L(wo,{Data:K(function(a,b,c){a.setAttribute("name",b.name);a={node:a};b=b.value;"object"==typeof b?(null!==b&&b.displayName&&Bl(a,Up,yl,[b.displayName],c,["displayName"]),null!==b&&b.value&&Bl(a,Up,yl,[b.value],c,["value"])):Bl(a,Up,yl,[b],c,["value"])}),value:K(function(a,b){Om(a,b)}),displayName:K(function(a,b){a.appendChild(il.createCDATASection(b))})}), -Vp={Point:"Point",LineString:"LineString",LinearRing:"LinearRing",Polygon:"Polygon",MultiPoint:"MultiGeometry",MultiLineString:"MultiGeometry",MultiPolygon:"MultiGeometry",GeometryCollection:"MultiGeometry"},Wp=L(wo,["href"],L(vo,["x","y","w","h"])),Xp=L(wo,{href:K(Om)},L(vo,{x:K(Pm),y:K(Pm),w:K(Pm),h:K(Pm)})),Yp=L(wo,["scale","heading","Icon","hotSpot"]),$p=L(wo,{Icon:K(function(a,b,c){a={node:a};var d=Wp[c[c.length-1].node.namespaceURI],e=zl(b,d);Bl(a,Xp,yl,e,c,d);d=Wp[vo[0]];e=zl(b,d);Bl(a,Xp, -Zp,e,c,d)}),heading:K(Pm),hotSpot:K(function(a,b){a.setAttribute("x",b.x);a.setAttribute("y",b.y);a.setAttribute("xunits",b.Pg);a.setAttribute("yunits",b.Qg)}),scale:K(Pp)}),aq=L(wo,["color","scale"]),bq=L(wo,{color:K(up),scale:K(Pp)}),cq=L(wo,["color","width"]),dq=L(wo,{color:K(up),width:K(Pm)}),Cp=L(wo,{LinearRing:K(Ip)}),Ap=L(wo,{LineString:K(Ip),Point:K(Ip),Polygon:K(Lp),GeometryCollection:K(vp)}),Hp=L(wo,"name open visibility address phoneNumber description styleUrl Style".split(" ")),Fp=L(wo, -{ExtendedData:K(function(a,b,c){a={node:a};var d=b.names;b=b.values;for(var e=d.length,f=0;f<e;f++)Bl(a,Up,eq,[{name:d[f],value:b[f]}],c)}),MultiGeometry:K(vp),LineString:K(Ip),LinearRing:K(Ip),Point:K(Ip),Polygon:K(Lp),Style:K(function(a,b,c){a={node:a};var d={},e=b.Ca(),f=b.Da(),g=b.Y();b=b.Oa();g instanceof co&&(d.IconStyle=g);b&&(d.LabelStyle=b);f&&(d.LineStyle=f);e&&(d.PolyStyle=e);b=fq[c[c.length-1].node.namespaceURI];d=zl(d,b);Bl(a,gq,yl,d,c,b)}),address:K(Om),description:K(Om),name:K(Om), -open:K(Nm),phoneNumber:K(Om),styleUrl:K(Om),visibility:K(Nm)}),Jp=L(wo,{coordinates:K(function(a,b,c){c=c[c.length-1];var d=c.layout;c=c.stride;var e;"XY"==d||"XYM"==d?e=2:"XYZ"==d||"XYZM"==d?e=3:sa(!1,34);var f,g=b.length,h="";if(0<g){h+=b[0];for(d=1;d<e;++d)h+=","+b[d];for(f=c;f<g;f+=c)for(h+=" "+b[f],d=1;d<e;++d)h+=","+b[f+d]}Om(a,h)})}),Mp=L(wo,{outerBoundaryIs:K(Bp),innerBoundaryIs:K(Bp)}),hq=L(wo,{color:K(up)}),fq=L(wo,["IconStyle","LabelStyle","LineStyle","PolyStyle"]),gq=L(wo,{IconStyle:K(function(a, -b,c){a={node:a};var d={},e=b.kc(),f=b.ye(),g={href:b.b.l};if(e){g.w=e[0];g.h=e[1];var h=b.Jc(),l=b.Tc();l&&f&&l[0]&&l[1]!==e[1]&&(g.x=l[0],g.y=f[1]-(l[1]+e[1]));h&&h[0]&&h[1]!==e[1]&&(d.hotSpot={x:h[0],Pg:"pixels",y:e[1]-h[1],Qg:"pixels"})}d.Icon=g;e=b.c;1!==e&&(d.scale=e);(b=b.j)&&(d.heading=b);b=Yp[c[c.length-1].node.namespaceURI];d=zl(d,b);Bl(a,$p,yl,d,c,b)}),LabelStyle:K(function(a,b,c){a={node:a};var d={},e=b.Ca();e&&(d.color=e.b);(b=b.b)&&1!==b&&(d.scale=b);b=aq[c[c.length-1].node.namespaceURI]; -d=zl(d,b);Bl(a,bq,yl,d,c,b)}),LineStyle:K(function(a,b,c){a={node:a};var d=cq[c[c.length-1].node.namespaceURI];b=zl({color:b.a,width:b.c},d);Bl(a,dq,yl,b,c,d)}),PolyStyle:K(function(a,b,c){Bl({node:a},hq,iq,[b.b],c)})});function Zp(a,b,c){return kl(vo[0],"gx:"+c)}function Sp(a,b){return kl(b[b.length-1].node.namespaceURI,"Placemark")}function wp(a,b){if(a)return kl(b[b.length-1].node.namespaceURI,Vp[a.S()])} -var iq=wl("color"),Kp=wl("coordinates"),eq=wl("Data"),Gp=wl("ExtendedData"),Np=wl("innerBoundaryIs"),xp=wl("Point"),yp=wl("LineString"),Dp=wl("LinearRing"),zp=wl("Polygon"),Op=wl("outerBoundaryIs"); -fo.prototype.Zb=function(a,b){b=Gl(this,b);var c=kl(wo[4],"kml");c.setAttributeNS("http://www.w3.org/2000/xmlns/","xmlns:gx",vo[0]);c.setAttributeNS("http://www.w3.org/2000/xmlns/","xmlns:xsi","http://www.w3.org/2001/XMLSchema-instance");c.setAttributeNS("http://www.w3.org/2001/XMLSchema-instance","xsi:schemaLocation","http://www.opengis.net/kml/2.2 https://developers.google.com/kml/schema/kml22gx.xsd");var d={node:c},e={};1<a.length?e.Document=a:1==a.length&&(e.Placemark=a[0]);var f=Qp[c.namespaceURI], -e=zl(e,f);Bl(d,Tp,yl,e,[b],f,this);return c};(function(){var a={},b={ma:a};(function(c){if("object"===typeof a&&"undefined"!==typeof b)b.ma=c();else{var d;"undefined"!==typeof window?d=window:"undefined"!==typeof global?d=global:"undefined"!==typeof self?d=self:d=this;d.Bq=c()}})(function(){return function d(a,b,g){function e(h,l){if(!b[h]){if(!a[h]){var m="function"==typeof require&&require;if(!l&&m)return m(h,!0);if(f)return f(h,!0);m=Error("Cannot find module '"+h+"'");throw m.code="MODULE_NOT_FOUND",m;}m=b[h]={ma:{}};a[h][0].call(m.ma,function(b){var d= -a[h][1][b];return e(d?d:b)},m,m.ma,d,a,b,g)}return b[h].ma}for(var f="function"==typeof require&&require,m=0;m<g.length;m++)e(g[m]);return e}({1:[function(a,b,f){f.read=function(a,b,d,e,f){var g;g=8*f-e-1;var h=(1<<g)-1,l=h>>1,m=-7;f=d?f-1:0;var n=d?-1:1,y=a[b+f];f+=n;d=y&(1<<-m)-1;y>>=-m;for(m+=g;0<m;d=256*d+a[b+f],f+=n,m-=8);g=d&(1<<-m)-1;d>>=-m;for(m+=e;0<m;g=256*g+a[b+f],f+=n,m-=8);if(0===d)d=1-l;else{if(d===h)return g?NaN:Infinity*(y?-1:1);g+=Math.pow(2,e);d-=l}return(y?-1:1)*g*Math.pow(2,d- -e)};f.write=function(a,b,d,e,f,p){var g,h=8*p-f-1,l=(1<<h)-1,m=l>>1,n=23===f?Math.pow(2,-24)-Math.pow(2,-77):0;p=e?0:p-1;var A=e?1:-1,B=0>b||0===b&&0>1/b?1:0;b=Math.abs(b);isNaN(b)||Infinity===b?(b=isNaN(b)?1:0,e=l):(e=Math.floor(Math.log(b)/Math.LN2),1>b*(g=Math.pow(2,-e))&&(e--,g*=2),b=1<=e+m?b+n/g:b+n*Math.pow(2,1-m),2<=b*g&&(e++,g/=2),e+m>=l?(b=0,e=l):1<=e+m?(b=(b*g-1)*Math.pow(2,f),e+=m):(b=b*Math.pow(2,m-1)*Math.pow(2,f),e=0));for(;8<=f;a[d+p]=b&255,p+=A,b/=256,f-=8);e=e<<f|b;for(h+=f;0<h;a[d+ -p]=e&255,p+=A,e/=256,h-=8);a[d+p-A]|=128*B}},{}],2:[function(a,b){function d(a){this.nc=ArrayBuffer.isView&&ArrayBuffer.isView(a)?a:new Uint8Array(a||0);this.type=this.ha=0;this.length=this.nc.length}function e(a,b,d){var e=d.nc,f,g;g=e[d.ha++];f=(g&112)>>4;if(128>g)return h(a,f,b);g=e[d.ha++];f|=(g&127)<<3;if(128>g)return h(a,f,b);g=e[d.ha++];f|=(g&127)<<10;if(128>g)return h(a,f,b);g=e[d.ha++];f|=(g&127)<<17;if(128>g)return h(a,f,b);g=e[d.ha++];f|=(g&127)<<24;if(128>g)return h(a,f,b);g=e[d.ha++]; -if(128>g)return h(a,f|(g&1)<<31,b);throw Error("Expected varint not more than 10 bytes");}function h(a,b,d){return d?4294967296*b+(a>>>0):4294967296*(b>>>0)+(a>>>0)}b.ma=d;var l=a("ieee754");d.c=0;d.g=1;d.b=2;d.a=5;d.prototype={ug:function(a,b,d){for(d=d||this.length;this.ha<d;){var e=this.Ma(),f=e>>3,g=this.ha;this.type=e&7;a(f,b,this);this.ha===g&&this.bq(e)}return b},op:function(){var a=l.read(this.nc,this.ha,!0,23,4);this.ha+=4;return a},kp:function(){var a=l.read(this.nc,this.ha,!0,52,8);this.ha+= -8;return a},Ma:function(a){var b=this.nc,d,f;f=b[this.ha++];d=f&127;if(128>f)return d;f=b[this.ha++];d|=(f&127)<<7;if(128>f)return d;f=b[this.ha++];d|=(f&127)<<14;if(128>f)return d;f=b[this.ha++];d|=(f&127)<<21;if(128>f)return d;f=b[this.ha];return e(d|(f&15)<<28,a,this)},Ap:function(){return this.Ma(!0)},be:function(){var a=this.Ma();return 1===a%2?(a+1)/-2:a/2},ip:function(){return!!this.Ma()},Ag:function(){for(var a=this.Ma()+this.ha,b=this.nc,d="",e=this.ha;e<a;){var f=b[e],g=null,h=239<f?4:223< -f?3:191<f?2:1;if(e+h>a)break;var l,A,B;if(1===h)128>f&&(g=f);else if(2===h)l=b[e+1],128===(l&192)&&(g=(f&31)<<6|l&63,127>=g&&(g=null));else if(3===h){if(l=b[e+1],A=b[e+2],128===(l&192)&&128===(A&192)&&(g=(f&15)<<12|(l&63)<<6|A&63,2047>=g||55296<=g&&57343>=g))g=null}else 4===h&&(l=b[e+1],A=b[e+2],B=b[e+3],128===(l&192)&&128===(A&192)&&128===(B&192)&&(g=(f&15)<<18|(l&63)<<12|(A&63)<<6|B&63,65535>=g||1114112<=g))&&(g=null);null===g?(g=65533,h=1):65535<g&&(g-=65536,d+=String.fromCharCode(g>>>10&1023| -55296),g=56320|g&1023);d+=String.fromCharCode(g);e+=h}this.ha=a;return d},bq:function(a){a&=7;if(a===d.c)for(;127<this.nc[this.ha++];);else if(a===d.b)this.ha=this.Ma()+this.ha;else if(a===d.a)this.ha+=4;else if(a===d.g)this.ha+=8;else throw Error("Unimplemented type: "+a);}}},{ieee754:1}]},{},[2])(2)});Dj=b.ma})();(function(){var a={},b={ma:a};(function(c){if("object"===typeof a&&"undefined"!==typeof b)b.ma=c();else{var d;"undefined"!==typeof window?d=window:"undefined"!==typeof global?d=global:"undefined"!==typeof self?d=self:d=this;d.Eq=c()}})(function(){return function d(a,b,g){function e(h,l){if(!b[h]){if(!a[h]){var m="function"==typeof require&&require;if(!l&&m)return m(h,!0);if(f)return f(h,!0);m=Error("Cannot find module '"+h+"'");throw m.code="MODULE_NOT_FOUND",m;}m=b[h]={ma:{}};a[h][0].call(m.ma,function(b){var d= -a[h][1][b];return e(d?d:b)},m,m.ma,d,a,b,g)}return b[h].ma}for(var f="function"==typeof require&&require,m=0;m<g.length;m++)e(g[m]);return e}({1:[function(a,b){function d(a,b){this.x=a;this.y=b}b.ma=d;d.prototype={clone:function(){return new d(this.x,this.y)},add:function(a){return this.clone().Uj(a)},rotate:function(a){return this.clone().dk(a)},round:function(){return this.clone().ek()},angle:function(){return Math.atan2(this.y,this.x)},Uj:function(a){this.x+=a.x;this.y+=a.y;return this},dk:function(a){var b= -Math.cos(a);a=Math.sin(a);var d=a*this.x+b*this.y;this.x=b*this.x-a*this.y;this.y=d;return this},ek:function(){this.x=Math.round(this.x);this.y=Math.round(this.y);return this}};d.b=function(a){return a instanceof d?a:Array.isArray(a)?new d(a[0],a[1]):a}},{}],2:[function(a,b){b.ma.Tj=a("./lib/vectortile.js");b.ma.yq=a("./lib/vectortilefeature.js");b.ma.zq=a("./lib/vectortilelayer.js")},{"./lib/vectortile.js":3,"./lib/vectortilefeature.js":4,"./lib/vectortilelayer.js":5}],3:[function(a,b){function d(a, -b,d){3===a&&(a=new e(d,d.Ma()+d.ha),a.length&&(b[a.name]=a))}var e=a("./vectortilelayer");b.ma=function(a,b){this.layers=a.ug(d,{},b)}},{"./vectortilelayer":5}],4:[function(a,b){function d(a,b,d,f,g){this.properties={};this.extent=d;this.type=0;this.Ec=a;this.Af=-1;this.ne=f;this.pe=g;a.ug(e,this,b)}function e(a,b,d){if(1==a)b.id=d.Ma();else if(2==a)for(a=d.Ma()+d.ha;d.ha<a;){var e=b.ne[d.Ma()],f=b.pe[d.Ma()];b.properties[e]=f}else 3==a?b.type=d.Ma():4==a&&(b.Af=d.ha)}var h=a("point-geometry");b.ma= -d;d.b=["Unknown","Point","LineString","Polygon"];d.prototype.Hh=function(){var a=this.Ec;a.ha=this.Af;for(var b=a.Ma()+a.ha,d=1,e=0,f=0,g=0,v=[],x;a.ha<b;)if(e||(e=a.Ma(),d=e&7,e>>=3),e--,1===d||2===d)f+=a.be(),g+=a.be(),1===d&&(x&&v.push(x),x=[]),x.push(new h(f,g));else if(7===d)x&&x.push(x[0].clone());else throw Error("unknown command "+d);x&&v.push(x);return v};d.prototype.bbox=function(){var a=this.Ec;a.ha=this.Af;for(var b=a.Ma()+a.ha,d=1,e=0,f=0,g=0,h=Infinity,x=-Infinity,y=Infinity,A=-Infinity;a.ha< -b;)if(e||(e=a.Ma(),d=e&7,e>>=3),e--,1===d||2===d)f+=a.be(),g+=a.be(),f<h&&(h=f),f>x&&(x=f),g<y&&(y=g),g>A&&(A=g);else if(7!==d)throw Error("unknown command "+d);return[h,y,x,A]}},{"point-geometry":1}],5:[function(a,b){function d(a,b){this.version=1;this.name=null;this.extent=4096;this.length=0;this.Ec=a;this.ne=[];this.pe=[];this.me=[];a.ug(e,this,b);this.length=this.me.length}function e(a,b,d){15===a?b.version=d.Ma():1===a?b.name=d.Ag():5===a?b.extent=d.Ma():2===a?b.me.push(d.ha):3===a?b.ne.push(d.Ag()): -4===a&&b.pe.push(h(d))}function h(a){for(var b=null,d=a.Ma()+a.ha;a.ha<d;)b=a.Ma()>>3,b=1===b?a.Ag():2===b?a.op():3===b?a.kp():4===b?a.Ap():5===b?a.Ma():6===b?a.be():7===b?a.ip():null;return b}var l=a("./vectortilefeature.js");b.ma=d;d.prototype.feature=function(a){if(0>a||a>=this.me.length)throw Error("feature index out of bounds");this.Ec.ha=this.me[a];a=this.Ec.Ma()+this.Ec.ha;return new l(this.Ec,a,this.extent,this.ne,this.pe)}},{"./vectortilefeature.js":4}]},{},[2])(2)});Ej=b.ma})();function jq(a,b,c,d){this.g=a;this.b=b;this.i=c;this.c=d}k=jq.prototype;k.get=function(a){return this.c[a]};k.Sb=function(){return this.i};k.D=function(){this.a||(this.a="Point"===this.g?Xa(this.b):Ya(this.b,0,this.b.length,2));return this.a};k.gc=function(){return this.b};k.ia=jq.prototype.gc;k.U=function(){return this};k.Nn=function(){return this.c};k.Td=jq.prototype.U;k.sa=function(){return 2};k.Rc=oa;k.S=function(){return this.g};function kq(a){El.call(this);a=a?a:{};this.defaultDataProjection=new zb({code:"",units:"tile-pixels"});this.b=a.featureClass?a.featureClass:jq;this.g=a.geometryName;this.a=a.layerName?a.layerName:"layer";this.c=a.layers?a.layers:null}u(kq,El);k=kq.prototype;k.S=function(){return"arraybuffer"}; -k.Pa=function(a,b){var c=this.c,d=new Dj(a),d=new Ej.Tj(d),e=[],f=this.b,g,h,l;for(l in d.layers)if(!c||-1!=c.indexOf(l)){g=d.layers[l];for(var m=0,n=g.length;m<n;++m){if(f===jq){h=void 0;var p=g.feature(m),q=l,r=p.Hh(),v=[],x=[];lq(r,x,v);var y=p.type;1===y?h=1===r.length?"Point":"MultiPoint":2===y?h=1===r.length?"LineString":"MultiLineString":3===y&&(h="Polygon");p=p.properties;p[this.a]=q;h=new this.b(h,x,v,p)}else{y=g.feature(m);p=l;x=b;h=new this.b;q=y.id;v=y.properties;v[this.a]=p;this.g&&h.Yc(this.g); -p=void 0;r=y.type;if(0===r)p=null;else{var y=y.Hh(),A=[],B=[];lq(y,B,A);1===r?p=1===y.length?new E(null):new P(null):2===r?1===y.length?p=new N(null):p=new O(null):3===r&&(p=new F(null));p.ca("XY",B,A)}x=Hl(p,!1,Gl(this,x));h.Ta(x);h.lc(q);h.H(v)}e.push(h)}}return e};k.jb=function(){return this.defaultDataProjection};k.fn=function(a){this.c=a};function lq(a,b,c){for(var d=0,e=0,f=a.length;e<f;++e){var g=a[e],h,l;h=0;for(l=g.length;h<l;++h){var m=g[h];b.push(m.x,m.y)}d+=2*h;c.push(d)}}k.Vb=function(){}; -k.Xc=function(){};k.Dd=function(){};k.ed=function(){};k.Yb=function(){};function mq(){Bm.call(this);this.defaultDataProjection=Tb("EPSG:4326")}u(mq,Bm);function nq(a,b){b[b.length-1].ee[a.getAttribute("k")]=a.getAttribute("v")} -var oq=[null],pq=L(oq,{nd:function(a,b){b[b.length-1].qd.push(a.getAttribute("ref"))},tag:nq}),rq=L(oq,{node:function(a,b){var c=b[0],d=b[b.length-1],e=a.getAttribute("id"),f=[parseFloat(a.getAttribute("lon")),parseFloat(a.getAttribute("lat"))];d.Lh[e]=f;var g=M({ee:{}},qq,a,b);tb(g.ee)||(f=new E(f),Hl(f,!1,c),c=new I(f),c.lc(e),c.H(g.ee),d.features.push(c))},way:function(a,b){for(var c=b[0],d=a.getAttribute("id"),e=M({qd:[],ee:{}},pq,a,b),f=b[b.length-1],g=[],h=0,l=e.qd.length;h<l;h++)ha(g,f.Lh[e.qd[h]]); -e.qd[0]==e.qd[e.qd.length-1]?(h=new F(null),h.ca("XY",g,[g.length])):(h=new N(null),h.ca("XY",g));Hl(h,!1,c);c=new I(h);c.lc(d);c.H(e.ee);f.features.push(c)}}),qq=L(oq,{tag:nq});mq.prototype.Bc=function(a,b){var c=Fl(this,a,b);return"osm"==a.localName&&(c=M({Lh:{},features:[]},rq,a,[c]),c.features)?c.features:[]};mq.prototype.Ng=function(){};mq.prototype.Zb=function(){};mq.prototype.he=function(){};function tq(a){return a.getAttributeNS("http://www.w3.org/1999/xlink","href")};function uq(){}uq.prototype.read=function(a){return nl(a)?this.a(a):pl(a)?this.b(a):"string"===typeof a?(a=ql(a),this.a(a)):null};function vq(){}u(vq,uq);vq.prototype.a=function(a){for(a=a.firstChild;a;a=a.nextSibling)if(a.nodeType==Node.ELEMENT_NODE)return this.b(a);return null};vq.prototype.b=function(a){return(a=M({},wq,a,[]))?a:null}; -var xq=[null,"http://www.opengis.net/ows/1.1"],wq=L(xq,{ServiceIdentification:J(function(a,b){return M({},yq,a,b)}),ServiceProvider:J(function(a,b){return M({},zq,a,b)}),OperationsMetadata:J(function(a,b){return M({},Aq,a,b)})}),Bq=L(xq,{DeliveryPoint:J(R),City:J(R),AdministrativeArea:J(R),PostalCode:J(R),Country:J(R),ElectronicMailAddress:J(R)}),Cq=L(xq,{Value:ul(function(a){return R(a)})}),Dq=L(xq,{AllowedValues:J(function(a,b){return M({},Cq,a,b)})}),Fq=L(xq,{Phone:J(function(a,b){return M({}, -Eq,a,b)}),Address:J(function(a,b){return M({},Bq,a,b)})}),Hq=L(xq,{HTTP:J(function(a,b){return M({},Gq,a,b)})}),Gq=L(xq,{Get:ul(function(a,b){var c=tq(a);if(c)return M({href:c},Iq,a,b)}),Post:void 0}),Jq=L(xq,{DCP:J(function(a,b){return M({},Hq,a,b)})}),Aq=L(xq,{Operation:function(a,b){var c=a.getAttribute("name"),d=M({},Jq,a,b);d&&(b[b.length-1][c]=d)}}),Eq=L(xq,{Voice:J(R),Facsimile:J(R)}),Iq=L(xq,{Constraint:ul(function(a,b){var c=a.getAttribute("name");if(c)return M({name:c},Dq,a,b)})}),Kq=L(xq, -{IndividualName:J(R),PositionName:J(R),ContactInfo:J(function(a,b){return M({},Fq,a,b)})}),yq=L(xq,{Title:J(R),ServiceTypeVersion:J(R),ServiceType:J(R)}),zq=L(xq,{ProviderName:J(R),ProviderSite:J(tq),ServiceContact:J(function(a,b){return M({},Kq,a,b)})});function Lq(a,b,c,d){var e;void 0!==d?e=d:e=[];for(var f=d=0;f<b;){var g=a[f++];e[d++]=a[f++];e[d++]=g;for(g=2;g<c;++g)e[d++]=a[f++]}e.length=d};function Mq(a){a=a?a:{};El.call(this);this.defaultDataProjection=Tb("EPSG:4326");this.b=a.factor?a.factor:1E5;this.a=a.geometryLayout?a.geometryLayout:"XY"}u(Mq,Un);function Nq(a,b,c){var d,e=Array(b);for(d=0;d<b;++d)e[d]=0;var f,g;f=0;for(g=a.length;f<g;)for(d=0;d<b;++d,++f){var h=a[f],l=h-e[d];e[d]=h;a[f]=l}return Oq(a,c?c:1E5)}function Pq(a,b,c){var d,e=Array(b);for(d=0;d<b;++d)e[d]=0;a=Qq(a,c?c:1E5);var f;c=0;for(f=a.length;c<f;)for(d=0;d<b;++d,++c)e[d]+=a[c],a[c]=e[d];return a} -function Oq(a,b){var c=b?b:1E5,d,e;d=0;for(e=a.length;d<e;++d)a[d]=Math.round(a[d]*c);c=0;for(d=a.length;c<d;++c)e=a[c],a[c]=0>e?~(e<<1):e<<1;c="";d=0;for(e=a.length;d<e;++d){for(var f,g=a[d],h="";32<=g;)f=(32|g&31)+63,h+=String.fromCharCode(f),g>>=5;h+=String.fromCharCode(g+63);c+=h}return c} -function Qq(a,b){var c=b?b:1E5,d=[],e=0,f=0,g,h;g=0;for(h=a.length;g<h;++g){var l=a.charCodeAt(g)-63,e=e|(l&31)<<f;32>l?(d.push(e),f=e=0):f+=5}e=0;for(f=d.length;e<f;++e)g=d[e],d[e]=g&1?~(g>>1):g>>1;e=0;for(f=d.length;e<f;++e)d[e]/=c;return d}k=Mq.prototype;k.$d=function(a,b){var c=this.yd(a,b);return new I(c)};k.tg=function(a,b){return[this.$d(a,b)]};k.yd=function(a,b){var c=pf(this.a),d=Pq(a,c,this.b);Lq(d,d.length,c,d);c=Cf(d,0,d.length,c);return Hl(new N(c,this.a),!1,Gl(this,b))}; -k.fe=function(a,b){var c=a.U();if(c)return this.Ed(c,b);sa(!1,40);return""};k.Og=function(a,b){return this.fe(a[0],b)};k.Ed=function(a,b){a=Hl(a,!0,Gl(this,b));var c=a.ia(),d=a.sa();Lq(c,c.length,d,c);return Nq(c,d,this.b)};function Rq(a){a=a?a:{};El.call(this);this.defaultDataProjection=Tb(a.defaultDataProjection?a.defaultDataProjection:"EPSG:4326")}u(Rq,Il);function Sq(a,b){var c=[],d,e,f,g;f=0;for(g=a.length;f<g;++f)d=a[f],0<f&&c.pop(),0<=d?e=b[d]:e=b[~d].slice().reverse(),c.push.apply(c,e);d=0;for(e=c.length;d<e;++d)c[d]=c[d].slice();return c}function Tq(a,b,c,d,e){a=a.geometries;var f=[],g,h;g=0;for(h=a.length;g<h;++g)f[g]=Uq(a[g],b,c,d,e);return f} -function Uq(a,b,c,d,e){var f=a.type,g=Vq[f];b="Point"===f||"MultiPoint"===f?g(a,c,d):g(a,b);c=new I;c.Ta(Hl(b,!1,e));void 0!==a.id&&c.lc(a.id);a.properties&&c.H(a.properties);return c} -Rq.prototype.sg=function(a,b){if("Topology"==a.type){var c,d=null,e=null;a.transform&&(c=a.transform,d=c.scale,e=c.translate);var f=a.arcs;if(c){c=d;var g=e,h,l;h=0;for(l=f.length;h<l;++h){var m,n,p,q=f[h],r=c,v=g,x=0,y=0;n=0;for(m=q.length;n<m;++n)p=q[n],x+=p[0],y+=p[1],p[0]=x,p[1]=y,Wq(p,r,v)}}c=[];g=sb(a.objects);h=0;for(l=g.length;h<l;++h)"GeometryCollection"===g[h].type?(m=g[h],c.push.apply(c,Tq(m,f,d,e,b))):(m=g[h],c.push(Uq(m,f,d,e,b)));return c}return[]}; -function Wq(a,b,c){a[0]=a[0]*b[0]+c[0];a[1]=a[1]*b[1]+c[1]}Rq.prototype.zg=function(){return this.defaultDataProjection}; -var Vq={Point:function(a,b,c){a=a.coordinates;b&&c&&Wq(a,b,c);return new E(a)},LineString:function(a,b){var c=Sq(a.arcs,b);return new N(c)},Polygon:function(a,b){var c=[],d,e;d=0;for(e=a.arcs.length;d<e;++d)c[d]=Sq(a.arcs[d],b);return new F(c)},MultiPoint:function(a,b,c){a=a.coordinates;var d,e;if(b&&c)for(d=0,e=a.length;d<e;++d)Wq(a[d],b,c);return new P(a)},MultiLineString:function(a,b){var c=[],d,e;d=0;for(e=a.arcs.length;d<e;++d)c[d]=Sq(a.arcs[d],b);return new O(c)},MultiPolygon:function(a,b){var c= -[],d,e,f,g,h,l;h=0;for(l=a.arcs.length;h<l;++h){d=a.arcs[h];e=[];f=0;for(g=d.length;f<g;++f)e[f]=Sq(d[f],b);c[h]=e}return new Q(c)}};k=Rq.prototype;k.dd=function(){};k.ge=function(){};k.ie=function(){};k.wg=function(){};k.Wc=function(){};function Xq(a){a=a?a:{};this.c=a.featureType;this.a=a.featureNS;this.b=a.gmlFormat?a.gmlFormat:new Rm;this.l=a.schemaLocation?a.schemaLocation:Yq["1.1.0"];Bm.call(this)}u(Xq,Bm);var Yq={"1.1.0":"http://www.opengis.net/wfs http://schemas.opengis.net/wfs/1.1.0/wfs.xsd","1.0.0":"http://www.opengis.net/wfs http://schemas.opengis.net/wfs/1.0.0/wfs.xsd"}; -Xq.prototype.Bc=function(a,b){var c={featureType:this.c,featureNS:this.a};qb(c,Fl(this,a,b?b:{}));c=[c];this.b.b["http://www.opengis.net/gml"].featureMember=sl(Em.prototype.ae);(c=M([],this.b.b,a,c,this.b))||(c=[]);return c};Xq.prototype.j=function(a){if(nl(a))return Zq(a);if(pl(a))return M({},$q,a,[]);if("string"===typeof a)return a=ql(a),Zq(a)};Xq.prototype.f=function(a){if(nl(a))return ar(this,a);if(pl(a))return br(this,a);if("string"===typeof a)return a=ql(a),ar(this,a)}; -function ar(a,b){for(var c=b.firstChild;c;c=c.nextSibling)if(c.nodeType==Node.ELEMENT_NODE)return br(a,c)}var cr={"http://www.opengis.net/gml":{boundedBy:J(Em.prototype.ef,"bounds")}};function br(a,b){var c={},d=Mm(b.getAttribute("numberOfFeatures"));c.numberOfFeatures=d;return M(c,cr,b,[],a.b)} -var dr={"http://www.opengis.net/wfs":{totalInserted:J(Lm),totalUpdated:J(Lm),totalDeleted:J(Lm)}},er={"http://www.opengis.net/ogc":{FeatureId:sl(function(a){return a.getAttribute("fid")})}},fr={"http://www.opengis.net/wfs":{Feature:function(a,b){Al(er,a,b)}}},$q={"http://www.opengis.net/wfs":{TransactionSummary:J(function(a,b){return M({},dr,a,b)},"transactionSummary"),InsertResults:J(function(a,b){return M([],fr,a,b)},"insertIds")}}; -function Zq(a){for(a=a.firstChild;a;a=a.nextSibling)if(a.nodeType==Node.ELEMENT_NODE)return M({},$q,a,[])}var gr={"http://www.opengis.net/wfs":{PropertyName:K(Om)}};function hr(a,b){var c=kl("http://www.opengis.net/ogc","Filter"),d=kl("http://www.opengis.net/ogc","FeatureId");c.appendChild(d);d.setAttribute("fid",b);a.appendChild(c)} -var ir={"http://www.opengis.net/wfs":{Insert:K(function(a,b,c){var d=c[c.length-1],e=d.gmlVersion,d=kl(d.featureNS,d.featureType);a.appendChild(d);if(2===e){a=$m.prototype;(e=b.a)&&d.setAttribute("fid",e);var e=c[c.length-1],f=e.featureNS,g=b.c;e.kb||(e.kb={},e.kb[f]={});var h=b.M();b=[];var l=[],m;for(m in h){var n=h[m];null!==n&&(b.push(m),l.push(n),m==g||n instanceof lf?m in e.kb[f]||(e.kb[f][m]=K(a.Uh,a)):m in e.kb[f]||(e.kb[f][m]=K(Om)))}m=qb({},e);m.node=d;Bl(m,e.kb,wl(void 0,f),l,c,b)}else Rm.prototype.bi(d, -b,c)}),Update:K(function(a,b,c){var d=c[c.length-1];sa(void 0!==b.a,27);var e=d.featureType,f=d.featurePrefix,f=f?f:"feature",g=d.featureNS;a.setAttribute("typeName",f+":"+e);a.setAttributeNS("http://www.w3.org/2000/xmlns/","xmlns:"+f,g);e=b.a;if(void 0!==e){for(var f=b.P(),g=[],h=0,l=f.length;h<l;h++){var m=b.get(f[h]);void 0!==m&&g.push({name:f[h],value:m})}Bl({gmlVersion:d.gmlVersion,node:a,srsName:d.srsName},ir,wl("Property"),g,c);hr(a,e)}}),Delete:K(function(a,b,c){var d=c[c.length-1];sa(void 0!== -b.a,26);c=d.featureType;var e=d.featurePrefix,e=e?e:"feature",d=d.featureNS;a.setAttribute("typeName",e+":"+c);a.setAttributeNS("http://www.w3.org/2000/xmlns/","xmlns:"+e,d);b=b.a;void 0!==b&&hr(a,b)}),Property:K(function(a,b,c){var d=kl("http://www.opengis.net/wfs","Name"),e=c[c.length-1].gmlVersion;a.appendChild(d);Om(d,b.name);void 0!==b.value&&null!==b.value&&(d=kl("http://www.opengis.net/wfs","Value"),a.appendChild(d),b.value instanceof lf?2===e?$m.prototype.Uh(d,b.value,c):Rm.prototype.rd(d, -b.value,c):Om(d,b.value))}),Native:K(function(a,b){b.kq&&a.setAttribute("vendorId",b.kq);void 0!==b.Lp&&a.setAttribute("safeToIgnore",b.Lp);void 0!==b.value&&Om(a,b.value)})}};function jr(a,b,c){var d={node:a};b.b.forEach(function(a){Bl(d,kr,wl(a.mc),[a],c)})}function lr(a,b){void 0!==b.a&&a.setAttribute("matchCase",b.a.toString());mr(a,b.b);nr(a,""+b.g)}function or(a,b,c){a=kl("http://www.opengis.net/ogc",a);Om(a,c);b.appendChild(a)}function mr(a,b){or("PropertyName",a,b)} -function nr(a,b){or("Literal",a,b)} -var kr={"http://www.opengis.net/wfs":{Query:K(function(a,b,c){var d=c[c.length-1],e=d.featurePrefix,f=d.featureNS,g=d.propertyNames,h=d.srsName;a.setAttribute("typeName",(e?e+":":"")+b);h&&a.setAttribute("srsName",h);f&&a.setAttributeNS("http://www.w3.org/2000/xmlns/","xmlns:"+e,f);b=qb({},d);b.node=a;Bl(b,gr,wl("PropertyName"),g,c);if(d=d.filter)g=kl("http://www.opengis.net/ogc","Filter"),a.appendChild(g),Bl({node:g},kr,wl(d.mc),[d],c)})},"http://www.opengis.net/ogc":{And:K(jr),Or:K(jr),Not:K(function(a, -b,c){b=b.condition;Bl({node:a},kr,wl(b.mc),[b],c)}),BBOX:K(function(a,b,c){c[c.length-1].srsName=b.srsName;mr(a,b.geometryName);Rm.prototype.rd(a,b.extent,c)}),Intersects:K(function(a,b,c){c[c.length-1].srsName=b.srsName;mr(a,b.geometryName);Rm.prototype.rd(a,b.geometry,c)}),Within:K(function(a,b,c){c[c.length-1].srsName=b.srsName;mr(a,b.geometryName);Rm.prototype.rd(a,b.geometry,c)}),PropertyIsEqualTo:K(lr),PropertyIsNotEqualTo:K(lr),PropertyIsLessThan:K(lr),PropertyIsLessThanOrEqualTo:K(lr),PropertyIsGreaterThan:K(lr), -PropertyIsGreaterThanOrEqualTo:K(lr),PropertyIsNull:K(function(a,b){mr(a,b.b)}),PropertyIsBetween:K(function(a,b){mr(a,b.b);var c=kl("http://www.opengis.net/ogc","LowerBoundary");a.appendChild(c);nr(c,""+b.a);c=kl("http://www.opengis.net/ogc","UpperBoundary");a.appendChild(c);nr(c,""+b.g)}),PropertyIsLike:K(function(a,b){a.setAttribute("wildCard",b.f);a.setAttribute("singleChar",b.i);a.setAttribute("escapeChar",b.g);void 0!==b.a&&a.setAttribute("matchCase",b.a.toString());mr(a,b.b);nr(a,""+b.c)})}}; -Xq.prototype.o=function(a){var b=kl("http://www.opengis.net/wfs","GetFeature");b.setAttribute("service","WFS");b.setAttribute("version","1.1.0");var c;if(a&&(a.handle&&b.setAttribute("handle",a.handle),a.outputFormat&&b.setAttribute("outputFormat",a.outputFormat),void 0!==a.maxFeatures&&b.setAttribute("maxFeatures",a.maxFeatures),a.resultType&&b.setAttribute("resultType",a.resultType),void 0!==a.startIndex&&b.setAttribute("startIndex",a.startIndex),void 0!==a.count&&b.setAttribute("count",a.count), -c=a.filter,a.bbox)){sa(a.geometryName,12);var d=rm(a.geometryName,a.bbox,a.srsName);c?c=qm(c,d):c=d}b.setAttributeNS("http://www.w3.org/2001/XMLSchema-instance","xsi:schemaLocation",this.l);c={node:b,srsName:a.srsName,featureNS:a.featureNS?a.featureNS:this.a,featurePrefix:a.featurePrefix,geometryName:a.geometryName,filter:c,propertyNames:a.propertyNames?a.propertyNames:[]};sa(Array.isArray(a.featureTypes),11);a=a.featureTypes;c=[c];d=qb({},c[c.length-1]);d.node=b;Bl(d,kr,wl("Query"),a,c);return b}; -Xq.prototype.u=function(a,b,c,d){var e=[],f=kl("http://www.opengis.net/wfs","Transaction"),g=d.version?d.version:"1.1.0",h="1.0.0"===g?2:3;f.setAttribute("service","WFS");f.setAttribute("version",g);var l;d&&(l=d.gmlOptions?d.gmlOptions:{},d.handle&&f.setAttribute("handle",d.handle));f.setAttributeNS("http://www.w3.org/2001/XMLSchema-instance","xsi:schemaLocation",Yq[g]);a&&(g={node:f,featureNS:d.featureNS,featureType:d.featureType,featurePrefix:d.featurePrefix,gmlVersion:h,srsName:d.srsName},qb(g, -l),Bl(g,ir,wl("Insert"),a,e));b&&(g={node:f,featureNS:d.featureNS,featureType:d.featureType,featurePrefix:d.featurePrefix,gmlVersion:h,srsName:d.srsName},qb(g,l),Bl(g,ir,wl("Update"),b,e));c&&Bl({node:f,featureNS:d.featureNS,featureType:d.featureType,featurePrefix:d.featurePrefix,gmlVersion:h,srsName:d.srsName},ir,wl("Delete"),c,e);d.nativeElements&&Bl({node:f,featureNS:d.featureNS,featureType:d.featureType,featurePrefix:d.featurePrefix,gmlVersion:h,srsName:d.srsName},ir,wl("Native"),d.nativeElements, -e);return f};Xq.prototype.yg=function(a){for(a=a.firstChild;a;a=a.nextSibling)if(a.nodeType==Node.ELEMENT_NODE)return this.hf(a);return null};Xq.prototype.hf=function(a){if(a.firstElementChild&&a.firstElementChild.firstElementChild)for(a=a.firstElementChild.firstElementChild,a=a.firstElementChild;a;a=a.nextElementSibling)if(0!==a.childNodes.length&&(1!==a.childNodes.length||3!==a.firstChild.nodeType)){var b=[{}];this.b.ef(a,b);return Tb(b.pop().srsName)}return null};function pr(a){a=a?a:{};El.call(this);this.b=void 0!==a.splitCollection?a.splitCollection:!1}u(pr,Un);function qr(a){a=a.W();return a.length?a.join(" "):""}function rr(a){a=a.W();for(var b=[],c=0,d=a.length;c<d;++c)b.push(a[c].join(" "));return b.join(",")}function sr(a){var b=[];a=a.Oc();for(var c=0,d=a.length;c<d;++c)b.push("("+rr(a[c])+")");return b.join(",")} -function tr(a){var b=a.S(),c=(0,ur[b])(a),b=b.toUpperCase();if(a instanceof of){a=a.la;var d="";if("XYZ"===a||"XYZM"===a)d+="Z";if("XYM"===a||"XYZM"===a)d+="M";a=d;0<a.length&&(b+=" "+a)}return c.length?b+"("+c+")":b+" EMPTY"} -var ur={Point:qr,LineString:rr,Polygon:sr,MultiPoint:function(a){var b=[];a=a.Zd();for(var c=0,d=a.length;c<d;++c)b.push("("+qr(a[c])+")");return b.join(",")},MultiLineString:function(a){var b=[];a=a.Nc();for(var c=0,d=a.length;c<d;++c)b.push("("+rr(a[c])+")");return b.join(",")},MultiPolygon:function(a){var b=[];a=a.md();for(var c=0,d=a.length;c<d;++c)b.push("("+sr(a[c])+")");return b.join(",")},GeometryCollection:function(a){var b=[];a=a.Qf();for(var c=0,d=a.length;c<d;++c)b.push(tr(a[c]));return b.join(",")}}; -k=pr.prototype;k.$d=function(a,b){var c=this.yd(a,b);if(c){var d=new I;d.Ta(c);return d}return null};k.tg=function(a,b){var c=[],d=this.yd(a,b);this.b&&"GeometryCollection"==d.S()?c=d.a:c=[d];for(var e=[],f=0,g=c.length;f<g;++f)d=new I,d.Ta(c[f]),e.push(d);return e};k.yd=function(a,b){var c;c=new vr(new wr(a));xr(c);return(c=yr(c))?Hl(c,!1,b):null};k.fe=function(a,b){var c=a.U();return c?this.Ed(c,b):""}; -k.Og=function(a,b){if(1==a.length)return this.fe(a[0],b);for(var c=[],d=0,e=a.length;d<e;++d)c.push(a[d].U());c=new sm(c);return this.Ed(c,b)};k.Ed=function(a,b){return tr(Hl(a,!0,b))};function wr(a){this.a=a;this.b=-1} -function zr(a){var b=a.a.charAt(++a.b),c={position:a.b,value:b};if("("==b)c.type=2;else if(","==b)c.type=5;else if(")"==b)c.type=3;else if("0"<=b&&"9">=b||"."==b||"-"==b){c.type=4;var d,b=a.b,e=!1,f=!1;do{if("."==d)e=!0;else if("e"==d||"E"==d)f=!0;d=a.a.charAt(++a.b)}while("0"<=d&&"9">=d||"."==d&&(void 0===e||!e)||!f&&("e"==d||"E"==d)||f&&("-"==d||"+"==d));a=parseFloat(a.a.substring(b,a.b--));c.value=a}else if("a"<=b&&"z">=b||"A"<=b&&"Z">=b){c.type=1;b=a.b;do d=a.a.charAt(++a.b);while("a"<=d&&"z">= -d||"A"<=d&&"Z">=d);a=a.a.substring(b,a.b--).toUpperCase();c.value=a}else{if(" "==b||"\t"==b||"\r"==b||"\n"==b)return zr(a);if(""===b)c.type=6;else throw Error("Unexpected character: "+b);}return c}function vr(a){this.g=a;this.a="XY"}function xr(a){a.b=zr(a.g)}function Ar(a,b){var c=a.b.type==b;c&&xr(a);return c} -function yr(a){var b=a.b;if(Ar(a,1)){var b=b.value,c="XY",d=a.b;1==a.b.type&&(d=d.value,"Z"===d?c="XYZ":"M"===d?c="XYM":"ZM"===d&&(c="XYZM"),"XY"!==c&&xr(a));a.a=c;if("GEOMETRYCOLLECTION"==b){a:{if(Ar(a,2)){b=[];do b.push(yr(a));while(Ar(a,5));if(Ar(a,3)){a=b;break a}}else if(Br(a)){a=[];break a}throw Error(Cr(a));}return new sm(a)}d=Dr[b];c=Er[b];if(!d||!c)throw Error("Invalid geometry type: "+b);b=d.call(a);return new c(b,a.a)}throw Error(Cr(a));}k=vr.prototype; -k.ng=function(){if(Ar(this,2)){var a=Fr(this);if(Ar(this,3))return a}else if(Br(this))return null;throw Error(Cr(this));};k.mg=function(){if(Ar(this,2)){var a=Gr(this);if(Ar(this,3))return a}else if(Br(this))return[];throw Error(Cr(this));};k.og=function(){if(Ar(this,2)){var a=Hr(this);if(Ar(this,3))return a}else if(Br(this))return[];throw Error(Cr(this));}; -k.Vo=function(){if(Ar(this,2)){var a;if(2==this.b.type)for(a=[this.ng()];Ar(this,5);)a.push(this.ng());else a=Gr(this);if(Ar(this,3))return a}else if(Br(this))return[];throw Error(Cr(this));};k.Uo=function(){if(Ar(this,2)){var a=Hr(this);if(Ar(this,3))return a}else if(Br(this))return[];throw Error(Cr(this));};k.Wo=function(){if(Ar(this,2)){for(var a=[this.og()];Ar(this,5);)a.push(this.og());if(Ar(this,3))return a}else if(Br(this))return[];throw Error(Cr(this));}; -function Fr(a){for(var b=[],c=a.a.length,d=0;d<c;++d){var e=a.b;if(Ar(a,4))b.push(e.value);else break}if(b.length==c)return b;throw Error(Cr(a));}function Gr(a){for(var b=[Fr(a)];Ar(a,5);)b.push(Fr(a));return b}function Hr(a){for(var b=[a.mg()];Ar(a,5);)b.push(a.mg());return b}function Br(a){var b=1==a.b.type&&"EMPTY"==a.b.value;b&&xr(a);return b}function Cr(a){return"Unexpected `"+a.b.value+"` at position "+a.b.position+" in `"+a.g.a+"`"} -var Er={POINT:E,LINESTRING:N,POLYGON:F,MULTIPOINT:P,MULTILINESTRING:O,MULTIPOLYGON:Q},Dr={POINT:vr.prototype.ng,LINESTRING:vr.prototype.mg,POLYGON:vr.prototype.og,MULTIPOINT:vr.prototype.Vo,MULTILINESTRING:vr.prototype.Uo,MULTIPOLYGON:vr.prototype.Wo};function Ir(){this.version=void 0}u(Ir,uq);Ir.prototype.a=function(a){for(a=a.firstChild;a;a=a.nextSibling)if(a.nodeType==Node.ELEMENT_NODE)return this.b(a);return null};Ir.prototype.b=function(a){this.version=a.getAttribute("version").trim();return(a=M({version:this.version},Jr,a,[]))?a:null};function Kr(a,b){return M({},Lr,a,b)}function Mr(a,b){return M({},Nr,a,b)}function Or(a,b){var c=Kr(a,b);if(c){var d=[Mm(a.getAttribute("width")),Mm(a.getAttribute("height"))];c.size=d;return c}} -function Pr(a,b){return M([],Qr,a,b)} -var Rr=[null,"http://www.opengis.net/wms"],Jr=L(Rr,{Service:J(function(a,b){return M({},Sr,a,b)}),Capability:J(function(a,b){return M({},Tr,a,b)})}),Tr=L(Rr,{Request:J(function(a,b){return M({},Ur,a,b)}),Exception:J(function(a,b){return M([],Vr,a,b)}),Layer:J(function(a,b){return M({},Wr,a,b)})}),Sr=L(Rr,{Name:J(R),Title:J(R),Abstract:J(R),KeywordList:J(Pr),OnlineResource:J(tq),ContactInformation:J(function(a,b){return M({},Xr,a,b)}),Fees:J(R),AccessConstraints:J(R),LayerLimit:J(Lm),MaxWidth:J(Lm), -MaxHeight:J(Lm)}),Xr=L(Rr,{ContactPersonPrimary:J(function(a,b){return M({},Yr,a,b)}),ContactPosition:J(R),ContactAddress:J(function(a,b){return M({},Zr,a,b)}),ContactVoiceTelephone:J(R),ContactFacsimileTelephone:J(R),ContactElectronicMailAddress:J(R)}),Yr=L(Rr,{ContactPerson:J(R),ContactOrganization:J(R)}),Zr=L(Rr,{AddressType:J(R),Address:J(R),City:J(R),StateOrProvince:J(R),PostCode:J(R),Country:J(R)}),Vr=L(Rr,{Format:sl(R)}),Wr=L(Rr,{Name:J(R),Title:J(R),Abstract:J(R),KeywordList:J(Pr),CRS:ul(R), -EX_GeographicBoundingBox:J(function(a,b){var c=M({},$r,a,b);if(c){var d=c.westBoundLongitude,e=c.southBoundLatitude,f=c.eastBoundLongitude,c=c.northBoundLatitude;if(void 0!==d&&void 0!==e&&void 0!==f&&void 0!==c)return[d,e,f,c]}}),BoundingBox:ul(function(a){var b=[Km(a.getAttribute("minx")),Km(a.getAttribute("miny")),Km(a.getAttribute("maxx")),Km(a.getAttribute("maxy"))],c=[Km(a.getAttribute("resx")),Km(a.getAttribute("resy"))];return{crs:a.getAttribute("CRS"),extent:b,res:c}}),Dimension:ul(function(a){return{name:a.getAttribute("name"), -units:a.getAttribute("units"),unitSymbol:a.getAttribute("unitSymbol"),"default":a.getAttribute("default"),multipleValues:Hm(a.getAttribute("multipleValues")),nearestValue:Hm(a.getAttribute("nearestValue")),current:Hm(a.getAttribute("current")),values:R(a)}}),Attribution:J(function(a,b){return M({},as,a,b)}),AuthorityURL:ul(function(a,b){var c=Kr(a,b);if(c)return c.name=a.getAttribute("name"),c}),Identifier:ul(R),MetadataURL:ul(function(a,b){var c=Kr(a,b);if(c)return c.type=a.getAttribute("type"), -c}),DataURL:ul(Kr),FeatureListURL:ul(Kr),Style:ul(function(a,b){return M({},bs,a,b)}),MinScaleDenominator:J(Jm),MaxScaleDenominator:J(Jm),Layer:ul(function(a,b){var c=b[b.length-1],d=M({},Wr,a,b);if(d){var e=Hm(a.getAttribute("queryable"));void 0===e&&(e=c.queryable);d.queryable=void 0!==e?e:!1;e=Mm(a.getAttribute("cascaded"));void 0===e&&(e=c.cascaded);d.cascaded=e;e=Hm(a.getAttribute("opaque"));void 0===e&&(e=c.opaque);d.opaque=void 0!==e?e:!1;e=Hm(a.getAttribute("noSubsets"));void 0===e&&(e=c.noSubsets); -d.noSubsets=void 0!==e?e:!1;(e=Km(a.getAttribute("fixedWidth")))||(e=c.fixedWidth);d.fixedWidth=e;(e=Km(a.getAttribute("fixedHeight")))||(e=c.fixedHeight);d.fixedHeight=e;["Style","CRS","AuthorityURL"].forEach(function(a){a in c&&(d[a]=(d[a]||[]).concat(c[a]))});"EX_GeographicBoundingBox BoundingBox Dimension Attribution MinScaleDenominator MaxScaleDenominator".split(" ").forEach(function(a){a in d||(d[a]=c[a])});return d}})}),as=L(Rr,{Title:J(R),OnlineResource:J(tq),LogoURL:J(Or)}),$r=L(Rr,{westBoundLongitude:J(Jm), -eastBoundLongitude:J(Jm),southBoundLatitude:J(Jm),northBoundLatitude:J(Jm)}),Ur=L(Rr,{GetCapabilities:J(Mr),GetMap:J(Mr),GetFeatureInfo:J(Mr)}),Nr=L(Rr,{Format:ul(R),DCPType:ul(function(a,b){return M({},cs,a,b)})}),cs=L(Rr,{HTTP:J(function(a,b){return M({},ds,a,b)})}),ds=L(Rr,{Get:J(Kr),Post:J(Kr)}),bs=L(Rr,{Name:J(R),Title:J(R),Abstract:J(R),LegendURL:ul(Or),StyleSheetURL:J(Kr),StyleURL:J(Kr)}),Lr=L(Rr,{Format:J(R),OnlineResource:J(tq)}),Qr=L(Rr,{Keyword:sl(R)});function es(a){a=a?a:{};this.a="http://mapserver.gis.umn.edu/mapserver";this.b=new $m;this.c=a.layers?a.layers:null;Bm.call(this)}u(es,Bm); -es.prototype.Bc=function(a,b){var c={};b&&qb(c,Fl(this,a,b));var d=[c];a.setAttribute("namespaceURI",this.a);var e=a.localName,c=[];if(a.childNodes.length){if("msGMLOutput"==e)for(var f=0,g=a.childNodes.length;f<g;f++){var h=a.childNodes[f];if(h.nodeType===Node.ELEMENT_NODE){var l=d[0],m=h.localName.replace("_layer","");if(!this.c||fa(this.c,m)){m+="_feature";l.featureType=m;l.featureNS=this.a;var n={};n[m]=sl(this.b.qg,this.b);l=L([l.featureNS,null],n);h.setAttribute("namespaceURI",this.a);(h=M([], -l,h,d,this.b))&&ha(c,h)}}}"FeatureCollection"==e&&(d=M([],this.b.b,a,[{}],this.b))&&(c=d)}return c};es.prototype.Ng=function(){};es.prototype.Zb=function(){};es.prototype.he=function(){};function fs(){this.g=new vq}u(fs,uq);fs.prototype.a=function(a){for(a=a.firstChild;a;a=a.nextSibling)if(a.nodeType==Node.ELEMENT_NODE)return this.b(a);return null};fs.prototype.b=function(a){var b=a.getAttribute("version").trim(),c=this.g.b(a);if(!c)return null;c.version=b;return(c=M(c,gs,a,[]))?c:null};function hs(a){var b=R(a).split(" ");if(b&&2==b.length&&(a=+b[0],b=+b[1],!isNaN(a)&&!isNaN(b)))return[a,b]} -var is=[null,"http://www.opengis.net/wmts/1.0"],js=[null,"http://www.opengis.net/ows/1.1"],gs=L(is,{Contents:J(function(a,b){return M({},ks,a,b)})}),ks=L(is,{Layer:ul(function(a,b){return M({},ls,a,b)}),TileMatrixSet:ul(function(a,b){return M({},ms,a,b)})}),ls=L(is,{Style:ul(function(a,b){var c=M({},ns,a,b);if(c){var d="true"===a.getAttribute("isDefault");c.isDefault=d;return c}}),Format:ul(R),TileMatrixSetLink:ul(function(a,b){return M({},os,a,b)}),Dimension:ul(function(a,b){return M({},ps,a,b)}), -ResourceURL:ul(function(a){var b=a.getAttribute("format"),c=a.getAttribute("template");a=a.getAttribute("resourceType");var d={};b&&(d.format=b);c&&(d.template=c);a&&(d.resourceType=a);return d})},L(js,{Title:J(R),Abstract:J(R),WGS84BoundingBox:J(function(a,b){var c=M([],qs,a,b);if(2==c.length)return Ia(c)}),Identifier:J(R)})),ns=L(is,{LegendURL:ul(function(a){var b={};b.format=a.getAttribute("format");b.href=tq(a);return b})},L(js,{Title:J(R),Identifier:J(R)})),os=L(is,{TileMatrixSet:J(R),TileMatrixSetLimits:J(function(a, -b){return M([],rs,a,b)})}),rs=L(is,{TileMatrixLimits:sl(function(a,b){return M({},ss,a,b)})}),ss=L(is,{TileMatrix:J(R),MinTileRow:J(Lm),MaxTileRow:J(Lm),MinTileCol:J(Lm),MaxTileCol:J(Lm)}),ps=L(is,{Default:J(R),Value:ul(R)},L(js,{Identifier:J(R)})),qs=L(js,{LowerCorner:sl(hs),UpperCorner:sl(hs)}),ms=L(is,{WellKnownScaleSet:J(R),TileMatrix:ul(function(a,b){return M({},ts,a,b)})},L(js,{SupportedCRS:J(R),Identifier:J(R)})),ts=L(is,{TopLeftCorner:J(hs),ScaleDenominator:J(Jm),TileWidth:J(Lm),TileHeight:J(Lm), -MatrixWidth:J(Lm),MatrixHeight:J(Lm)},L(js,{Identifier:J(R)}));function us(a){Qc.call(this);a=a||{};this.a=null;this.i=ec;this.c=void 0;z(this,Sc("projection"),this.wm,this);z(this,Sc("tracking"),this.xm,this);void 0!==a.projection&&this.Ph(Tb(a.projection));void 0!==a.trackingOptions&&this.sj(a.trackingOptions);this.Je(void 0!==a.tracking?a.tracking:!1)}u(us,Qc);k=us.prototype;k.ra=function(){this.Je(!1);Qc.prototype.ra.call(this)};k.wm=function(){var a=this.Nh();a&&(this.i=Sb(Tb("EPSG:4326"),a),this.a&&this.set("position",this.i(this.a)))}; -k.xm=function(){if(Xd){var a=this.Oh();a&&void 0===this.c?this.c=navigator.geolocation.watchPosition(this.cp.bind(this),this.ep.bind(this),this.zh()):a||void 0===this.c||(navigator.geolocation.clearWatch(this.c),this.c=void 0)}}; -k.cp=function(a){a=a.coords;this.set("accuracy",a.accuracy);this.set("altitude",null===a.altitude?void 0:a.altitude);this.set("altitudeAccuracy",null===a.altitudeAccuracy?void 0:a.altitudeAccuracy);this.set("heading",null===a.heading?void 0:Ca(a.heading));this.a?(this.a[0]=a.longitude,this.a[1]=a.latitude):this.a=[a.longitude,a.latitude];var b=this.i(this.a);this.set("position",b);this.set("speed",null===a.speed?void 0:a.speed);a=Uf(Hb,this.a,a.accuracy);a.Fc(this.i);this.set("accuracyGeometry",a); -this.s()};k.ep=function(a){a.type="error";this.Je(!1);this.b(a)};k.zk=function(){return this.get("accuracy")};k.Ak=function(){return this.get("accuracyGeometry")||null};k.Ck=function(){return this.get("altitude")};k.Dk=function(){return this.get("altitudeAccuracy")};k.um=function(){return this.get("heading")};k.vm=function(){return this.get("position")};k.Nh=function(){return this.get("projection")};k.gl=function(){return this.get("speed")};k.Oh=function(){return this.get("tracking")};k.zh=function(){return this.get("trackingOptions")}; -k.Ph=function(a){this.set("projection",a)};k.Je=function(a){this.set("tracking",a)};k.sj=function(a){this.set("trackingOptions",a)};function vs(a,b,c){of.call(this);this.Gg(a,b?b:0,c)}u(vs,of);k=vs.prototype;k.clone=function(){var a=new vs(null);qf(a,this.la,this.B.slice());a.s();return a};k.Hb=function(a,b,c,d){var e=this.B;a-=e[0];var f=b-e[1];b=a*a+f*f;if(b<d){if(b)for(d=this.Yd()/Math.sqrt(b),c[0]=e[0]+d*a,c[1]=e[1]+d*f,d=2;d<this.a;++d)c[d]=e[d];else for(d=0;d<this.a;++d)c[d]=e[d];c.length=this.a;return b}return d};k.Sc=function(a,b){var c=this.B,d=a-c[0],c=b-c[1];return d*d+c*c<=ws(this)}; -k.za=function(){return this.B.slice(0,this.a)};k.se=function(a){var b=this.B,c=b[this.a]-b[0];return Wa(b[0]-c,b[1]-c,b[0]+c,b[1]+c,a)};k.Yd=function(){return Math.sqrt(ws(this))};function ws(a){var b=a.B[a.a]-a.B[0];a=a.B[a.a+1]-a.B[1];return b*b+a*a}k.S=function(){return"Circle"};k.Ya=function(a){var b=this.D();return nb(a,b)?(b=this.za(),a[0]<=b[0]&&a[2]>=b[0]||a[1]<=b[1]&&a[3]>=b[1]?!0:bb(a,this.sb,this)):!1}; -k.lb=function(a){var b=this.a,c=a.slice();c[b]=c[0]+(this.B[b]-this.B[0]);var d;for(d=1;d<b;++d)c[b+d]=a[d];qf(this,this.la,c);this.s()};k.Gg=function(a,b,c){if(a){rf(this,c,a,0);this.B||(this.B=[]);c=this.B;a=zf(c,a);c[a++]=c[0]+b;var d;b=1;for(d=this.a;b<d;++b)c[a++]=c[b];c.length=a}else qf(this,"XY",null);this.s()};k.W=function(){};k.pa=function(){};k.Zc=function(a){this.B[this.a]=this.B[0]+a;this.s()};function xs(a,b,c){for(var d=[],e=a(0),f=a(1),g=b(e),h=b(f),l=[f,e],m=[h,g],n=[1,0],p={},q=1E5,r,v,x,y,A;0<--q&&0<n.length;)x=n.pop(),e=l.pop(),g=m.pop(),f=x.toString(),f in p||(d.push(g[0],g[1]),p[f]=!0),y=n.pop(),f=l.pop(),h=m.pop(),A=(x+y)/2,r=a(A),v=b(r),Aa(v[0],v[1],g[0],g[1],h[0],h[1])<c?(d.push(h[0],h[1]),f=y.toString(),p[f]=!0):(n.push(y,A,A,x),m.push(h,v,v,g),l.push(f,r,r,e));return d}function ys(a,b,c,d,e){var f=Tb("EPSG:4326");return xs(function(d){return[a,b+(c-b)*d]},dc(f,d),e)} -function zs(a,b,c,d,e){var f=Tb("EPSG:4326");return xs(function(d){return[b+(c-b)*d,a]},dc(f,d),e)};function As(a){a=a||{};this.i=this.l=null;this.g=this.f=Infinity;this.c=this.j=-Infinity;this.A=this.O=Infinity;this.G=this.C=-Infinity;this.I=void 0!==a.targetSize?a.targetSize:100;this.qa=void 0!==a.maxLines?a.maxLines:100;this.b=[];this.a=[];this.ta=void 0!==a.strokeStyle?a.strokeStyle:Bs;this.v=this.o=void 0;this.u=null;this.setMap(void 0!==a.map?a.map:null)}var Bs=new tj({color:"rgba(0,0,0,0.2)"}),Cs=[90,45,30,20,10,5,2,1,.5,.2,.1,.05,.01,.005,.002,.001]; -function Ds(a,b,c,d,e,f,g){var h=g;b=ys(b,c,d,a.i,e);h=void 0!==a.b[h]?a.b[h]:new N(null);h.ca("XY",b);nb(h.D(),f)&&(a.b[g++]=h);return g}function Es(a,b,c,d,e){var f=e;b=zs(b,a.c,a.g,a.i,c);f=void 0!==a.a[f]?a.a[f]:new N(null);f.ca("XY",b);nb(f.D(),d)&&(a.a[e++]=f);return e}k=As.prototype;k.ym=function(){return this.l};k.Wk=function(){return this.b};k.cl=function(){return this.a}; -k.Dh=function(a){var b=a.vectorContext,c=a.frameState,d=c.extent;a=c.viewState;var e=a.center,f=a.projection,g=a.resolution;a=c.pixelRatio;a=g*g/(4*a*a);if(!this.i||!bc(this.i,f)){var h=Tb("EPSG:4326"),l=f.D(),m=f.f,n=gc(m,h,f),p=m[2],q=m[1],r=m[0],v=n[3],x=n[2],y=n[1],n=n[0];this.f=m[3];this.g=p;this.j=q;this.c=r;this.O=v;this.A=x;this.C=y;this.G=n;this.o=dc(h,f);this.v=dc(f,h);this.u=this.v(kb(l));this.i=f}f.a&&(f=f.D(),h=ib(f),c=c.focus[0],c<f[0]||c>f[2])&&(c=h*Math.ceil((f[0]-c)/h),d=[d[0]+c, -d[1],d[2]+c,d[3]]);c=this.u[0];f=this.u[1];h=-1;m=Math.pow(this.I*g,2);p=[];q=[];g=0;for(l=Cs.length;g<l;++g){r=Cs[g]/2;p[0]=c-r;p[1]=f-r;q[0]=c+r;q[1]=f+r;this.o(p,p);this.o(q,q);r=Math.pow(q[0]-p[0],2)+Math.pow(q[1]-p[1],2);if(r<=m)break;h=Cs[g]}g=h;if(-1==g)this.b.length=this.a.length=0;else{c=this.v(e);e=c[0];c=c[1];f=this.qa;h=[Math.max(d[0],this.G),Math.max(d[1],this.C),Math.min(d[2],this.A),Math.min(d[3],this.O)];h=gc(h,this.i,"EPSG:4326");m=h[3];q=h[1];e=Math.floor(e/g)*g;p=xa(e,this.c,this.g); -l=Ds(this,p,q,m,a,d,0);for(h=0;p!=this.c&&h++<f;)p=Math.max(p-g,this.c),l=Ds(this,p,q,m,a,d,l);p=xa(e,this.c,this.g);for(h=0;p!=this.g&&h++<f;)p=Math.min(p+g,this.g),l=Ds(this,p,q,m,a,d,l);this.b.length=l;c=Math.floor(c/g)*g;e=xa(c,this.j,this.f);l=Es(this,e,a,d,0);for(h=0;e!=this.j&&h++<f;)e=Math.max(e-g,this.j),l=Es(this,e,a,d,l);e=xa(c,this.j,this.f);for(h=0;e!=this.f&&h++<f;)e=Math.min(e+g,this.f),l=Es(this,e,a,d,l);this.a.length=l}b.Na(null,this.ta);a=0;for(e=this.b.length;a<e;++a)g=this.b[a], -b.Rb(g,null);a=0;for(e=this.a.length;a<e;++a)g=this.a[a],b.Rb(g,null)};k.setMap=function(a){this.l&&(this.l.K("postcompose",this.Dh,this),this.l.render());a&&(a.J("postcompose",this.Dh,this),a.render());this.l=a};function Fs(a,b,c,d,e){Nc.call(this);this.i=e;this.extent=a;this.a=c;this.resolution=b;this.state=d}u(Fs,Nc);Fs.prototype.s=function(){this.b("change")};Fs.prototype.D=function(){return this.extent};Fs.prototype.V=function(){return this.state};function Gs(a,b,c,d,e,f,g){Fs.call(this,a,b,c,0,d);this.j=e;this.N=new Image;null!==f&&(this.N.crossOrigin=f);this.c={};this.g=null;this.state=0;this.f=g}u(Gs,Fs);k=Gs.prototype;k.Y=function(a){if(void 0!==a){var b;a=w(a);if(a in this.c)return this.c[a];tb(this.c)?b=this.N:b=this.N.cloneNode(!1);return this.c[a]=b}return this.N};k.Bm=function(){this.state=3;this.g.forEach(Bc);this.g=null;this.s()}; -k.Cm=function(){void 0===this.resolution&&(this.resolution=jb(this.extent)/this.N.height);this.state=2;this.g.forEach(Bc);this.g=null;this.s()};k.load=function(){if(0==this.state||3==this.state)this.state=1,this.s(),this.g=[Gc(this.N,"error",this.Bm,this),Gc(this.N,"load",this.Cm,this)],this.f(this,this.j)};k.Hg=function(a){this.N=a};function Hs(a,b,c,d,e,f){this.c=f?f:null;Fs.call(this,a,b,c,f?0:2,d);this.g=e}u(Hs,Fs);Hs.prototype.f=function(a){this.state=a?3:2;this.s()};Hs.prototype.load=function(){0==this.state&&(this.state=1,this.s(),this.c(this.f.bind(this)))};Hs.prototype.Y=function(){return this.g};function Is(a,b){Nc.call(this);this.Ga=a;this.state=b;this.a=null;this.key=""}u(Is,Nc);Is.prototype.s=function(){this.b("change")};Is.prototype.hb=function(){return this.key+"/"+this.Ga};function Js(a){if(!a.a)return a;var b=a.a;do{if(2==b.V())return b;b=b.a}while(b);return a}Is.prototype.i=function(){return this.Ga};Is.prototype.V=function(){return this.state};function Ks(a,b,c,d,e){Is.call(this,a,b);this.f=c;this.N=new Image;null!==d&&(this.N.crossOrigin=d);this.c=null;this.l=e}u(Ks,Is);k=Ks.prototype;k.ra=function(){1==this.state&&Ls(this);this.a&&Kc(this.a);this.state=5;this.s();Is.prototype.ra.call(this)};k.Y=function(){return this.N};k.hb=function(){return this.f};k.zm=function(){this.state=3;Ls(this);this.s()};k.Am=function(){this.state=this.N.naturalWidth&&this.N.naturalHeight?2:4;Ls(this);this.s()}; -k.load=function(){if(0==this.state||3==this.state)this.state=1,this.s(),this.c=[Gc(this.N,"error",this.zm,this),Gc(this.N,"load",this.Am,this)],this.l(this,this.f)};function Ls(a){a.c.forEach(Bc);a.c=null};function Ms(a){a=a?a:{};kg.call(this,{handleEvent:jf});this.f=a.formatConstructors?a.formatConstructors:[];this.l=a.projection?Tb(a.projection):null;this.a=null;this.target=a.target?a.target:null}u(Ms,kg);function Ns(a){a=a.dataTransfer.files;var b,c,d;b=0;for(c=a.length;b<c;++b){d=a.item(b);var e=new FileReader;e.addEventListener("load",this.j.bind(this,d));e.readAsText(d)}}function Os(a){a.stopPropagation();a.preventDefault();a.dataTransfer.dropEffect="copy"} -Ms.prototype.j=function(a,b){var c=b.target.result,d=this.v,e=this.l;e||(e=d.$().o);var d=this.f,f=[],g,h;g=0;for(h=d.length;g<h;++g){var l=new d[g];var m={featureProjection:e};try{f=l.Pa(c,m)}catch(n){f=null}if(f&&0<f.length)break}this.b(new Ps(Qs,a,f,e))};Ms.prototype.setMap=function(a){this.a&&(this.a.forEach(Bc),this.a=null);kg.prototype.setMap.call(this,a);a&&(a=this.target?this.target:a.c,this.a=[z(a,"drop",Ns,this),z(a,"dragenter",Os,this),z(a,"dragover",Os,this),z(a,"drop",Os,this)])}; -var Qs="addfeatures";function Ps(a,b,c,d){Lc.call(this,a);this.features=c;this.file=b;this.projection=d}u(Ps,Lc);function Rs(a){a=a?a:{};Ag.call(this,{handleDownEvent:Ss,handleDragEvent:Ts,handleUpEvent:Us});this.o=a.condition?a.condition:wg;this.a=this.f=void 0;this.j=0;this.u=void 0!==a.duration?a.duration:400}u(Rs,Ag);function Ts(a){if(yg(a)){var b=a.map,c=b.Nb(),d=a.pixel;a=d[0]-c[0]/2;d=c[1]/2-d[1];c=Math.atan2(d,a);a=Math.sqrt(a*a+d*d);b=b.$();void 0!==this.f&&(d=c-this.f,lg(b,b.Sa()-d));this.f=c;void 0!==this.a&&(c=this.a*(b.Ra()/a),ng(b,c));void 0!==this.a&&(this.j=this.a/a);this.a=a}} -function Us(a){if(!yg(a))return!0;a=a.map.$();$f(a,1,-1);var b=this.j-1,c=a.Sa(),c=a.constrainRotation(c,0);lg(a,c,void 0,void 0);var c=a.Ra(),d=this.u,c=a.constrainResolution(c,0,b);ng(a,c,void 0,d);this.j=0;return!1}function Ss(a){return yg(a)&&this.o(a)?($f(a.map.$(),1,1),this.a=this.f=void 0,!0):!1};function Vs(a,b,c,d){this.na=a;this.T=b;this.overlaps=d;this.c=0;this.resolution=c;this.I=this.ta=null;this.a=[];this.coordinates=[];this.ea=yh();this.b=[];this.qa=null;this.mb=yh();this.fa=yh()}u(Vs,Th); -function Ws(a,b,c,d,e,f,g){var h=a.coordinates.length,l=a.Nf();g&&(c+=e);g=[b[c],b[c+1]];var m=[NaN,NaN],n=!0,p,q,r;for(p=c+e;p<d;p+=e)m[0]=b[p],m[1]=b[p+1],r=Va(l,m),r!==q?(n&&(a.coordinates[h++]=g[0],a.coordinates[h++]=g[1]),a.coordinates[h++]=m[0],a.coordinates[h++]=m[1],n=!1):1===r?(a.coordinates[h++]=m[0],a.coordinates[h++]=m[1],n=!1):n=!0,g[0]=m[0],g[1]=m[1],q=r;if(f&&n||p===c+e)a.coordinates[h++]=g[0],a.coordinates[h++]=g[1];return h} -function Xs(a,b){a.ta=[0,b,0];a.a.push(a.ta);a.I=[0,b,0];a.b.push(a.I)}Vs.prototype.Wa=function(a,b){if(this.$a){var c=Dh(this.ea,this.$a.slice());a.translate(c[0],c[1]);a.rotate(b)}a.fill();this.$a&&a.setTransform.apply(a,this.fa)}; -function Ys(a,b,c,d,e,f,g,h,l){var m;a.qa&&ja(d,a.ea)?m=a.qa:(a.qa||(a.qa=[]),m=mf(a.coordinates,0,a.coordinates.length,2,d,a.qa),Ch(a.ea,d));d=!tb(f);for(var n=0,p=g.length,q=0,r,v=a.mb,x=a.fa,y,A,B,aa,Ra=0,ra=0,Ka=a.a!=g||a.overlaps?0:200;n<p;){var C=g[n],Na,wb,Z,Ta;switch(C[0]){case 0:q=C[1];d&&f[w(q).toString()]||!q.U()?n=C[2]:void 0===l||nb(l,q.U().D())?++n:n=C[2]+1;break;case 1:Ra>Ka&&(a.Wa(b,e),Ra=0);ra>Ka&&(b.stroke(),ra=0);Ra||ra||(b.beginPath(),y=A=NaN);++n;break;case 2:q=C[1];r=m[q];C= -m[q+1];B=m[q+2]-r;q=m[q+3]-C;q=Math.sqrt(B*B+q*q);b.moveTo(r+q,C);b.arc(r,C,q,0,2*Math.PI,!0);++n;break;case 3:b.closePath();++n;break;case 4:q=C[1];r=C[2];Na=C[3];wb=C[4]*c;Z=C[5]*c;var Pb=C[6],cc=C[7],$c=C[8],re=C[9];Ta=C[10];B=C[11];aa=C[12];var Jd=C[13],ug=C[14];for(Ta&&(B+=e);q<r;q+=2){C=m[q]-wb;Ta=m[q+1]-Z;Jd&&(C=Math.round(C),Ta=Math.round(Ta));if(1!=aa||B){var bf=C+wb,mh=Ta+Z;Hh(v,bf,mh,aa,aa,B,-bf,-mh);b.setTransform.apply(b,v)}bf=b.globalAlpha;1!=cc&&(b.globalAlpha=bf*cc);var mh=ug+$c>Na.width? -Na.width-$c:ug,sq=Pb+re>Na.height?Na.height-re:Pb;b.drawImage(Na,$c,re,mh,sq,C,Ta,mh*c,sq*c);1!=cc&&(b.globalAlpha=bf);(1!=aa||B)&&b.setTransform.apply(b,x)}++n;break;case 5:q=C[1];r=C[2];Z=C[3];Pb=C[4]*c;cc=C[5]*c;B=C[6];aa=C[7]*c;Na=C[8];wb=C[9];for((Ta=C[10])&&(B+=e);q<r;q+=2){C=m[q]+Pb;Ta=m[q+1]+cc;if(1!=aa||B)Hh(v,C,Ta,aa,aa,B,-C,-Ta),b.setTransform.apply(b,v);$c=Z.split("\n");re=$c.length;1<re?(Jd=Math.round(1.5*b.measureText("M").width),Ta-=(re-1)/2*Jd):Jd=0;for(ug=0;ug<re;ug++)bf=$c[ug],wb&& -b.strokeText(bf,C,Ta),Na&&b.fillText(bf,C,Ta),Ta+=Jd;(1!=aa||B)&&b.setTransform.apply(b,x)}++n;break;case 6:if(h&&(q=C[1],q=h(q)))return q;++n;break;case 7:Ka?Ra++:a.Wa(b,e);++n;break;case 8:q=C[1];r=C[2];C=m[q];Ta=m[q+1];B=C+.5|0;aa=Ta+.5|0;if(B!==y||aa!==A)b.moveTo(C,Ta),y=B,A=aa;for(q+=2;q<r;q+=2)if(C=m[q],Ta=m[q+1],B=C+.5|0,aa=Ta+.5|0,q==r-2||B!==y||aa!==A)b.lineTo(C,Ta),y=B,A=aa;++n;break;case 9:a.$a=C[2];Ra&&(a.Wa(b,e),Ra=0,ra&&(b.stroke(),ra=0));b.fillStyle=C[1];++n;break;case 10:var q=void 0!== -C[8]?C[8]:!0,jl=C[9];r=C[2];ra&&(b.stroke(),ra=0);b.strokeStyle=C[1];b.lineWidth=q?r*c:r;b.lineCap=C[3];b.lineJoin=C[4];b.miterLimit=C[5];Ud&&(r=C[6],B=C[7],q&&c!==jl&&(r=r.map(function(a){return a*c/jl}),B*=c/jl,C[6]=r,C[7]=B,C[9]=c),b.lineDashOffset=B,b.setLineDash(r));++n;break;case 11:b.font=C[1];b.textAlign=C[2];b.textBaseline=C[3];++n;break;case 12:Ka?ra++:b.stroke();++n;break;default:++n}}Ra&&a.Wa(b,e);ra&&b.stroke()}Vs.prototype.i=function(a,b,c,d,e){Ys(this,a,b,c,d,e,this.a,void 0,void 0)}; -function Zs(a){var b=a.b;b.reverse();var c,d=b.length,e,f,g=-1;for(c=0;c<d;++c)if(e=b[c],f=e[0],6==f)g=c;else if(0==f){e[2]=c;e=a.b;for(f=c;g<f;){var h=e[g];e[g]=e[f];e[f]=h;++g;--f}g=-1}}function $s(a,b){a.ta[2]=a.a.length;a.ta=null;a.I[2]=a.b.length;a.I=null;var c=[6,b];a.a.push(c);a.b.push(c)}Vs.prototype.Se=oa;Vs.prototype.Nf=function(){return this.T};function at(a,b,c,d){Vs.call(this,a,b,c,d);this.N=this.Z=null;this.G=this.C=this.A=this.O=this.v=this.u=this.o=this.l=this.j=this.f=this.g=void 0}u(at,Vs); -at.prototype.sc=function(a,b){if(this.N){Xs(this,b);var c=a.ia(),d=this.coordinates.length,c=Ws(this,c,0,c.length,a.sa(),!1,!1);this.a.push([4,d,c,this.N,this.g,this.f,this.j,this.l,this.o,this.u,this.v,this.O,this.A,this.C,this.G]);this.b.push([4,d,c,this.Z,this.g,this.f,this.j,this.l,this.o,this.u,this.v,this.O,this.A,this.C,this.G]);$s(this,b)}}; -at.prototype.qc=function(a,b){if(this.N){Xs(this,b);var c=a.ia(),d=this.coordinates.length,c=Ws(this,c,0,c.length,a.sa(),!1,!1);this.a.push([4,d,c,this.N,this.g,this.f,this.j,this.l,this.o,this.u,this.v,this.O,this.A,this.C,this.G]);this.b.push([4,d,c,this.Z,this.g,this.f,this.j,this.l,this.o,this.u,this.v,this.O,this.A,this.C,this.G]);$s(this,b)}};at.prototype.Se=function(){Zs(this);this.f=this.g=void 0;this.N=this.Z=null;this.G=this.C=this.O=this.v=this.u=this.o=this.l=this.A=this.j=void 0}; -at.prototype.Wb=function(a){var b=a.Jc(),c=a.kc(),d=a.kg(1),e=a.Y(1),f=a.Tc();this.g=b[0];this.f=b[1];this.Z=d;this.N=e;this.j=c[1];this.l=a.f;this.o=f[0];this.u=f[1];this.v=a.o;this.O=a.j;this.A=a.c;this.C=a.u;this.G=c[0]};function bt(a,b,c,d){Vs.call(this,a,b,c,d);this.f=null;this.g={Nd:void 0,Hd:void 0,Id:null,Jd:void 0,Kd:void 0,Ld:void 0,Md:void 0,$f:0,strokeStyle:void 0,lineCap:void 0,lineDash:null,lineDashOffset:void 0,lineJoin:void 0,lineWidth:void 0,miterLimit:void 0}}u(bt,Vs);function ct(a,b,c,d,e){var f=a.coordinates.length;b=Ws(a,b,c,d,e,!1,!1);f=[8,f,b];a.a.push(f);a.b.push(f);return d}k=bt.prototype;k.Nf=function(){this.f||(this.f=Oa(this.T),0<this.c&&Ma(this.f,this.resolution*(this.c+1)/2,this.f));return this.f}; -function dt(a){var b=a.g,c=b.strokeStyle,d=b.lineCap,e=b.lineDash,f=b.lineDashOffset,g=b.lineJoin,h=b.lineWidth,l=b.miterLimit;b.Nd==c&&b.Hd==d&&ja(b.Id,e)&&b.Jd==f&&b.Kd==g&&b.Ld==h&&b.Md==l||(b.$f!=a.coordinates.length&&(a.a.push([12]),b.$f=a.coordinates.length),a.a.push([10,c,h,d,g,l,e,f,!0,1],[1]),b.Nd=c,b.Hd=d,b.Id=e,b.Jd=f,b.Kd=g,b.Ld=h,b.Md=l)} -k.Rb=function(a,b){var c=this.g,d=c.lineWidth;void 0!==c.strokeStyle&&void 0!==d&&(dt(this),Xs(this,b),this.b.push([10,c.strokeStyle,c.lineWidth,c.lineCap,c.lineJoin,c.miterLimit,c.lineDash,c.lineDashOffset,!0,1],[1]),c=a.ia(),ct(this,c,0,c.length,a.sa()),this.b.push([12]),$s(this,b))}; -k.pc=function(a,b){var c=this.g,d=c.lineWidth;if(void 0!==c.strokeStyle&&void 0!==d){dt(this);Xs(this,b);this.b.push([10,c.strokeStyle,c.lineWidth,c.lineCap,c.lineJoin,c.miterLimit,c.lineDash,c.lineDashOffset,!0,1],[1]);var c=a.Sb(),d=a.ia(),e=a.sa(),f=0,g,h;g=0;for(h=c.length;g<h;++g)f=ct(this,d,f,c[g],e);this.b.push([12]);$s(this,b)}};k.Se=function(){this.g.$f!=this.coordinates.length&&this.a.push([12]);Zs(this);this.g=null}; -k.Na=function(a,b){var c=b.a;this.g.strokeStyle=fd(c?c:Rh);c=b.i;this.g.lineCap=void 0!==c?c:"round";c=b.g;this.g.lineDash=c?c:Qh;c=b.f;this.g.lineDashOffset=c?c:0;c=b.j;this.g.lineJoin=void 0!==c?c:"round";c=b.c;this.g.lineWidth=void 0!==c?c:1;c=b.l;this.g.miterLimit=void 0!==c?c:10;this.g.lineWidth>this.c&&(this.c=this.g.lineWidth,this.f=null)};function et(a,b,c,d){Vs.call(this,a,b,c,d);this.f=null;this.g={gh:void 0,Nd:void 0,Hd:void 0,Id:null,Jd:void 0,Kd:void 0,Ld:void 0,Md:void 0,fillStyle:void 0,strokeStyle:void 0,lineCap:void 0,lineDash:null,lineDashOffset:void 0,lineJoin:void 0,lineWidth:void 0,miterLimit:void 0}}u(et,Vs); -function ft(a,b,c,d,e){var f=a.g,g=void 0!==f.fillStyle,f=void 0!=f.strokeStyle,h=d.length,l=[1];a.a.push(l);a.b.push(l);for(l=0;l<h;++l){var m=d[l],n=a.coordinates.length;c=Ws(a,b,c,m,e,!0,!f);c=[8,n,c];a.a.push(c);a.b.push(c);f&&(c=[3],a.a.push(c),a.b.push(c));c=m}b=[7];a.b.push(b);g&&a.a.push(b);f&&(g=[12],a.a.push(g),a.b.push(g));return c}k=et.prototype; -k.ac=function(a,b){var c=this.g,d=c.strokeStyle;if(void 0!==c.fillStyle||void 0!==d){gt(this,a);Xs(this,b);this.b.push([9,dd(Ph)]);void 0!==c.strokeStyle&&this.b.push([10,c.strokeStyle,c.lineWidth,c.lineCap,c.lineJoin,c.miterLimit,c.lineDash,c.lineDashOffset,!0,1]);var e=a.ia(),d=this.coordinates.length;Ws(this,e,0,e.length,a.sa(),!1,!1);e=[1];d=[2,d];this.a.push(e,d);this.b.push(e,d);d=[7];this.b.push(d);void 0!==c.fillStyle&&this.a.push(d);void 0!==c.strokeStyle&&(c=[12],this.a.push(c),this.b.push(c)); -$s(this,b)}};k.tc=function(a,b){var c=this.g;gt(this,a);Xs(this,b);this.b.push([9,dd(Ph)]);void 0!==c.strokeStyle&&this.b.push([10,c.strokeStyle,c.lineWidth,c.lineCap,c.lineJoin,c.miterLimit,c.lineDash,c.lineDashOffset,!0,1]);var c=a.Sb(),d=a.gc();ft(this,d,0,c,a.sa());$s(this,b)}; -k.rc=function(a,b){var c=this.g,d=c.strokeStyle;if(void 0!==c.fillStyle||void 0!==d){gt(this,a);Xs(this,b);this.b.push([9,dd(Ph)]);void 0!==c.strokeStyle&&this.b.push([10,c.strokeStyle,c.lineWidth,c.lineCap,c.lineJoin,c.miterLimit,c.lineDash,c.lineDashOffset,!0,1]);var c=a.c,d=ci(a),e=a.sa(),f=0,g,h;g=0;for(h=c.length;g<h;++g)f=ft(this,d,f,c[g],e);$s(this,b)}};k.Se=function(){Zs(this);this.g=null;var a=this.na;if(a){var b=this.coordinates,c,d;c=0;for(d=b.length;c<d;++c)b[c]=a*Math.round(b[c]/a)}}; -k.Nf=function(){this.f||(this.f=Oa(this.T),0<this.c&&Ma(this.f,this.resolution*(this.c+1)/2,this.f));return this.f}; -k.Na=function(a,b){var c=this.g;if(a){var d=a.b;c.fillStyle=fd(d?d:Ph)}else c.fillStyle=void 0;b?(d=b.a,c.strokeStyle=fd(d?d:Rh),d=b.i,c.lineCap=void 0!==d?d:"round",d=b.g,c.lineDash=d?d.slice():Qh,d=b.f,c.lineDashOffset=d?d:0,d=b.j,c.lineJoin=void 0!==d?d:"round",d=b.c,c.lineWidth=void 0!==d?d:1,d=b.l,c.miterLimit=void 0!==d?d:10,c.lineWidth>this.c&&(this.c=c.lineWidth,this.f=null)):(c.strokeStyle=void 0,c.lineCap=void 0,c.lineDash=null,c.lineDashOffset=void 0,c.lineJoin=void 0,c.lineWidth=void 0, -c.miterLimit=void 0)};function gt(a,b){var c=a.g,d=c.fillStyle,e=c.strokeStyle,f=c.lineCap,g=c.lineDash,h=c.lineDashOffset,l=c.lineJoin,m=c.lineWidth,n=c.miterLimit;if(void 0!==d&&("string"!==typeof d||c.gh!=d)){var p=[9,d];"string"!==typeof d&&(d=b.D(),p.push([d[0],d[3]]));a.a.push(p);c.gh=c.fillStyle}void 0===e||c.Nd==e&&c.Hd==f&&ja(c.Id,g)&&c.Jd==h&&c.Kd==l&&c.Ld==m&&c.Md==n||(a.a.push([10,e,m,f,l,n,g,h,!0,1]),c.Nd=e,c.Hd=f,c.Id=g,c.Jd=h,c.Kd=l,c.Ld=m,c.Md=n)};function ht(a,b,c,d){Vs.call(this,a,b,c,d);this.G=this.C=this.A=null;this.Fa="";this.o=this.l=0;this.u=void 0;this.O=this.v=0;this.j=this.f=this.g=null}u(ht,Vs); -ht.prototype.Ac=function(a,b,c,d,e,f){if(""!==this.Fa&&this.j&&(this.g||this.f)){if(this.g){e=this.g;var g=this.A;if(!g||g.fillStyle!=e.fillStyle){var h=[9,e.fillStyle];this.a.push(h);this.b.push(h);g?g.fillStyle=e.fillStyle:this.A={fillStyle:e.fillStyle}}}this.f&&(e=this.f,g=this.C,g&&g.lineCap==e.lineCap&&g.lineDash==e.lineDash&&g.lineDashOffset==e.lineDashOffset&&g.lineJoin==e.lineJoin&&g.lineWidth==e.lineWidth&&g.miterLimit==e.miterLimit&&g.strokeStyle==e.strokeStyle||(h=[10,e.strokeStyle,e.lineWidth, -e.lineCap,e.lineJoin,e.miterLimit,e.lineDash,e.lineDashOffset,!1,1],this.a.push(h),this.b.push(h),g?(g.lineCap=e.lineCap,g.lineDash=e.lineDash,g.lineDashOffset=e.lineDashOffset,g.lineJoin=e.lineJoin,g.lineWidth=e.lineWidth,g.miterLimit=e.miterLimit,g.strokeStyle=e.strokeStyle):this.C={lineCap:e.lineCap,lineDash:e.lineDash,lineDashOffset:e.lineDashOffset,lineJoin:e.lineJoin,lineWidth:e.lineWidth,miterLimit:e.miterLimit,strokeStyle:e.strokeStyle}));e=this.j;g=this.G;g&&g.font==e.font&&g.textAlign== -e.textAlign&&g.textBaseline==e.textBaseline||(h=[11,e.font,e.textAlign,e.textBaseline],this.a.push(h),this.b.push(h),g?(g.font=e.font,g.textAlign=e.textAlign,g.textBaseline=e.textBaseline):this.G={font:e.font,textAlign:e.textAlign,textBaseline:e.textBaseline});Xs(this,f);e=this.coordinates.length;a=Ws(this,a,b,c,d,!1,!1);a=[5,e,a,this.Fa,this.l,this.o,this.v,this.O,!!this.g,!!this.f,this.u];this.a.push(a);this.b.push(a);$s(this,f)}}; -ht.prototype.Ub=function(a){if(a){var b=a.Ca();b?(b=b.b,b=fd(b?b:Ph),this.g?this.g.fillStyle=b:this.g={fillStyle:b}):this.g=null;var c=a.Da();if(c){var b=c.a,d=c.i,e=c.g,f=c.f,g=c.j,h=c.c,c=c.l,d=void 0!==d?d:"round",e=e?e.slice():Qh,f=void 0!==f?f:0,g=void 0!==g?g:"round",h=void 0!==h?h:1,c=void 0!==c?c:10,b=fd(b?b:Rh);if(this.f){var l=this.f;l.lineCap=d;l.lineDash=e;l.lineDashOffset=f;l.lineJoin=g;l.lineWidth=h;l.miterLimit=c;l.strokeStyle=b}else this.f={lineCap:d,lineDash:e,lineDashOffset:f,lineJoin:g, -lineWidth:h,miterLimit:c,strokeStyle:b}}else this.f=null;var m=a.a,b=a.g,d=a.c,e=a.l,h=a.i,c=a.b,f=a.Oa(),g=a.f,l=a.j;a=void 0!==m?m:"10px sans-serif";g=void 0!==g?g:"center";l=void 0!==l?l:"middle";this.j?(m=this.j,m.font=a,m.textAlign=g,m.textBaseline=l):this.j={font:a,textAlign:g,textBaseline:l};this.Fa=void 0!==f?f:"";this.l=void 0!==b?b:0;this.o=void 0!==d?d:0;this.u=void 0!==e?e:!1;this.v=void 0!==h?h:0;this.O=void 0!==c?c:1}else this.Fa=""};function it(a,b,c,d,e){this.v=a;this.c=b;this.o=d;this.u=c;this.f=e;this.a={};this.j=hd(1,1);this.l=yh()}u(it,hi);var jt={0:[[!0]]};function kt(a,b,c){var d,e=Math.floor(a.length/2);if(b>=e)for(d=e;d<b;d++)a[d][c]=!0;else if(b<e)for(d=b+1;d<e;d++)a[d][c]=!0} -function lt(a){if(void 0!==jt[a])return jt[a];for(var b=2*a+1,c=Array(b),d=0;d<b;d++)c[d]=Array(b);for(var b=a,e=d=0;b>=d;)kt(c,a+b,a+d),kt(c,a+d,a+b),kt(c,a-d,a+b),kt(c,a-b,a+d),kt(c,a-b,a-d),kt(c,a-d,a-b),kt(c,a+d,a-b),kt(c,a+b,a-d),d++,e+=1+2*d,0<2*(e-b)+1&&(--b,e+=1-2*b);return jt[a]=c}function mt(a){for(var b in a.a){var c=a.a[b],d;for(d in c)c[d].Se()}} -it.prototype.Ba=function(a,b,c,d,e,f){d=Math.round(d);var g=2*d+1,h=Hh(this.l,d+.5,d+.5,1/b,-1/b,-c,-a[0],-a[1]),l=this.j;l.canvas.width!==g||l.canvas.height!==g?(l.canvas.width=g,l.canvas.height=g):l.clearRect(0,0,g,g);var m;void 0!==this.f&&(m=Ja(),La(m,a),Ma(m,b*(this.f+d),m));var n=lt(d);return nt(this,l,h,c,e,function(a){for(var b=l.getImageData(0,0,g,g).data,c=0;c<g;c++)for(var d=0;d<g;d++)if(n[c][d]&&0<b[4*(d*g+c)+3]){if(a=f(a))return a;l.clearRect(0,0,g,g);return}},m)}; -function ot(a,b){var c=a.c,d=c[0],e=c[1],f=c[2],c=c[3],d=[d,e,d,c,f,c,f,e];mf(d,0,8,2,b,d);return d}it.prototype.b=function(a,b){var c=void 0!==a?a.toString():"0",d=this.a[c];void 0===d&&(d={},this.a[c]=d);c=d[b];void 0===c&&(c=new pt[b](this.v,this.c,this.u,this.o),d[b]=c);return c};it.prototype.g=function(){return tb(this.a)}; -it.prototype.i=function(a,b,c,d,e,f){var g=Object.keys(this.a).map(Number);g.sort(ea);var h=ot(this,c);a.save();a.beginPath();a.moveTo(h[0],h[1]);a.lineTo(h[2],h[3]);a.lineTo(h[4],h[5]);a.lineTo(h[6],h[7]);a.clip();f=f?f:gi;var l,m,n,p,q,h=0;for(l=g.length;h<l;++h)for(p=this.a[g[h].toString()],m=0,n=f.length;m<n;++m)q=p[f[m]],void 0!==q&&q.i(a,b,c,d,e);a.restore()}; -function nt(a,b,c,d,e,f,g){var h=Object.keys(a.a).map(Number);h.sort(function(a,b){return b-a});var l,m,n,p,q;l=0;for(m=h.length;l<m;++l)for(p=a.a[h[l].toString()],n=gi.length-1;0<=n;--n)if(q=p[gi[n]],void 0!==q&&(q=Ys(q,b,1,c,d,e,q.b,f,g)))return q}var pt={Circle:et,Image:at,LineString:bt,Polygon:et,Text:ht};function qt(a){Pc.call(this);this.a=a}u(qt,Pc);qt.prototype.Ba=oa;qt.prototype.Te=kf;qt.prototype.Jf=function(a,b,c){return function(d,e){return rt(a,b,d,e,function(a){c[d]||(c[d]={});c[d][a.Ga.toString()]=a})}};qt.prototype.ea=function(a){2===a.target.V()&&st(this)};function tt(a,b){var c=b.V();2!=c&&3!=c&&z(b,"change",a.ea,a);0==c&&(b.load(),c=b.V());return 2==c}function st(a){var b=a.a;b.Lb()&&"ready"==b.Vf()&&a.s()} -function ut(a,b){b.Ei()&&a.postRenderFunctions.push(function(a,b,e){b=w(a).toString();a.ld(e.viewState.projection,e.usedTiles[b])}.bind(null,b))}function vt(a,b){if(b){var c,d,e;d=0;for(e=b.length;d<e;++d)c=b[d],a[w(c).toString()]=c}}function wt(a,b){var c=b.Z;void 0!==c&&("string"===typeof c?a.logos[c]="":c&&(sa("string"==typeof c.href,44),sa("string"==typeof c.src,45),a.logos[c.src]=c.href))} -function xt(a,b,c,d){b=w(b).toString();c=c.toString();b in a?c in a[b]?(a=a[b][c],d.da<a.da&&(a.da=d.da),d.ba>a.ba&&(a.ba=d.ba),d.ga<a.ga&&(a.ga=d.ga),d.ja>a.ja&&(a.ja=d.ja)):a[b][c]=d:(a[b]={},a[b][c]=d)} -function yt(a,b,c,d,e,f,g,h,l,m){var n=w(b).toString();n in a.wantedTiles||(a.wantedTiles[n]={});var p=a.wantedTiles[n];a=a.tileQueue;var q=c.minZoom,r,v,x,y,A,B;for(B=g;B>=q;--B)for(v=nc(c,f,B,v),x=c.La(B),y=v.da;y<=v.ba;++y)for(A=v.ga;A<=v.ja;++A)g-B<=h?(r=b.Pc(B,y,A,d,e),0==r.V()&&(p[r.hb()]=!0,r.hb()in a.a||a.i([r,n,sc(c,r.Ga),x])),l&&l.call(m,r)):b.Mg(B,y,A,e)};function zt(a){qt.call(this,a);this.fa=yh()}u(zt,qt);function At(a,b,c){var d=b.pixelRatio,e=b.size[0]*d,f=b.size[1]*d,g=b.viewState.rotation,h=fb(c),l=eb(c),m=db(c);c=cb(c);Dh(b.coordinateToPixelTransform,h);Dh(b.coordinateToPixelTransform,l);Dh(b.coordinateToPixelTransform,m);Dh(b.coordinateToPixelTransform,c);a.save();Sh(a,-g,e/2,f/2);a.beginPath();a.moveTo(h[0]*d,h[1]*d);a.lineTo(l[0]*d,l[1]*d);a.lineTo(m[0]*d,m[1]*d);a.lineTo(c[0]*d,c[1]*d);a.clip();Sh(a,g,e/2,f/2)} -function Bt(a,b,c,d,e){var f=a.a;if(Oc(f,b)){var g=d.size[0]*d.pixelRatio,h=d.size[1]*d.pixelRatio,l=d.viewState.rotation;Sh(c,-l,g/2,h/2);a=e?e:Ct(a,d,0);f.b(new Oh(b,new Uh(c,d.pixelRatio,d.extent,a,d.viewState.rotation),d,c,null));Sh(c,l,g/2,h/2)}}zt.prototype.v=function(a,b,c,d){if(this.Ba(a,b,0,jf,this))return c.call(d,this.a,null)};zt.prototype.cf=function(a,b,c,d){Bt(this,"postcompose",a,b,d)}; -function Ct(a,b,c){var d=b.viewState,e=b.pixelRatio,f=e/d.resolution;return Hh(a.fa,e*b.size[0]/2,e*b.size[1]/2,f,-f,-d.rotation,-d.center[0]+c,-d.center[1])};function Dt(a,b){return w(a)-w(b)}function Et(a,b){var c=.5*a/b;return c*c}function Ft(a,b,c,d,e,f){var g=!1,h,l;if(h=c.Y())l=h.Xe(),2==l||3==l?h.xj(e,f):(0==l&&h.load(),h.Gh(e,f),g=!0);if(e=(0,c.Qa)(b))d=e.Td(d),(0,Gt[d.S()])(a,d,c,b);return g} -var Gt={Point:function(a,b,c,d){var e=c.Y();if(e){if(2!=e.Xe())return;var f=a.b(c.Aa(),"Image");f.Wb(e);f.sc(b,d)}if(e=c.Oa())a=a.b(c.Aa(),"Text"),a.Ub(e),a.Ac(b.ia(),0,2,2,b,d)},LineString:function(a,b,c,d){var e=c.Da();if(e){var f=a.b(c.Aa(),"LineString");f.Na(null,e);f.Rb(b,d)}if(e=c.Oa())a=a.b(c.Aa(),"Text"),a.Ub(e),a.Ac(ai(b),0,2,2,b,d)},Polygon:function(a,b,c,d){var e=c.Ca(),f=c.Da();if(e||f){var g=a.b(c.Aa(),"Polygon");g.Na(e,f);g.tc(b,d)}if(e=c.Oa())a=a.b(c.Aa(),"Text"),a.Ub(e),a.Ac(Tf(b), -0,2,2,b,d)},MultiPoint:function(a,b,c,d){var e=c.Y();if(e){if(2!=e.Xe())return;var f=a.b(c.Aa(),"Image");f.Wb(e);f.qc(b,d)}if(e=c.Oa())a=a.b(c.Aa(),"Text"),a.Ub(e),c=b.ia(),a.Ac(c,0,c.length,b.sa(),b,d)},MultiLineString:function(a,b,c,d){var e=c.Da();if(e){var f=a.b(c.Aa(),"LineString");f.Na(null,e);f.pc(b,d)}if(e=c.Oa())a=a.b(c.Aa(),"Text"),a.Ub(e),c=bi(b),a.Ac(c,0,c.length,2,b,d)},MultiPolygon:function(a,b,c,d){var e=c.Ca(),f=c.Da();if(f||e){var g=a.b(c.Aa(),"Polygon");g.Na(e,f);g.rc(b,d)}if(e= -c.Oa())a=a.b(c.Aa(),"Text"),a.Ub(e),c=di(b),a.Ac(c,0,c.length,2,b,d)},GeometryCollection:function(a,b,c,d){b=b.a;var e,f;e=0;for(f=b.length;e<f;++e)(0,Gt[b[e].S()])(a,b[e],c,d)},Circle:function(a,b,c,d){var e=c.Ca(),f=c.Da();if(e||f){var g=a.b(c.Aa(),"Circle");g.Na(e,f);g.ac(b,d)}if(e=c.Oa())a=a.b(c.Aa(),"Text"),a.Ub(e),a.Ac(b.za(),0,2,2,b,d)}};function Ht(a){zt.call(this,a);this.c=!1;this.u=-1;this.o=NaN;this.j=Ja();this.i=this.l=null;this.f=hd()}u(Ht,zt); -Ht.prototype.O=function(a,b,c){var d=a.extent,e=a.pixelRatio,f=b.Ie?a.skippedFeatureUids:{},g=a.viewState,h=g.projection,g=g.rotation,l=h.D(),m=this.a.ka(),n=Ct(this,a,0);Bt(this,"precompose",c,a,n);var p=b.extent,q=void 0!==p;q&&At(c,a,p);if((p=this.i)&&!p.g()){var r=0,v=0,x;if(Oc(this.a,"render")){x=c.canvas.width;var y=c.canvas.height;if(g){var A=Math.round(Math.sqrt(x*x+y*y)),r=(A-x)/2,v=(A-y)/2;x=y=A}this.f.canvas.width=x;this.f.canvas.height=y;x=this.f}else x=c;y=x.globalAlpha;x.globalAlpha= -b.opacity;x!=c&&x.translate(r,v);var A=a.size[0]*e,B=a.size[1]*e;Sh(x,-g,A/2,B/2);p.i(x,e,n,g,f);if(m.G&&h.a&&!Ua(l,d)){for(var h=d[0],m=ib(l),aa=0;h<l[0];)--aa,n=m*aa,n=Ct(this,a,n),p.i(x,e,n,g,f),h+=m;aa=0;for(h=d[2];h>l[2];)++aa,n=m*aa,n=Ct(this,a,n),p.i(x,e,n,g,f),h-=m;n=Ct(this,a,0)}Sh(x,g,A/2,B/2);x!=c&&(Bt(this,"render",x,a,n),c.drawImage(x.canvas,-r,-v),x.translate(-r,-v));x.globalAlpha=y}q&&c.restore();this.cf(c,a,b,n)}; -Ht.prototype.Ba=function(a,b,c,d,e){if(this.i){var f=this.a,g={};return this.i.Ba(a,b.viewState.resolution,b.viewState.rotation,c,{},function(a){var b=w(a).toString();if(!(b in g))return g[b]=!0,d.call(e,a,f)})}};Ht.prototype.A=function(){st(this)}; -Ht.prototype.ud=function(a){function b(a){var b,d=a.Rc();d?b=d.call(a,m):(d=c.i)&&(b=d(a,m));if(b){if(b){d=!1;if(Array.isArray(b))for(var e=0,f=b.length;e<f;++e)d=Ft(q,a,b[e],Et(m,n),this.A,this)||d;else d=Ft(q,a,b,Et(m,n),this.A,this)||d;a=d}else a=!1;this.c=this.c||a}}var c=this.a,d=c.ka();vt(a.attributions,d.j);wt(a,d);var e=a.viewHints[0],f=a.viewHints[1],g=c.ea,h=c.fa;if(!this.c&&!g&&e||!h&&f)return!0;var l=a.extent,h=a.viewState,e=h.projection,m=h.resolution,n=a.pixelRatio,f=c.g,p=c.c,g=c.get(It); -void 0===g&&(g=Dt);l=Ma(l,p*m);p=h.projection.D();d.G&&h.projection.a&&!Ua(p,a.extent)&&(a=Math.max(ib(l)/2,ib(p)),l[0]=p[0]-a,l[2]=p[2]+a);if(!this.c&&this.o==m&&this.u==f&&this.l==g&&Ua(this.j,l))return!0;this.i=null;this.c=!1;var q=new it(.5*m/n,l,m,d.Ha,c.c);d.Xd(l,m,e);if(g){var r=[];d.bc(l,function(a){r.push(a)},this);r.sort(g);r.forEach(b,this)}else d.bc(l,b,this);mt(q);this.o=m;this.u=f;this.l=g;this.j=l;this.i=q;return!0};function Jt(){this.b="precision mediump float;varying vec2 a;uniform float f;uniform sampler2D g;void main(void){vec4 texColor=texture2D(g,a);gl_FragColor.rgb=texColor.rgb;gl_FragColor.a=texColor.a*f;}"}u(Jt,ji);var Kt=new Jt;function Lt(){this.b="varying vec2 a;attribute vec2 b;attribute vec2 c;uniform mat4 d;uniform mat4 e;void main(void){gl_Position=e*vec4(b,0.,1.);a=(d*vec4(c,0.,1.)).st;}"}u(Lt,ki);var Mt=new Lt; -function Nt(a,b){this.g=a.getUniformLocation(b,"f");this.c=a.getUniformLocation(b,"e");this.f=a.getUniformLocation(b,"d");this.i=a.getUniformLocation(b,"g");this.b=a.getAttribLocation(b,"b");this.a=a.getAttribLocation(b,"c")};function Ot(a,b){qt.call(this,b);this.c=a;this.T=new Ai([-1,-1,0,0,1,-1,1,0,-1,1,0,1,1,1,1,1]);this.f=this.Fb=null;this.j=void 0;this.u=yh();this.O=yh();this.C=qi();this.v=null}u(Ot,qt); -function Pt(a,b,c){var d=a.c.g;if(void 0===a.j||a.j!=c){b.postRenderFunctions.push(function(a,b,c){a.isContextLost()||(a.deleteFramebuffer(b),a.deleteTexture(c))}.bind(null,d,a.f,a.Fb));b=Ni(d,c,c);var e=d.createFramebuffer();d.bindFramebuffer(36160,e);d.framebufferTexture2D(36160,36064,3553,b,0);a.Fb=b;a.f=e;a.j=c}else d.bindFramebuffer(36160,a.f)} -Ot.prototype.zi=function(a,b,c){Qt(this,"precompose",c,a);ti(c,34962,this.T);var d=c.b,e=Ei(c,Kt,Mt),f;this.v?f=this.v:this.v=f=new Nt(d,e);c.Vc(e)&&(d.enableVertexAttribArray(f.b),d.vertexAttribPointer(f.b,2,5126,!1,16,0),d.enableVertexAttribArray(f.a),d.vertexAttribPointer(f.a,2,5126,!1,16,8),d.uniform1i(f.i,0));d.uniformMatrix4fv(f.f,!1,ri(this.C,this.u));d.uniformMatrix4fv(f.c,!1,ri(this.C,this.O));d.uniform1f(f.g,b.opacity);d.bindTexture(3553,this.Fb);d.drawArrays(5,0,4);Qt(this,"postcompose", -c,a)};function Qt(a,b,c,d){a=a.a;if(Oc(a,b)){var e=d.viewState;a.b(new Oh(b,new kk(c,e.center,e.resolution,e.rotation,d.size,d.extent,d.pixelRatio),d,null,c))}}Ot.prototype.hg=function(){this.f=this.Fb=null;this.j=void 0};function Rt(a,b){Ot.call(this,a,b);this.o=!1;this.Z=-1;this.I=NaN;this.A=Ja();this.l=this.i=this.G=null}u(Rt,Ot);k=Rt.prototype;k.zi=function(a,b,c){this.l=b;var d=a.viewState,e=this.i,f=a.size,g=a.pixelRatio,h=this.c.g;e&&!e.g()&&(h.enable(h.SCISSOR_TEST),h.scissor(0,0,f[0]*g,f[1]*g),e.i(c,d.center,d.resolution,d.rotation,f,g,b.opacity,b.Ie?a.skippedFeatureUids:{}),h.disable(h.SCISSOR_TEST))};k.ra=function(){var a=this.i;a&&(ek(a,this.c.i)(),this.i=null);Ot.prototype.ra.call(this)}; -k.Ba=function(a,b,c,d,e){if(this.i&&this.l){c=b.viewState;var f=this.a,g={};return this.i.Ba(a,this.c.i,c.center,c.resolution,c.rotation,b.size,b.pixelRatio,this.l.opacity,{},function(a){var b=w(a).toString();if(!(b in g))return g[b]=!0,d.call(e,a,f)})}};k.Te=function(a,b){if(this.i&&this.l){var c=b.viewState;return jk(this.i,a,this.c.i,c.resolution,c.rotation,b.pixelRatio,this.l.opacity,b.skippedFeatureUids)}return!1}; -k.gg=function(a,b,c,d){a=Dh(b.pixelToCoordinateTransform,a.slice());if(this.Te(a,b))return c.call(d,this.a,null)};k.Ai=function(){st(this)}; -k.ig=function(a,b,c){function d(a){var b,c=a.Rc();c?b=c.call(a,m):(c=e.i)&&(b=c(a,m));if(b){if(b){c=!1;if(Array.isArray(b))for(var d=b.length-1;0<=d;--d)c=Ft(q,a,b[d],Et(m,n),this.Ai,this)||c;else c=Ft(q,a,b,Et(m,n),this.Ai,this)||c;a=c}else a=!1;this.o=this.o||a}}var e=this.a;b=e.ka();vt(a.attributions,b.j);wt(a,b);var f=a.viewHints[0],g=a.viewHints[1],h=e.ea,l=e.fa;if(!this.o&&!h&&f||!l&&g)return!0;var g=a.extent,h=a.viewState,f=h.projection,m=h.resolution,n=a.pixelRatio,h=e.g,p=e.c,l=e.get(It); -void 0===l&&(l=Dt);g=Ma(g,p*m);if(!this.o&&this.I==m&&this.Z==h&&this.G==l&&Ua(this.A,g))return!0;this.i&&a.postRenderFunctions.push(ek(this.i,c));this.o=!1;var q=new dk(.5*m/n,g,e.c);b.Xd(g,m,f);if(l){var r=[];b.bc(g,function(a){r.push(a)},this);r.sort(l);r.forEach(d,this)}else b.bc(g,d,this);fk(q,c);this.I=m;this.Z=h;this.G=l;this.A=g;this.i=q;return!0};function S(a){a=a?a:{};var b=qb({},a);delete b.style;delete b.renderBuffer;delete b.updateWhileAnimating;delete b.updateWhileInteracting;th.call(this,b);this.c=void 0!==a.renderBuffer?a.renderBuffer:100;this.A=null;this.i=void 0;this.f(a.style);this.ea=void 0!==a.updateWhileAnimating?a.updateWhileAnimating:!1;this.fa=void 0!==a.updateWhileInteracting?a.updateWhileInteracting:!1}u(S,th);S.prototype.Gd=function(a){var b=null,c=a.S();"canvas"===c?b=new Ht(this):"webgl"===c&&(b=new Rt(a,this));return b}; -S.prototype.C=function(){return this.A};S.prototype.G=function(){return this.i};S.prototype.f=function(a){this.A=void 0!==a?a:fl;this.i=null===a?void 0:dl(this.A);this.s()};var It="renderOrder";function St(){return[[-Infinity,-Infinity,Infinity,Infinity]]};function Tt(a){Qc.call(this);this.c=Tb(a.projection);this.j=Ut(a.attributions);this.Z=a.logo;this.Ja=void 0!==a.state?a.state:"ready";this.G=void 0!==a.wrapX?a.wrapX:!1}u(Tt,Qc);function Ut(a){if("string"===typeof a)return[new xc({html:a})];if(a instanceof xc)return[a];if(Array.isArray(a)){for(var b=a.length,c=Array(b),d=0;d<b;d++){var e=a[d];c[d]="string"===typeof e?new xc({html:e}):e}return c}return null}k=Tt.prototype;k.Ba=oa;k.xa=function(){return this.j};k.wa=function(){return this.Z};k.ya=function(){return this.c}; -k.V=function(){return this.Ja};k.va=function(){this.s()};k.ua=function(a){this.j=Ut(a);this.s()};function Vt(a,b){a.Ja=b;a.s()};function T(a){a=a||{};Tt.call(this,{attributions:a.attributions,logo:a.logo,projection:void 0,state:"ready",wrapX:void 0!==a.wrapX?a.wrapX:!0});this.ea=oa;this.T=a.format;this.Ha=void 0==a.overlaps?!0:a.overlaps;this.fa=a.url;a.loader?this.ea=a.loader:void 0!==this.fa&&(sa(this.T,7),this.ea=Dl(this.fa,this.T));this.Va=a.strategy?a.strategy:St;var b=void 0!==a.useSpatialIndex?a.useSpatialIndex:!0;this.a=b?new Gj:null;this.na=new Gj;this.f={};this.l={};this.o={};this.u={};this.i=null;var c,d;a.features instanceof -D?(c=a.features,d=c.a):Array.isArray(a.features)&&(d=a.features);b||c||(c=new D(d));d&&Wt(this,d);c&&Xt(this,c)}u(T,Tt);k=T.prototype;k.zb=function(a){var b=w(a).toString();if(Yt(this,b,a)){Zt(this,b,a);var c=a.U();c?(b=c.D(),this.a&&this.a.Ea(b,a)):this.f[b]=a;this.b(new $t("addfeature",a))}this.s()};function Zt(a,b,c){a.u[b]=[z(c,"change",a.Ii,a),z(c,"propertychange",a.Ii,a)]} -function Yt(a,b,c){var d=!0,e=c.a;void 0!==e?e.toString()in a.l?d=!1:a.l[e.toString()]=c:(sa(!(b in a.o),30),a.o[b]=c);return d}k.gd=function(a){Wt(this,a);this.s()};function Wt(a,b){var c,d,e,f,g=[],h=[],l=[];d=0;for(e=b.length;d<e;d++)f=b[d],c=w(f).toString(),Yt(a,c,f)&&h.push(f);d=0;for(e=h.length;d<e;d++){f=h[d];c=w(f).toString();Zt(a,c,f);var m=f.U();m?(c=m.D(),g.push(c),l.push(f)):a.f[c]=f}a.a&&a.a.load(g,l);d=0;for(e=h.length;d<e;d++)a.b(new $t("addfeature",h[d]))} -function Xt(a,b){var c=!1;z(a,"addfeature",function(a){c||(c=!0,b.push(a.feature),c=!1)});z(a,"removefeature",function(a){c||(c=!0,b.remove(a.feature),c=!1)});z(b,"add",function(a){c||(c=!0,this.zb(a.element),c=!1)},a);z(b,"remove",function(a){c||(c=!0,this.Db(a.element),c=!1)},a);a.i=b} -k.clear=function(a){if(a){for(var b in this.u)this.u[b].forEach(Bc);this.i||(this.u={},this.l={},this.o={})}else if(this.a){this.a.forEach(this.Cg,this);for(var c in this.f)this.Cg(this.f[c])}this.i&&this.i.clear();this.a&&this.a.clear();this.na.clear();this.f={};this.b(new $t("clear"));this.s()};k.kh=function(a,b){if(this.a)return this.a.forEach(a,b);if(this.i)return this.i.forEach(a,b)};function au(a,b,c){a.bc([b[0],b[1],b[0],b[1]],function(a){if(a.U().sb(b))return c.call(void 0,a)})} -k.bc=function(a,b,c){if(this.a)return Lj(this.a,a,b,c);if(this.i)return this.i.forEach(b,c)};k.lh=function(a,b,c){return this.bc(a,function(d){if(d.U().Ya(a)&&(d=b.call(c,d)))return d})};k.th=function(){return this.i};k.We=function(){var a;this.i?a=this.i.a:this.a&&(a=Ij(this.a),tb(this.f)||ha(a,sb(this.f)));return a};k.sh=function(a){var b=[];au(this,a,function(a){b.push(a)});return b};k.Pf=function(a){return Jj(this.a,a)}; -k.oh=function(a,b){var c=a[0],d=a[1],e=null,f=[NaN,NaN],g=Infinity,h=[-Infinity,-Infinity,Infinity,Infinity],l=b?b:jf;Lj(this.a,h,function(a){if(l(a)){var b=a.U(),m=g;g=b.Hb(c,d,f,g);g<m&&(e=a,a=Math.sqrt(g),h[0]=c-a,h[1]=d-a,h[2]=c+a,h[3]=d+a)}});return e};k.D=function(a){return this.a.D(a)};k.rh=function(a){a=this.l[a.toString()];return void 0!==a?a:null};k.Gi=function(){return this.T};k.Hi=function(){return this.fa}; -k.Ii=function(a){a=a.target;var b=w(a).toString(),c=a.U();c?(c=c.D(),b in this.f?(delete this.f[b],this.a&&this.a.Ea(c,a)):this.a&&Hj(this.a,c,a)):b in this.f||(this.a&&this.a.remove(a),this.f[b]=a);c=a.a;void 0!==c?(c=c.toString(),b in this.o?(delete this.o[b],this.l[c]=a):this.l[c]!==a&&(bu(this,a),this.l[c]=a)):b in this.o||(bu(this,a),this.o[b]=a);this.s();this.b(new $t("changefeature",a))}; -k.Xd=function(a,b,c){var d=this.na;a=this.Va(a,b);var e,f;e=0;for(f=a.length;e<f;++e){var g=a[e];Lj(d,g,function(a){return Ua(a.extent,g)})||(this.ea.call(this,g,b,c),d.Ea(g,{extent:g.slice()}))}};k.Db=function(a){var b=w(a).toString();b in this.f?delete this.f[b]:this.a&&this.a.remove(a);this.Cg(a);this.s()};k.Cg=function(a){var b=w(a).toString();this.u[b].forEach(Bc);delete this.u[b];var c=a.a;void 0!==c?delete this.l[c.toString()]:delete this.o[b];this.b(new $t("removefeature",a))}; -function bu(a,b){for(var c in a.l)if(a.l[c]===b){delete a.l[c];break}}function $t(a,b){Lc.call(this,a);this.feature=b}u($t,Lc);function cu(a){Ag.call(this,{handleDownEvent:du,handleEvent:eu,handleUpEvent:fu});this.T=!1;this.fa=null;this.u=!1;this.Gb=a.source?a.source:null;this.Va=a.features?a.features:null;this.sk=a.snapTolerance?a.snapTolerance:12;this.Z=a.type;this.f=gu(this.Z);this.Ha=a.minPoints?a.minPoints:this.f===hu?3:2;this.Ja=a.maxPoints?a.maxPoints:Infinity;this.yf=a.finishCondition?a.finishCondition:jf;var b=a.geometryFunction;if(!b)if("Circle"===this.Z)b=function(a,b){var c=b?b:new vs([NaN,NaN]);c.Gg(a[0],Math.sqrt(ef(a[0], -a[1])));return c};else{var c,d=this.f;d===iu?c=E:d===ju?c=N:d===hu&&(c=F);b=function(a,b){var e=b;e?d===hu?e.pa([a[0].concat([a[0][0]])]):e.pa(a):e=new c(a);return e}}this.Qa=b;this.I=this.C=this.a=this.G=this.j=this.o=null;this.le=a.clickTolerance?a.clickTolerance*a.clickTolerance:36;this.na=new S({source:new T({useSpatialIndex:!1,wrapX:a.wrapX?a.wrapX:!1}),style:a.style?a.style:ku()});this.yb=a.geometryName;this.rk=a.condition?a.condition:vg;this.zf=a.freehand?jf:a.freehandCondition?a.freehandCondition: -wg;z(this,Sc("active"),this.ji,this)}u(cu,Ag);function ku(){var a=gl();return function(b){return a[b.U().S()]}}k=cu.prototype;k.setMap=function(a){Ag.prototype.setMap.call(this,a);this.ji()};function eu(a){this.u=this.f!==iu&&this.zf(a);var b=!this.u;this.u&&"pointerdrag"===a.type&&null!==this.j?(lu(this,a),b=!1):"pointermove"===a.type?b=mu(this,a):"dblclick"===a.type&&(b=!1);return Bg.call(this,a)&&b} -function du(a){this.T=!this.u;return this.u?(this.fa=a.pixel,this.o||nu(this,a),!0):this.rk(a)?(this.fa=a.pixel,!0):!1}function fu(a){var b=!0;mu(this,a);var c=this.f===ou;this.T?(this.o?this.u||c?this.Qd():pu(this,a)?this.yf(a)&&this.Qd():lu(this,a):(nu(this,a),this.f===iu&&this.Qd()),b=!1):this.u&&(this.o=null,qu(this));return b} -function mu(a,b){if(a.fa&&(!a.u&&a.T||a.u&&!a.T)){var c=a.fa,d=b.pixel,e=c[0]-d[0],c=c[1]-d[1],e=e*e+c*c;a.T=a.u?e>a.le:e<=a.le}a.o?(e=b.coordinate,c=a.j.U(),a.f===iu?d=a.a:a.f===hu?(d=a.a[0],d=d[d.length-1],pu(a,b)&&(e=a.o.slice())):(d=a.a,d=d[d.length-1]),d[0]=e[0],d[1]=e[1],a.Qa(a.a,c),a.G&&a.G.U().pa(e),c instanceof F&&a.f!==hu?(a.C||(a.C=new I(new N(null))),c=c.vh(0),e=a.C.U(),e.ca(c.la,c.ia())):a.I&&(e=a.C.U(),e.pa(a.I)),ru(a)):(e=b.coordinate.slice(),a.G?a.G.U().pa(e):(a.G=new I(new E(e)), -ru(a)));return!0}function pu(a,b){var c=!1;if(a.j){var d=!1,e=[a.o];a.f===ju?d=a.a.length>a.Ha:a.f===hu&&(d=a.a[0].length>a.Ha,e=[a.a[0][0],a.a[0][a.a[0].length-2]]);if(d)for(var d=b.map,f=0,g=e.length;f<g;f++){var h=e[f],l=d.Ka(h),m=b.pixel,c=m[0]-l[0],l=m[1]-l[1];if(c=Math.sqrt(c*c+l*l)<=(a.u?1:a.sk)){a.o=h;break}}}return c} -function nu(a,b){var c=b.coordinate;a.o=c;a.f===iu?a.a=c.slice():a.f===hu?(a.a=[[c.slice(),c.slice()]],a.I=a.a[0]):(a.a=[c.slice(),c.slice()],a.f===ou&&(a.I=a.a));a.I&&(a.C=new I(new N(a.I)));c=a.Qa(a.a);a.j=new I;a.yb&&a.j.Yc(a.yb);a.j.Ta(c);ru(a);a.b(new su("drawstart",a.j))} -function lu(a,b){var c=b.coordinate,d=a.j.U(),e,f;a.f===ju?(a.o=c.slice(),f=a.a,f.length>=a.Ja&&(a.u?f.pop():e=!0),f.push(c.slice()),a.Qa(f,d)):a.f===hu&&(f=a.a[0],f.length>=a.Ja&&(a.u?f.pop():e=!0),f.push(c.slice()),e&&(a.o=f[0]),a.Qa(a.a,d));ru(a);e&&a.Qd()} -k.Ep=function(){if(this.j){var a=this.j.U(),b,c;this.f===ju?(b=this.a,b.splice(-2,1),this.Qa(b,a),2<=b.length&&(this.o=b[b.length-2].slice())):this.f===hu&&(b=this.a[0],b.splice(-2,1),c=this.C.U(),c.pa(b),this.Qa(this.a,a));0===b.length&&(this.o=null);ru(this)}}; -k.Qd=function(){var a=qu(this),b=this.a,c=a.U();this.f===ju?(b.pop(),this.Qa(b,c)):this.f===hu&&(b[0].pop(),this.Qa(b,c),b=c.W());"MultiPoint"===this.Z?a.Ta(new P([b])):"MultiLineString"===this.Z?a.Ta(new O([b])):"MultiPolygon"===this.Z&&a.Ta(new Q([b]));this.b(new su("drawend",a));this.Va&&this.Va.push(a);this.Gb&&this.Gb.zb(a)};function qu(a){a.o=null;var b=a.j;b&&(a.j=null,a.G=null,a.C=null,a.na.ka().clear(!0));return b} -k.nn=function(a){var b=a.U();this.j=a;this.a=b.W();a=this.a[this.a.length-1];this.o=a.slice();this.a.push(a.slice());ru(this);this.b(new su("drawstart",this.j))};k.bd=kf;function ru(a){var b=[];a.j&&b.push(a.j);a.C&&b.push(a.C);a.G&&b.push(a.G);a=a.na.ka();a.clear(!0);a.gd(b)}k.ji=function(){var a=this.v,b=this.c();a&&b||qu(this);this.na.setMap(b?a:null)}; -function gu(a){var b;"Point"===a||"MultiPoint"===a?b=iu:"LineString"===a||"MultiLineString"===a?b=ju:"Polygon"===a||"MultiPolygon"===a?b=hu:"Circle"===a&&(b=ou);return b}var iu="Point",ju="LineString",hu="Polygon",ou="Circle";function su(a,b){Lc.call(this,a);this.feature=b}u(su,Lc);function tu(a){this.a=this.j=null;this.C=!1;this.G=this.o=null;a||(a={});a.extent&&this.f(a.extent);Ag.call(this,{handleDownEvent:uu,handleDragEvent:vu,handleEvent:wu,handleUpEvent:xu});this.u=new S({source:new T({useSpatialIndex:!1,wrapX:!!a.wrapX}),style:a.boxStyle?a.boxStyle:yu(),updateWhileAnimating:!0,updateWhileInteracting:!0});this.I=new S({source:new T({useSpatialIndex:!1,wrapX:!!a.wrapX}),style:a.pointerStyle?a.pointerStyle:zu(),updateWhileAnimating:!0,updateWhileInteracting:!0})}u(tu,Ag); -function wu(a){if(!(a instanceof Kd))return!0;if("pointermove"==a.type&&!this.A){var b=a.pixel,c=a.map,d=Au(this,b,c);d||(d=c.Xa(b));Bu(this,d)}Bg.call(this,a);return!1} -function uu(a){function b(a){var b=null,c=null;a[0]==e[0]?b=e[2]:a[0]==e[2]&&(b=e[0]);a[1]==e[1]?c=e[3]:a[1]==e[3]&&(c=e[1]);return null!==b&&null!==c?[b,c]:null}var c=a.pixel,d=a.map,e=this.D();(a=Au(this,c,d))&&e?(c=a[0]==e[0]||a[0]==e[2]?a[0]:null,d=a[1]==e[1]||a[1]==e[3]?a[1]:null,null!==c&&null!==d?this.a=Cu(b(a)):null!==c?this.a=Du(b([c,e[1]]),b([c,e[3]])):null!==d&&(this.a=Du(b([e[0],d]),b([e[2],d])))):(a=d.Xa(c),this.f([a[0],a[1],a[0],a[1]]),this.a=Cu(a));return!0} -function vu(a){this.a&&(a=a.coordinate,this.f(this.a(a)),Bu(this,a));return!0}function xu(){this.a=null;var a=this.D();a&&gb(a)||this.f(null);return!1}function yu(){var a=gl();return function(){return a.Polygon}}function zu(){var a=gl();return function(){return a.Point}}function Cu(a){return function(b){return Ia([a,b])}}function Du(a,b){return a[0]==b[0]?function(c){return Ia([a,[c[0],b[1]]])}:a[1]==b[1]?function(c){return Ia([a,[b[0],c[1]]])}:null} -function Au(a,b,c){function d(a,b){return gf(e,a)-gf(e,b)}var e=c.Xa(b),f=a.D();if(f){f=[[[f[0],f[1]],[f[0],f[3]]],[[f[0],f[3]],[f[2],f[3]]],[[f[2],f[3]],[f[2],f[1]]],[[f[2],f[1]],[f[0],f[1]]]];f.sort(d);var f=f[0],g=Ye(e,f),h=c.Ka(g);if(10>=ff(b,h))return b=c.Ka(f[0]),c=c.Ka(f[1]),b=ef(h,b),c=ef(h,c),a.C=10>=Math.sqrt(Math.min(b,c)),a.C&&(g=b>c?f[1]:f[0]),g}return null}function Bu(a,b){var c=a.G;c?c.U().pa(b):(c=new I(new E(b)),a.G=c,a.I.ka().zb(c))} -tu.prototype.setMap=function(a){this.u.setMap(a);this.I.setMap(a);Ag.prototype.setMap.call(this,a)};tu.prototype.D=function(){return this.j};tu.prototype.f=function(a){this.j=a?a:null;var b=this.o;b?a?b.Ta(Vf(a)):b.Ta(void 0):(this.o=b=a?new I(Vf(a)):new I({}),this.u.ka().zb(b));this.b(new Eu(this.j))};function Eu(a){Lc.call(this,Fu);this.b=a}u(Eu,Lc);var Fu="extentchanged";function Gu(a){Ag.call(this,{handleDownEvent:Hu,handleDragEvent:Iu,handleEvent:Ju,handleUpEvent:Ku});this.Gb=a.condition?a.condition:zg;this.Va=function(a){return vg(a)&&tg(a)};this.yb=a.deleteCondition?a.deleteCondition:this.Va;this.Ha=this.f=null;this.Ja=[0,0];this.C=this.I=!1;this.a=new Gj;this.fa=void 0!==a.pixelTolerance?a.pixelTolerance:10;this.o=this.na=!1;this.j=[];this.G=new S({source:new T({useSpatialIndex:!1,wrapX:!!a.wrapX}),style:a.style?a.style:Lu(),updateWhileAnimating:!0,updateWhileInteracting:!0}); -this.T={Point:this.wn,LineString:this.li,LinearRing:this.li,Polygon:this.xn,MultiPoint:this.tn,MultiLineString:this.sn,MultiPolygon:this.vn,Circle:this.lq,GeometryCollection:this.rn};this.u=a.features;this.u.forEach(this.fg,this);z(this.u,"add",this.pn,this);z(this.u,"remove",this.qn,this);this.Z=null}u(Gu,Ag);k=Gu.prototype;k.fg=function(a){var b=a.U();b&&b.S()in this.T&&this.T[b.S()].call(this,a,b);(b=this.v)&&b.a&&this.c()&&Mu(this,this.Ja,b);z(a,"change",this.ki,this)}; -function Nu(a,b){a.C||(a.C=!0,a.b(new Ou("modifystart",a.u,b)))}function Pu(a,b){Qu(a,b);a.f&&!a.u.fc()&&(a.G.ka().Db(a.f),a.f=null);Hc(b,"change",a.ki,a)}function Qu(a,b){var c=a.a,d=[];c.forEach(function(a){b===a.feature&&d.push(a)});for(var e=d.length-1;0<=e;--e)c.remove(d[e])}k.Ia=function(a){this.f&&!a&&(this.G.ka().Db(this.f),this.f=null);Ag.prototype.Ia.call(this,a)};k.setMap=function(a){this.G.setMap(a);Ag.prototype.setMap.call(this,a)};k.pn=function(a){this.fg(a.element)}; -k.ki=function(a){this.o||(a=a.target,Pu(this,a),this.fg(a))};k.qn=function(a){Pu(this,a.element)};k.wn=function(a,b){var c=b.W(),c={feature:a,geometry:b,oa:[c,c]};this.a.Ea(b.D(),c)};k.tn=function(a,b){var c=b.W(),d,e,f;e=0;for(f=c.length;e<f;++e)d=c[e],d={feature:a,geometry:b,depth:[e],index:e,oa:[d,d]},this.a.Ea(b.D(),d)};k.li=function(a,b){var c=b.W(),d,e,f,g;d=0;for(e=c.length-1;d<e;++d)f=c.slice(d,d+2),g={feature:a,geometry:b,index:d,oa:f},this.a.Ea(Ia(f),g)}; -k.sn=function(a,b){var c=b.W(),d,e,f,g,h,l,m;g=0;for(h=c.length;g<h;++g)for(d=c[g],e=0,f=d.length-1;e<f;++e)l=d.slice(e,e+2),m={feature:a,geometry:b,depth:[g],index:e,oa:l},this.a.Ea(Ia(l),m)};k.xn=function(a,b){var c=b.W(),d,e,f,g,h,l,m;g=0;for(h=c.length;g<h;++g)for(d=c[g],e=0,f=d.length-1;e<f;++e)l=d.slice(e,e+2),m={feature:a,geometry:b,depth:[g],index:e,oa:l},this.a.Ea(Ia(l),m)}; -k.vn=function(a,b){var c=b.W(),d,e,f,g,h,l,m,n,p,q;l=0;for(m=c.length;l<m;++l)for(n=c[l],g=0,h=n.length;g<h;++g)for(d=n[g],e=0,f=d.length-1;e<f;++e)p=d.slice(e,e+2),q={feature:a,geometry:b,depth:[g,l],index:e,oa:p},this.a.Ea(Ia(p),q)};k.lq=function(a,b){var c=b.za(),d={feature:a,geometry:b,index:0,oa:[c,c]},e={feature:a,geometry:b,index:1,oa:[c,c]};d.Lf=e.Lf=[d,e];this.a.Ea(Xa(c),d);this.a.Ea(b.D(),e)};k.rn=function(a,b){var c,d=b.a;for(c=0;c<d.length;++c)this.T[d[c].S()].call(this,a,d[c])}; -function Ru(a,b){var c=a.f;c?c.U().pa(b):(c=new I(new E(b)),a.f=c,a.G.ka().zb(c))}function Su(a,b){return a.index-b.index} -function Hu(a){if(!this.Gb(a))return!1;Mu(this,a.pixel,a.map);var b=a.map.Xa(a.pixel);this.j.length=0;this.C=!1;var c=this.f;if(c){var d=[],c=c.U().W(),e=Ia([c]),e=Jj(this.a,e),f={};e.sort(Su);for(var g=0,h=e.length;g<h;++g){var l=e[g],m=l.oa,n=w(l.feature),p=l.depth;p&&(n+="-"+p.join("-"));f[n]||(f[n]=Array(2));if("Circle"===l.geometry.S()&&1===l.index)m=Tu(b,l),af(m,c)&&!f[n][0]&&(this.j.push([l,0]),f[n][0]=l);else if(af(m[0],c)&&!f[n][0])this.j.push([l,0]),f[n][0]=l;else if(af(m[1],c)&&!f[n][1]){if("LineString"!== -l.geometry.S()&&"MultiLineString"!==l.geometry.S()||!f[n][0]||0!==f[n][0].index)this.j.push([l,1]),f[n][1]=l}else w(m)in this.Ha&&!f[n][0]&&!f[n][1]&&d.push([l,c])}d.length&&Nu(this,a);for(a=d.length-1;0<=a;--a)this.Xl.apply(this,d[a])}return!!this.f} -function Iu(a){this.I=!1;Nu(this,a);a=a.coordinate;for(var b=0,c=this.j.length;b<c;++b){for(var d=this.j[b],e=d[0],f=e.depth,g=e.geometry,h,l=e.oa,d=d[1];a.length<g.sa();)a.push(l[d][a.length]);switch(g.S()){case "Point":h=a;l[0]=l[1]=a;break;case "MultiPoint":h=g.W();h[e.index]=a;l[0]=l[1]=a;break;case "LineString":h=g.W();h[e.index+d]=a;l[d]=a;break;case "MultiLineString":h=g.W();h[f[0]][e.index+d]=a;l[d]=a;break;case "Polygon":h=g.W();h[f[0]][e.index+d]=a;l[d]=a;break;case "MultiPolygon":h=g.W(); -h[f[1]][f[0]][e.index+d]=a;l[d]=a;break;case "Circle":l[0]=l[1]=a,0===e.index?(this.o=!0,g.lb(a)):(this.o=!0,g.Zc(ff(g.za(),a))),this.o=!1}h&&(e=g,f=h,this.o=!0,e.pa(f),this.o=!1)}Ru(this,a)}function Ku(a){for(var b,c,d=this.j.length-1;0<=d;--d)if(b=this.j[d][0],c=b.geometry,"Circle"===c.S()){var e=c.za(),f=b.Lf[0];b=b.Lf[1];f.oa[0]=f.oa[1]=e;b.oa[0]=b.oa[1]=e;Hj(this.a,Xa(e),f);Hj(this.a,c.D(),b)}else Hj(this.a,Ia(b.oa),b);this.C&&(this.b(new Ou("modifyend",this.u,a)),this.C=!1);return!1} -function Ju(a){if(!(a instanceof Kd))return!0;this.Z=a;var b;ag(a.map.$())[1]||"pointermove"!=a.type||this.A||(this.Ja=a.pixel,Mu(this,a.pixel,a.map));this.f&&this.yb(a)&&(b="singleclick"==a.type&&this.I?!0:this.cj());"singleclick"==a.type&&(this.I=!1);return Bg.call(this,a)&&!b} -function Mu(a,b,c){function d(a,b){return Uu(e,a)-Uu(e,b)}var e=c.Xa(b),f=Ma(Xa(e),c.$().Ra()*a.fa),f=Jj(a.a,f);if(0<f.length){f.sort(d);var g=f[0],h=g.oa,l=Tu(e,g),m=c.Ka(l),n=ff(b,m);if(n<=a.fa){b={};if("Circle"===g.geometry.S()&&1===g.index)a.na=!0,Ru(a,l);else for(n=c.Ka(h[0]),g=c.Ka(h[1]),c=ef(m,n),m=ef(m,g),n=Math.sqrt(Math.min(c,m)),a.na=n<=a.fa,a.na&&(l=c>m?h[1]:h[0]),Ru(a,l),m=1,c=f.length;m<c;++m)if(l=f[m].oa,af(h[0],l[0])&&af(h[1],l[1])||af(h[0],l[1])&&af(h[1],l[0]))b[w(l)]=!0;else break; -b[w(h)]=!0;a.Ha=b;return}}a.f&&(a.G.ka().Db(a.f),a.f=null)}function Uu(a,b){var c=b.geometry;if("Circle"===c.S()&&1===b.index){var d=ef(c.za(),a),c=Math.sqrt(d)-c.Yd();return c*c}return gf(a,b.oa)}function Tu(a,b){var c=b.geometry;return"Circle"===c.S()&&1===b.index?c.Ab(a):Ye(a,b.oa)} -k.Xl=function(a,b){for(var c=a.oa,d=a.feature,e=a.geometry,f=a.depth,g=a.index,h;b.length<e.sa();)b.push(0);switch(e.S()){case "MultiLineString":h=e.W();h[f[0]].splice(g+1,0,b);break;case "Polygon":h=e.W();h[f[0]].splice(g+1,0,b);break;case "MultiPolygon":h=e.W();h[f[1]][f[0]].splice(g+1,0,b);break;case "LineString":h=e.W();h.splice(g+1,0,b);break;default:return}this.o=!0;e.pa(h);this.o=!1;h=this.a;h.remove(a);Vu(this,e,g,f,1);var l={oa:[c[0],b],feature:d,geometry:e,depth:f,index:g};h.Ea(Ia(l.oa), -l);this.j.push([l,1]);c={oa:[b,c[1]],feature:d,geometry:e,depth:f,index:g+1};h.Ea(Ia(c.oa),c);this.j.push([c,0]);this.I=!0}; -k.cj=function(){if(this.Z&&"pointerdrag"!=this.Z.type){var a=this.Z;Nu(this,a);var b=this.j,c={},d,e,f,g,h,l,m,n,p,q;for(h=b.length-1;0<=h;--h)g=b[h],p=g[0],q=w(p.feature),p.depth&&(q+="-"+p.depth.join("-")),q in c||(c[q]={}),0===g[1]?(c[q].right=p,c[q].index=p.index):1==g[1]&&(c[q].left=p,c[q].index=p.index+1);for(q in c){n=c[q].right;l=c[q].left;h=c[q].index;m=h-1;p=void 0!==l?l:n;0>m&&(m=0);g=p.geometry;e=f=g.W();d=!1;switch(g.S()){case "MultiLineString":2<f[p.depth[0]].length&&(f[p.depth[0]].splice(h, -1),d=!0);break;case "LineString":2<f.length&&(f.splice(h,1),d=!0);break;case "MultiPolygon":e=e[p.depth[1]];case "Polygon":e=e[p.depth[0]],4<e.length&&(h==e.length-1&&(h=0),e.splice(h,1),d=!0,0===h&&(e.pop(),e.push(e[0]),m=e.length-1))}d&&(d=g,this.o=!0,d.pa(f),this.o=!1,f=[],void 0!==l&&(this.a.remove(l),f.push(l.oa[0])),void 0!==n&&(this.a.remove(n),f.push(n.oa[1])),void 0!==l&&void 0!==n&&(l={depth:p.depth,feature:p.feature,geometry:p.geometry,index:m,oa:f},this.a.Ea(Ia(l.oa),l)),Vu(this,g,h,p.depth, --1),this.f&&(this.G.ka().Db(this.f),this.f=null),b.length=0)}this.b(new Ou("modifyend",this.u,a));this.C=!1;return!0}return!1};function Vu(a,b,c,d,e){Lj(a.a,b.D(),function(a){a.geometry===b&&(void 0===d||void 0===a.depth||ja(a.depth,d))&&a.index>c&&(a.index+=e)})}function Lu(){var a=gl();return function(){return a.Point}}function Ou(a,b,c){Lc.call(this,a);this.features=b;this.mapBrowserEvent=c}u(Ou,Lc);function Wu(a){kg.call(this,{handleEvent:Xu});a=a?a:{};this.C=a.condition?a.condition:tg;this.A=a.addCondition?a.addCondition:kf;this.G=a.removeCondition?a.removeCondition:kf;this.I=a.toggleCondition?a.toggleCondition:wg;this.o=a.multi?a.multi:!1;this.l=a.filter?a.filter:jf;this.j=a.hitTolerance?a.hitTolerance:0;this.f=new S({source:new T({useSpatialIndex:!1,features:a.features,wrapX:a.wrapX}),style:a.style?a.style:Yu(),updateWhileAnimating:!0,updateWhileInteracting:!0});if(a.layers)if("function"=== -typeof a.layers)a=a.layers;else{var b=a.layers;a=function(a){return fa(b,a)}}else a=jf;this.u=a;this.a={};a=this.f.ka().i;z(a,"add",this.yn,this);z(a,"remove",this.Cn,this)}u(Wu,kg);k=Wu.prototype;k.zn=function(){return this.f.ka().i};k.An=function(){return this.j};k.Bn=function(a){a=w(a);return this.a[a]}; -function Xu(a){if(!this.C(a))return!0;var b=this.A(a),c=this.G(a),d=this.I(a),e=!b&&!c&&!d,f=a.map,g=this.f.ka().i,h=[],l=[];if(e){rb(this.a);f.we(a.pixel,function(a,b){if(this.l(a,b)){l.push(a);var c=w(a);this.a[c]=b;return!this.o}}.bind(this),{layerFilter:this.u,hitTolerance:this.j});for(e=g.fc()-1;0<=e;--e){var f=g.item(e),m=l.indexOf(f);-1<m?l.splice(m,1):(g.remove(f),h.push(f))}l.length&&g.ag(l)}else{f.we(a.pixel,function(a,e){if(this.l(a,e)){if(!b&&!d||fa(g.a,a))(c||d)&&fa(g.a,a)&&(h.push(a), -f=w(a),delete this.a[f]);else{l.push(a);var f=w(a);this.a[f]=e}return!this.o}}.bind(this),{layerFilter:this.u,hitTolerance:this.j});for(e=h.length-1;0<=e;--e)g.remove(h[e]);g.ag(l)}(0<l.length||0<h.length)&&this.b(new Zu($u,l,h,a));return sg(a)}k.Dn=function(a){this.j=a};k.setMap=function(a){var b=this.v,c=this.f.ka().i;b&&c.forEach(b.yj,b);kg.prototype.setMap.call(this,a);this.f.setMap(a);a&&c.forEach(a.tj,a)}; -function Yu(){var a=gl();ha(a.Polygon,a.LineString);ha(a.GeometryCollection,a.LineString);return function(b){return b.U()?a[b.U().S()]:null}}k.yn=function(a){var b=this.v;b&&b.tj(a.element)};k.Cn=function(a){var b=this.v;b&&b.yj(a.element)};function Zu(a,b,c,d){Lc.call(this,a);this.selected=b;this.deselected=c;this.mapBrowserEvent=d}u(Zu,Lc);var $u="select";function av(a){Ag.call(this,{handleEvent:bv,handleDownEvent:jf,handleUpEvent:cv});a=a?a:{};this.o=a.source?a.source:null;this.fa=void 0!==a.vertex?a.vertex:!0;this.I=void 0!==a.edge?a.edge:!0;this.j=a.features?a.features:null;this.na=[];this.C={};this.Z={};this.u={};this.G=null;this.f=void 0!==a.pixelTolerance?a.pixelTolerance:10;this.Ja=dv.bind(this);this.a=new Gj;this.T={Point:this.Jn,LineString:this.oi,LinearRing:this.oi,Polygon:this.Kn,MultiPoint:this.Hn,MultiLineString:this.Gn,MultiPolygon:this.In, -GeometryCollection:this.Fn}}u(av,Ag);k=av.prototype;k.zb=function(a,b){var c=void 0!==b?b:!0,d=w(a),e=a.U();if(e){var f=this.T[e.S()];f&&(this.Z[d]=e.D(Ja()),f.call(this,a,e))}c&&(this.C[d]=z(a,"change",this.En,this))};k.wk=function(a){this.zb(a)};k.xk=function(a){this.Db(a)};k.mi=function(a){var b;a instanceof $t?b=a.feature:a instanceof Yc&&(b=a.element);this.zb(b)};k.ni=function(a){var b;a instanceof $t?b=a.feature:a instanceof Yc&&(b=a.element);this.Db(b)}; -k.En=function(a){a=a.target;if(this.A){var b=w(a);b in this.u||(this.u[b]=a)}else this.zj(a)};k.Db=function(a,b){var c=void 0!==b?b:!0,d=w(a),e=this.Z[d];if(e){var f=this.a,g=[];Lj(f,e,function(b){a===b.feature&&g.push(b)});for(e=g.length-1;0<=e;--e)f.remove(g[e])}c&&(Bc(this.C[d]),delete this.C[d])}; -k.setMap=function(a){var b=this.v,c=this.na,d;this.j?d=this.j:this.o&&(d=this.o.We());b&&(c.forEach(Bc),c.length=0,d.forEach(this.xk,this));Ag.prototype.setMap.call(this,a);a&&(this.j?c.push(z(this.j,"add",this.mi,this),z(this.j,"remove",this.ni,this)):this.o&&c.push(z(this.o,"addfeature",this.mi,this),z(this.o,"removefeature",this.ni,this)),d.forEach(this.wk,this))};k.bd=kf;k.zj=function(a){this.Db(a,!1);this.zb(a,!1)}; -k.Fn=function(a,b){var c,d=b.a;for(c=0;c<d.length;++c)this.T[d[c].S()].call(this,a,d[c])};k.oi=function(a,b){var c=b.W(),d,e,f,g;d=0;for(e=c.length-1;d<e;++d)f=c.slice(d,d+2),g={feature:a,oa:f},this.a.Ea(Ia(f),g)};k.Gn=function(a,b){var c=b.W(),d,e,f,g,h,l,m;g=0;for(h=c.length;g<h;++g)for(d=c[g],e=0,f=d.length-1;e<f;++e)l=d.slice(e,e+2),m={feature:a,oa:l},this.a.Ea(Ia(l),m)};k.Hn=function(a,b){var c=b.W(),d,e,f;e=0;for(f=c.length;e<f;++e)d=c[e],d={feature:a,oa:[d,d]},this.a.Ea(b.D(),d)}; -k.In=function(a,b){var c=b.W(),d,e,f,g,h,l,m,n,p,q;l=0;for(m=c.length;l<m;++l)for(n=c[l],g=0,h=n.length;g<h;++g)for(d=n[g],e=0,f=d.length-1;e<f;++e)p=d.slice(e,e+2),q={feature:a,oa:p},this.a.Ea(Ia(p),q)};k.Jn=function(a,b){var c=b.W(),c={feature:a,oa:[c,c]};this.a.Ea(b.D(),c)};k.Kn=function(a,b){var c=b.W(),d,e,f,g,h,l,m;g=0;for(h=c.length;g<h;++g)for(d=c[g],e=0,f=d.length-1;e<f;++e)l=d.slice(e,e+2),m={feature:a,oa:l},this.a.Ea(Ia(l),m)}; -function bv(a){var b,c,d=a.pixel,e=a.coordinate;b=a.map;var f=b.Xa([d[0]-this.f,d[1]+this.f]);c=b.Xa([d[0]+this.f,d[1]-this.f]);var f=Ia([f,c]),g=Jj(this.a,f),h,f=!1,l=null;c=null;if(0<g.length){this.G=e;g.sort(this.Ja);g=g[0].oa;if(this.fa&&!this.I){if(e=b.Ka(g[0]),h=b.Ka(g[1]),e=ef(d,e),d=ef(d,h),h=Math.sqrt(Math.min(e,d)),h=h<=this.f)f=!0,l=e>d?g[1]:g[0],c=b.Ka(l)}else this.I&&(l=Ye(e,g),c=b.Ka(l),ff(d,c)<=this.f&&(f=!0,this.fa&&(e=b.Ka(g[0]),h=b.Ka(g[1]),e=ef(c,e),d=ef(c,h),h=Math.sqrt(Math.min(e, -d)),h=h<=this.f)))&&(l=e>d?g[1]:g[0],c=b.Ka(l));f&&(c=[Math.round(c[0]),Math.round(c[1])])}b=l;f&&(a.coordinate=b.slice(0,2),a.pixel=c);return Bg.call(this,a)}function cv(){var a=sb(this.u);a.length&&(a.forEach(this.zj,this),this.u={});return!1}function dv(a,b){return gf(this.G,a.oa)-gf(this.G,b.oa)};function ev(a){Ag.call(this,{handleDownEvent:fv,handleDragEvent:gv,handleMoveEvent:hv,handleUpEvent:iv});a=a?a:{};this.f=void 0;this.a=null;this.o=void 0!==a.features?a.features:null;var b;if(a.layers)if("function"===typeof a.layers)b=a.layers;else{var c=a.layers;b=function(a){return fa(c,a)}}else b=jf;this.G=b;this.u=a.hitTolerance?a.hitTolerance:0;this.j=null;z(this,Sc("active"),this.C,this)}u(ev,Ag); -function fv(a){this.j=jv(this,a.pixel,a.map);if(!this.a&&this.j){this.a=a.coordinate;hv.call(this,a);var b=this.o||new D([this.j]);this.b(new kv("translatestart",b,a.coordinate));return!0}return!1}function iv(a){if(this.a){this.a=null;hv.call(this,a);var b=this.o||new D([this.j]);this.b(new kv("translateend",b,a.coordinate));return!0}return!1} -function gv(a){if(this.a){a=a.coordinate;var b=a[0]-this.a[0],c=a[1]-this.a[1],d=this.o||new D([this.j]);d.forEach(function(a){var d=a.U();d.translate(b,c);a.Ta(d)});this.a=a;this.b(new kv("translating",d,a))}}function hv(a){var b=a.map.vc();jv(this,a.pixel,a.map)?(this.f=void 0!==this.f?this.f:b.style.cursor,b.style.cursor=this.a?"-webkit-grabbing":"-webkit-grab",b.style.cursor=this.a?"grabbing":"grab"):void 0!==this.f&&(b.style.cursor=this.f,this.f=void 0)} -function jv(a,b,c){return c.we(b,function(a){if(!this.o||fa(this.o.a,a))return a}.bind(a),{layerFilter:a.G,hitTolerance:a.u})}ev.prototype.I=function(){return this.u};ev.prototype.Z=function(a){this.u=a};ev.prototype.setMap=function(a){var b=this.v;Ag.prototype.setMap.call(this,a);lv(this,b)};ev.prototype.C=function(){lv(this,null)};function lv(a,b){var c=a.v,d=a.c();c&&d||void 0===a.f||(c||(c=b),c.vc().style.cursor=a.f,a.f=void 0)} -function kv(a,b,c){Lc.call(this,a);this.features=b;this.coordinate=c}u(kv,Lc);function U(a){a=a?a:{};var b=qb({},a);delete b.gradient;delete b.radius;delete b.blur;delete b.shadow;delete b.weight;S.call(this,b);this.j=null;this.T=void 0!==a.shadow?a.shadow:250;this.Z=void 0;this.I=null;z(this,Sc(mv),this.wl,this);this.kj(a.gradient?a.gradient:nv);this.ej(void 0!==a.blur?a.blur:15);this.Zc(void 0!==a.radius?a.radius:8);z(this,Sc(ov),this.Yf,this);z(this,Sc(pv),this.Yf,this);this.Yf();var c=a.weight?a.weight:"weight",d;"string"===typeof c?d=function(a){return a.get(c)}:d=c;this.f(function(a){a= -d(a);a=void 0!==a?xa(a,0,1):1;var b=255*a|0,c=this.I[b];c||(c=[new bl({image:new co({opacity:a,src:this.Z})})],this.I[b]=c);return c}.bind(this));this.set(It,null);z(this,"render",this.Nl,this)}u(U,S);var nv=["#00f","#0ff","#0f0","#ff0","#f00"];k=U.prototype;k.nh=function(){return this.get(ov)};k.uh=function(){return this.get(mv)};k.ri=function(){return this.get(pv)}; -k.wl=function(){for(var a=this.uh(),b=hd(1,256),c=b.createLinearGradient(0,0,1,256),d=1/(a.length-1),e=0,f=a.length;e<f;++e)c.addColorStop(e*d,a[e]);b.fillStyle=c;b.fillRect(0,0,1,256);this.j=b.getImageData(0,0,1,256).data};k.Yf=function(){var a=this.ri(),b=this.nh(),c=a+b+1,d=2*c,d=hd(d,d);d.shadowOffsetX=d.shadowOffsetY=this.T;d.shadowBlur=b;d.shadowColor="#000";d.beginPath();b=c-this.T;d.arc(b,b,a,0,2*Math.PI,!0);d.fill();this.Z=d.canvas.toDataURL();this.I=Array(256);this.s()}; -k.Nl=function(a){a=a.context;var b=a.canvas,b=a.getImageData(0,0,b.width,b.height),c=b.data,d,e,f;d=0;for(e=c.length;d<e;d+=4)if(f=4*c[d+3])c[d]=this.j[f],c[d+1]=this.j[f+1],c[d+2]=this.j[f+2];a.putImageData(b,0,0)};k.ej=function(a){this.set(ov,a)};k.kj=function(a){this.set(mv,a)};k.Zc=function(a){this.set(pv,a)};var ov="blur",mv="gradient",pv="radius";function qv(a){zt.call(this,a);this.u=yh();this.j=null}u(qv,zt);qv.prototype.O=function(a,b,c){Bt(this,"precompose",c,a,void 0);var d=this.Y();if(d){var e=b.extent,f=void 0!==e&&!Ua(e,a.extent)&&nb(e,a.extent);f&&At(c,a,e);var e=this.A(),g=c.globalAlpha;c.globalAlpha=b.opacity;c.drawImage(d,0,0,+d.width,+d.height,Math.round(e[4]),Math.round(e[5]),Math.round(d.width*e[0]),Math.round(d.height*e[3]));c.globalAlpha=g;f&&c.restore()}this.cf(c,a,b)}; -qv.prototype.Ba=function(a,b,c,d,e){var f=this.a;return f.ka().Ba(a,b.viewState.resolution,b.viewState.rotation,c,b.skippedFeatureUids,function(a){return d.call(e,a,f)})}; -qv.prototype.v=function(a,b,c,d){if(this.Y()){if(this.a.ka().Ba!==oa)return zt.prototype.v.apply(this,arguments);var e=Dh(this.u,a.slice());df(e,b.viewState.resolution/this.f);this.j||(this.j=hd(1,1));this.j.clearRect(0,0,1,1);this.j.drawImage(this.Y(),e[0],e[1],1,1,0,0,1,1);e=this.j.getImageData(0,0,1,1).data;if(0<e[3])return c.call(d,this.a,e)}};function rv(a){qv.call(this,a);this.N=null;this.c=yh()}u(rv,qv);rv.prototype.Y=function(){return this.N?this.N.Y():null};rv.prototype.A=function(){return this.c}; -rv.prototype.ud=function(a,b){var c=a.pixelRatio,d=a.size,e=a.viewState,f=e.center,g=e.resolution,h=this.a.ka(),l=a.viewHints,m=a.extent;void 0!==b.extent&&(m=mb(m,b.extent));l[0]||l[1]||hb(m)||(e=h.Y(m,g,c,e.projection))&&tt(this,e)&&(this.N=e);if(this.N){var e=this.N,m=e.D(),n=e.resolution,l=e.a,p=c*n/(g*l),m=Hh(this.c,c*d[0]/2,c*d[1]/2,p,p,0,l*(m[0]-f[0])/n,l*(f[1]-m[3])/n);Hh(this.u,c*d[0]/2-m[4],c*d[1]/2-m[5],c/g,-c/g,0,-f[0],-f[1]);vt(a.attributions,e.i);wt(a,h);this.f=g*c/l}return!!this.N};function sv(a,b,c,d){var e=fc(c,b,a);c=Rb(b,d,c);b=b.uc();void 0!==b&&(c*=b);b=a.uc();void 0!==b&&(c/=b);a=Rb(a,c,e)/c;isFinite(a)&&0<a&&(c/=a);return c}function tv(a,b,c,d){a=c-a;b=d-b;var e=Math.sqrt(a*a+b*b);return[Math.round(c+a/e),Math.round(d+b/e)]} -function uv(a,b,c,d,e,f,g,h,l,m,n){var p=hd(Math.round(c*a),Math.round(c*b));if(!l.length)return p.canvas;p.scale(c,c);var q=Ja();l.forEach(function(a){ab(q,a.extent)});var r=hd(Math.round(c*ib(q)/d),Math.round(c*jb(q)/d)),v=c/d;l.forEach(function(a){r.drawImage(a.image,m,m,a.image.width-2*m,a.image.height-2*m,(a.extent[0]-q[0])*v,-(a.extent[3]-q[3])*v,ib(a.extent)*v,jb(a.extent)*v)});var x=fb(g);h.c.forEach(function(a){var b=a.source,e=a.target,g=b[1][0],h=b[1][1],l=b[2][0],m=b[2][1];a=(e[0][0]- -x[0])/f;var n=-(e[0][1]-x[1])/f,v=(e[1][0]-x[0])/f,y=-(e[1][1]-x[1])/f,Z=(e[2][0]-x[0])/f,Ta=-(e[2][1]-x[1])/f,e=b[0][0],b=b[0][1],g=g-e,h=h-b,l=l-e,m=m-b;a:{g=[[g,h,0,0,v-a],[l,m,0,0,Z-a],[0,0,g,h,y-n],[0,0,l,m,Ta-n]];h=g.length;for(l=0;l<h;l++){for(var m=l,Pb=Math.abs(g[l][l]),cc=l+1;cc<h;cc++){var $c=Math.abs(g[cc][l]);$c>Pb&&(Pb=$c,m=cc)}if(!Pb){g=null;break a}Pb=g[m];g[m]=g[l];g[l]=Pb;for(m=l+1;m<h;m++)for(Pb=-g[m][l]/g[l][l],cc=l;cc<h+1;cc++)g[m][cc]=l==cc?0:g[m][cc]+Pb*g[l][cc]}l=Array(h); -for(m=h-1;0<=m;m--)for(l[m]=g[m][h]/g[m][m],Pb=m-1;0<=Pb;Pb--)g[Pb][h]-=g[Pb][m]*l[m];g=l}g&&(p.save(),p.beginPath(),l=(a+v+Z)/3,m=(n+y+Ta)/3,h=tv(l,m,a,n),v=tv(l,m,v,y),Z=tv(l,m,Z,Ta),p.moveTo(v[0],v[1]),p.lineTo(h[0],h[1]),p.lineTo(Z[0],Z[1]),p.clip(),p.transform(g[0],g[2],g[1],g[3],a,n),p.translate(q[0]-e,q[3]-b),p.scale(d/c,-d/c),p.drawImage(r.canvas,0,0),p.restore())});n&&(p.save(),p.strokeStyle="black",p.lineWidth=1,h.c.forEach(function(a){var b=a.target;a=(b[0][0]-x[0])/f;var c=-(b[0][1]-x[1])/ -f,d=(b[1][0]-x[0])/f,e=-(b[1][1]-x[1])/f,g=(b[2][0]-x[0])/f,b=-(b[2][1]-x[1])/f;p.beginPath();p.moveTo(d,e);p.lineTo(a,c);p.lineTo(g,b);p.closePath();p.stroke()}),p.restore());return p.canvas};function vv(a,b,c,d,e){this.g=a;this.i=b;var f={},g=dc(this.i,this.g);this.a=function(a){var b=a[0]+"/"+a[1];f[b]||(f[b]=g(a));return f[b]};this.f=d;this.u=e*e;this.c=[];this.l=!1;this.o=this.g.a&&!!d&&!!this.g.D()&&ib(d)==ib(this.g.D());this.b=this.g.D()?ib(this.g.D()):null;this.j=this.i.D()?ib(this.i.D()):null;a=fb(c);b=eb(c);d=db(c);c=cb(c);e=this.a(a);var h=this.a(b),l=this.a(d),m=this.a(c);wv(this,a,b,d,c,e,h,l,m,10);if(this.l){var n=Infinity;this.c.forEach(function(a){n=Math.min(n,a.source[0][0], -a.source[1][0],a.source[2][0])});this.c.forEach(function(a){if(Math.max(a.source[0][0],a.source[1][0],a.source[2][0])-n>this.b/2){var b=[[a.source[0][0],a.source[0][1]],[a.source[1][0],a.source[1][1]],[a.source[2][0],a.source[2][1]]];b[0][0]-n>this.b/2&&(b[0][0]-=this.b);b[1][0]-n>this.b/2&&(b[1][0]-=this.b);b[2][0]-n>this.b/2&&(b[2][0]-=this.b);Math.max(b[0][0],b[1][0],b[2][0])-Math.min(b[0][0],b[1][0],b[2][0])<this.b/2&&(a.source=b)}},this)}f={}} -function wv(a,b,c,d,e,f,g,h,l,m){var n=Ia([f,g,h,l]),p=a.b?ib(n)/a.b:null,q=a.b,r=a.g.a&&.5<p&&1>p,v=!1;if(0<m){if(a.i.g&&a.j)var x=Ia([b,c,d,e]),v=v|.25<ib(x)/a.j;!r&&a.g.g&&p&&(v|=.25<p)}if(v||!a.f||nb(n,a.f)){if(!(v||isFinite(f[0])&&isFinite(f[1])&&isFinite(g[0])&&isFinite(g[1])&&isFinite(h[0])&&isFinite(h[1])&&isFinite(l[0])&&isFinite(l[1])))if(0<m)v=!0;else return;if(0<m&&(v||(n=a.a([(b[0]+d[0])/2,(b[1]+d[1])/2]),q=r?(Da(f[0],q)+Da(h[0],q))/2-Da(n[0],q):(f[0]+h[0])/2-n[0],n=(f[1]+h[1])/2-n[1], -v=q*q+n*n>a.u),v)){Math.abs(b[0]-d[0])<=Math.abs(b[1]-d[1])?(r=[(c[0]+d[0])/2,(c[1]+d[1])/2],q=a.a(r),n=[(e[0]+b[0])/2,(e[1]+b[1])/2],p=a.a(n),wv(a,b,c,r,n,f,g,q,p,m-1),wv(a,n,r,d,e,p,q,h,l,m-1)):(r=[(b[0]+c[0])/2,(b[1]+c[1])/2],q=a.a(r),n=[(d[0]+e[0])/2,(d[1]+e[1])/2],p=a.a(n),wv(a,b,r,n,e,f,q,p,l,m-1),wv(a,r,c,d,n,q,g,h,p,m-1));return}if(r){if(!a.o)return;a.l=!0}a.c.push({source:[f,h,l],target:[b,d,e]});a.c.push({source:[f,g,h],target:[b,c,d]})}} -function xv(a){var b=Ja();a.c.forEach(function(a){a=a.source;La(b,a[0]);La(b,a[1]);La(b,a[2])});return b};function yv(a,b,c,d,e,f){this.u=b;this.o=a.D();var g=b.D(),h=g?mb(c,g):c,g=sv(a,b,kb(h),d);this.j=new vv(a,b,h,this.o,.5*g);this.c=d;this.g=c;a=xv(this.j);this.l=(this.Eb=f(a,g,e))?this.Eb.a:1;this.de=this.f=null;e=2;f=[];this.Eb&&(e=0,f=this.Eb.i);Fs.call(this,c,d,this.l,e,f)}u(yv,Fs);yv.prototype.ra=function(){1==this.state&&(Bc(this.de),this.de=null);Fs.prototype.ra.call(this)};yv.prototype.Y=function(){return this.f}; -yv.prototype.ce=function(){var a=this.Eb.V();2==a&&(this.f=uv(ib(this.g)/this.c,jb(this.g)/this.c,this.l,this.Eb.resolution,0,this.c,this.g,this.j,[{extent:this.Eb.D(),image:this.Eb.Y()}],0));this.state=a;this.s()};yv.prototype.load=function(){if(0==this.state){this.state=1;this.s();var a=this.Eb.V();2==a||3==a?this.ce():(this.de=z(this.Eb,"change",function(){var a=this.Eb.V();if(2==a||3==a)Bc(this.de),this.de=null,this.ce()},this),this.Eb.load())}};function zv(a){Tt.call(this,{attributions:a.attributions,extent:a.extent,logo:a.logo,projection:a.projection,state:a.state});this.v=void 0!==a.resolutions?a.resolutions:null;this.a=null;this.ea=0}u(zv,Tt);function Av(a,b){a.v&&(b=a.v[ga(a.v,b,0)]);return b} -zv.prototype.Y=function(a,b,c,d){var e=this.c;if(e&&d&&!bc(e,d)){if(this.a){if(this.ea==this.g&&bc(this.a.u,d)&&this.a.resolution==b&&this.a.a==c&&$a(this.a.D(),a))return this.a;Kc(this.a);this.a=null}this.a=new yv(e,d,a,b,c,function(a,b,c){return this.Lc(a,b,c,e)}.bind(this));this.ea=this.g;return this.a}e&&(d=e);return this.Lc(a,b,c,d)};zv.prototype.l=function(a){a=a.target;switch(a.V()){case 1:this.b(new Bv(Cv,a));break;case 2:this.b(new Bv(Dv,a));break;case 3:this.b(new Bv(Ev,a))}}; -function Fv(a,b){a.Y().src=b}function Bv(a,b){Lc.call(this,a);this.image=b}u(Bv,Lc);var Cv="imageloadstart",Dv="imageloadend",Ev="imageloaderror";function Gv(a){zv.call(this,{attributions:a.attributions,logo:a.logo,projection:a.projection,resolutions:a.resolutions,state:a.state});this.fa=a.canvasFunction;this.I=null;this.T=0;this.na=void 0!==a.ratio?a.ratio:1.5}u(Gv,zv);Gv.prototype.Lc=function(a,b,c,d){b=Av(this,b);var e=this.I;if(e&&this.T==this.g&&e.resolution==b&&e.a==c&&Ua(e.D(),a))return e;a=a.slice();ob(a,this.na);(d=this.fa(a,b,c,[ib(a)/b*c,jb(a)/b*c],d))&&(e=new Hs(a,b,c,this.j,d));this.I=e;this.T=this.g;return e};function Hv(a){this.i=a.source;this.Va=yh();this.f=hd();this.o=[0,0];this.Ha=void 0==a.renderBuffer?100:a.renderBuffer;this.A=null;Gv.call(this,{attributions:a.attributions,canvasFunction:this.pk.bind(this),logo:a.logo,projection:a.projection,ratio:a.ratio,resolutions:a.resolutions,state:this.i.V()});this.C=null;this.u=void 0;this.Bi(a.style);z(this.i,"change",this.ho,this)}u(Hv,Gv);k=Hv.prototype; -k.pk=function(a,b,c,d,e){var f=new it(.5*b/c,a,b,this.i.Ha,this.Ha);this.i.Xd(a,b,e);var g=!1;this.i.bc(a,function(a){var d;if(!(d=g)){var e;(d=a.Rc())?e=d.call(a,b):this.u&&(e=this.u(a,b));if(e){var h,p=!1;Array.isArray(e)||(e=[e]);d=0;for(h=e.length;d<h;++d)p=Ft(f,a,e[d],Et(b,c),this.fo,this)||p;d=p}else d=!1}g=d},this);mt(f);if(g)return null;this.o[0]!=d[0]||this.o[1]!=d[1]?(this.f.canvas.width=d[0],this.f.canvas.height=d[1],this.o[0]=d[0],this.o[1]=d[1]):this.f.clearRect(0,0,d[0],d[1]);a=Iv(this, -kb(a),b,c,d);f.i(this.f,c,a,0,{});this.A=f;return this.f.canvas};k.Ba=function(a,b,c,d,e,f){if(this.A){var g={};return this.A.Ba(a,b,0,d,e,function(a){var b=w(a).toString();if(!(b in g))return g[b]=!0,f(a)})}};k.bo=function(){return this.i};k.co=function(){return this.C};k.eo=function(){return this.u};function Iv(a,b,c,d,e){c=d/c;return Hh(a.Va,e[0]/2,e[1]/2,c,-c,0,-b[0],-b[1])}k.fo=function(){this.s()};k.ho=function(){Vt(this,this.i.V())}; -k.Bi=function(a){this.C=void 0!==a?a:fl;this.u=a?dl(this.C):void 0;this.s()};function Jv(a,b){Ot.call(this,a,b);this.l=this.i=this.N=null}u(Jv,Ot);function Kv(a,b){var c=b.Y();return Qi(a.c.g,c)}Jv.prototype.Ba=function(a,b,c,d,e){var f=this.a;return f.ka().Ba(a,b.viewState.resolution,b.viewState.rotation,c,b.skippedFeatureUids,function(a){return d.call(e,a,f)})}; -Jv.prototype.ig=function(a,b){var c=this.c.g,d=a.pixelRatio,e=a.viewState,f=e.center,g=e.resolution,h=e.rotation,l=this.N,m=this.Fb,n=this.a.ka(),p=a.viewHints,q=a.extent;void 0!==b.extent&&(q=mb(q,b.extent));p[0]||p[1]||hb(q)||(e=n.Y(q,g,d,e.projection))&&tt(this,e)&&(l=e,m=Kv(this,e),this.Fb&&a.postRenderFunctions.push(function(a,b){a.isContextLost()||a.deleteTexture(b)}.bind(null,c,this.Fb)));l&&(c=this.c.i.j,Lv(this,c.width,c.height,d,f,g,h,l.D()),this.l=null,d=this.u,zh(d),Fh(d,1,-1),Gh(d,0, --1),this.N=l,this.Fb=m,vt(a.attributions,l.i),wt(a,n));return!!l};function Lv(a,b,c,d,e,f,g,h){b*=f;c*=f;a=a.O;zh(a);Fh(a,2*d/b,2*d/c);Eh(a,-g);Gh(a,h[0]-e[0],h[1]-e[1]);Fh(a,(h[2]-h[0])/2,(h[3]-h[1])/2);Gh(a,1,1)}Jv.prototype.Te=function(a,b){return void 0!==this.Ba(a,b,0,jf,this)}; -Jv.prototype.gg=function(a,b,c,d){if(this.N&&this.N.Y())if(this.a.ka()instanceof Hv){var e=Dh(b.pixelToCoordinateTransform,a.slice());if(this.Ba(e,b,0,jf,this))return c.call(d,this.a,null)}else{e=[this.N.Y().width,this.N.Y().height];if(!this.l){var f=b.size;b=yh();Gh(b,-1,-1);Fh(b,2/f[0],2/f[1]);Gh(b,0,f[1]);Fh(b,1,-1);var f=Ih(this.O.slice()),g=yh();Gh(g,0,e[1]);Fh(g,1,-1);Fh(g,e[0]/2,e[1]/2);Gh(g,1,1);Bh(g,f);Bh(g,b);this.l=g}a=Dh(this.l,a.slice());if(!(0>a[0]||a[0]>e[0]||0>a[1]||a[1]>e[1])&&(this.i|| -(this.i=hd(1,1)),this.i.clearRect(0,0,1,1),this.i.drawImage(this.N.Y(),a[0],a[1],1,1,0,0,1,1),e=this.i.getImageData(0,0,1,1).data,0<e[3]))return c.call(d,this.a,e)}};function Mv(a){th.call(this,a?a:{})}u(Mv,th);Mv.prototype.Gd=function(a){var b=null,c=a.S();"canvas"===c?b=new rv(this):"webgl"===c&&(b=new Jv(a,this));return b};function Nv(a){qv.call(this,a);this.c=null===this.c?null:hd();this.l=null;this.i=[];this.o=Ja();this.Ja=new ta(0,0,0,0);this.C=yh();this.T=0}u(Nv,qv);function Ov(a,b){var c=b.V(),d=a.a.Wd();return 2==c||4==c||3==c&&!d} -Nv.prototype.ud=function(a,b){var c=a.pixelRatio,d=a.size,e=a.viewState,f=e.projection,g=e.resolution,e=e.center,h=this.a,l=h.ka(),m=l.g,n=l.Jb(f),p=n.Qc(g,this.T),q=n.La(p),r=Math.round(g/q)||1,v=a.extent;void 0!==b.extent&&(v=mb(v,b.extent));if(hb(v))return!1;var x=qc(n,v,q),y;y=n.Uc(p);var A=n.La(p),B=Ha(n.eb(p),n.j);y=Wa(y[0]+x.da*B[0]*A,y[1]+x.ga*B[1]*A,y[0]+(x.ba+1)*B[0]*A,y[1]+(x.ja+1)*B[1]*A,void 0);A=l.pb(c);B={};B[p]={};var aa=this.Jf(l,f,B),Ra=this.o,ra=this.Ja,Ka=!1,C,Na,wb;for(Na=x.da;Na<= -x.ba;++Na)for(wb=x.ga;wb<=x.ja;++wb)C=l.Pc(p,Na,wb,c,f),Ov(this,C)||(C=Js(C)),Ov(this,C)?2==C.V()&&(B[p][C.Ga.toString()]=C,Ka||-1!=this.i.indexOf(C)||(Ka=!0)):oc(n,C.Ga,aa,ra,Ra)||(C=pc(n,C.Ga,ra,Ra))&&aa(p+1,C);Na=a.viewHints;if(!(this.f&&16<Date.now()-a.time&&(Na[0]||Na[1])||!Ka&&this.l&&Ua(this.l,v)&&this.kf==m)||r!=this.I){if(Na=this.c)wb=l.Vd(p,c,f),C=Math.round((x.ba-x.da+1)*wb[0]/r),wb=Math.round((x.ja-x.ga+1)*wb[1]/r),Ka=Na.canvas,Ka.width!=C||Ka.height!=wb?(this.I=r,Ka.width=C,Ka.height= -wb):(Na.clearRect(0,0,C,wb),r=this.I);this.i.length=0;Ka=Object.keys(B).map(Number);Ka.sort(ea);var Z,Ta,Pb,cc,$c,re,ra=0;for(Ta=Ka.length;ra<Ta;++ra){Na=Ka[ra];aa=l.Vd(Na,c,f);C=n.La(Na);Z=C/q;Pb=A*l.Rf(f);cc=B[Na];for(var Jd in cc)C=cc[Jd],wb=n.Ua(C.Ga,Ra),Na=(wb[0]-y[0])/q*A/r,wb=(y[3]-wb[3])/q*A/r,$c=aa[0]*Z/r,re=aa[1]*Z/r,this.Kf(C,a,b,Na,wb,$c,re,Pb),this.i.push(C)}this.kf=m;this.f=q*c/A*r;this.l=y}Jd=this.f/g;Jd=Hh(this.C,c*d[0]/2,c*d[1]/2,Jd,Jd,0,(this.l[0]-e[0])/this.f*c,(e[1]-this.l[3])/ -this.f*c);Hh(this.u,c*d[0]/2-Jd[4],c*d[1]/2-Jd[5],c/g,-c/g,0,-e[0],-e[1]);xt(a.usedTiles,l,p,x);yt(a,l,n,c,f,v,p,h.Sd());ut(a,l);wt(a,l);return 0<this.i.length};Nv.prototype.Kf=function(a,b,c,d,e,f,g,h){this.a.ka().Uf(b.viewState.projection)||this.c.clearRect(d,e,f,g);(a=a.Y())&&this.c.drawImage(a,h,h,a.width-2*h,a.height-2*h,d,e,f,g)};Nv.prototype.Y=function(){var a=this.c;return a?a.canvas:null};Nv.prototype.A=function(){return this.C};function Pv(){this.b="precision mediump float;varying vec2 a;uniform sampler2D e;void main(void){gl_FragColor=texture2D(e,a);}"}u(Pv,ji);var Qv=new Pv;function Rv(){this.b="varying vec2 a;attribute vec2 b;attribute vec2 c;uniform vec4 d;void main(void){gl_Position=vec4(b*d.xy+d.zw,0.,1.);a=c;}"}u(Rv,ki);var Sv=new Rv;function Tv(a,b){this.g=a.getUniformLocation(b,"e");this.c=a.getUniformLocation(b,"d");this.b=a.getAttribLocation(b,"b");this.a=a.getAttribLocation(b,"c")};function Uv(a,b){Ot.call(this,a,b);this.I=Qv;this.fa=Sv;this.i=null;this.G=new Ai([0,0,0,1,1,0,1,1,0,1,0,0,1,1,1,0]);this.A=this.l=null;this.o=-1;this.Z=[0,0]}u(Uv,Ot);k=Uv.prototype;k.ra=function(){Di(this.c.i,this.G);Ot.prototype.ra.call(this)};k.Jf=function(a,b,c){var d=this.c;return function(e,f){return rt(a,b,e,f,function(a){var b=d.a.b.hasOwnProperty(a.hb());b&&(c[e]||(c[e]={}),c[e][a.Ga.toString()]=a);return b})}};k.hg=function(){Ot.prototype.hg.call(this);this.i=null}; -k.ig=function(a,b,c){var d=this.c,e=c.b,f=a.viewState,g=f.projection,h=this.a,l=h.ka(),m=l.Jb(g),n=m.Qc(f.resolution),p=m.La(n),q=l.Vd(n,a.pixelRatio,g),r=q[0]/Ha(m.eb(n),this.Z)[0],v=p/r,x=l.pb(r)*l.Rf(g),y=f.center,A=a.extent,B=qc(m,A,p);if(this.l&&va(this.l,B)&&this.o==l.g)v=this.A;else{var aa=[B.ba-B.da+1,B.ja-B.ga+1],Ra=za(Math.max(aa[0]*q[0],aa[1]*q[1])),aa=v*Ra,ra=m.Uc(n),Ka=ra[0]+B.da*q[0]*v,v=ra[1]+B.ga*q[1]*v,v=[Ka,v,Ka+aa,v+aa];Pt(this,a,Ra);e.viewport(0,0,Ra,Ra);e.clearColor(0,0,0,0); -e.clear(16384);e.disable(3042);Ra=Ei(c,this.I,this.fa);c.Vc(Ra);this.i||(this.i=new Tv(e,Ra));ti(c,34962,this.G);e.enableVertexAttribArray(this.i.b);e.vertexAttribPointer(this.i.b,2,5126,!1,16,0);e.enableVertexAttribArray(this.i.a);e.vertexAttribPointer(this.i.a,2,5126,!1,16,8);e.uniform1i(this.i.g,0);c={};c[n]={};var C=this.Jf(l,g,c),Na=h.Wd(),Ra=!0,Ka=Ja(),wb=new ta(0,0,0,0),Z,Ta,Pb;for(Ta=B.da;Ta<=B.ba;++Ta)for(Pb=B.ga;Pb<=B.ja;++Pb){ra=l.Pc(n,Ta,Pb,r,g);if(void 0!==b.extent&&(Z=m.Ua(ra.Ga,Ka), -!nb(Z,b.extent)))continue;Z=ra.V();(Z=2==Z||4==Z||3==Z&&!Na)||(ra=Js(ra));Z=ra.V();if(2==Z){if(d.a.b.hasOwnProperty(ra.hb())){c[n][ra.Ga.toString()]=ra;continue}}else if(4==Z||3==Z&&!Na)continue;Ra=!1;Z=oc(m,ra.Ga,C,wb,Ka);Z||(ra=pc(m,ra.Ga,wb,Ka))&&C(n+1,ra)}b=Object.keys(c).map(Number);b.sort(ea);for(var C=new Float32Array(4),cc,Na=0,wb=b.length;Na<wb;++Na)for(cc in Ta=c[b[Na]],Ta)ra=Ta[cc],Z=m.Ua(ra.Ga,Ka),C[0]=2*(Z[2]-Z[0])/aa,C[1]=2*(Z[3]-Z[1])/aa,C[2]=2*(Z[0]-v[0])/aa-1,C[3]=2*(Z[1]-v[1])/aa- -1,e.uniform4fv(this.i.c,C),nk(d,ra,q,x*r),e.drawArrays(5,0,4);Ra?(this.l=B,this.A=v,this.o=l.g):(this.A=this.l=null,this.o=-1,a.animate=!0)}xt(a.usedTiles,l,n,B);var $c=d.j;yt(a,l,m,r,g,A,n,h.Sd(),function(a){2!=a.V()||d.a.b.hasOwnProperty(a.hb())||a.hb()in $c.a||$c.i([a,sc(m,a.Ga),m.La(a.Ga[0]),q,x*r])},this);ut(a,l);wt(a,l);e=this.u;zh(e);Gh(e,(Math.round(y[0]/p)*p-v[0])/(v[2]-v[0]),(Math.round(y[1]/p)*p-v[1])/(v[3]-v[1]));f.rotation&&Eh(e,f.rotation);Fh(e,a.size[0]*f.resolution/(v[2]-v[0]),a.size[1]* -f.resolution/(v[3]-v[1]));Gh(e,-.5,-.5);return!0};k.gg=function(a,b,c,d){if(this.f){a=Dh(this.u,[a[0]/b.size[0],(b.size[1]-a[1])/b.size[1]].slice());a=[a[0]*this.j,a[1]*this.j];b=this.c.i.b;b.bindFramebuffer(b.FRAMEBUFFER,this.f);var e=new Uint8Array(4);b.readPixels(a[0],a[1],1,1,b.RGBA,b.UNSIGNED_BYTE,e);if(0<e[3])return c.call(d,this.a,e)}};function Vv(a){a=a?a:{};var b=qb({},a);delete b.preload;delete b.useInterimTilesOnError;th.call(this,b);this.si(void 0!==a.preload?a.preload:0);this.ti(void 0!==a.useInterimTilesOnError?a.useInterimTilesOnError:!0)}u(Vv,th);k=Vv.prototype;k.Gd=function(a){var b=null,c=a.S();"canvas"===c?b=new Nv(this):"webgl"===c&&(b=new Uv(a,this));return b};k.Sd=function(){return this.get("preload")};k.si=function(a){this.set("preload",a)};k.Wd=function(){return this.get("useInterimTilesOnError")}; -k.ti=function(a){this.set("useInterimTilesOnError",a)};function Wv(a){this.c=null;Nv.call(this,a);this.G=!1;this.Z=yh();this.T="vector"==a.u?1:0}u(Wv,Nv);var Xv={image:gi,hybrid:["Polygon","LineString"]},Yv={hybrid:["Image","Text"],vector:gi};k=Wv.prototype;k.ud=function(a,b){var c=this.a,d=c.g;this.na!=d&&(this.i.length=0,c=c.u,this.c||"vector"==c||(this.c=hd()),this.c&&"vector"==c&&(this.c=null));this.na=d;return Nv.prototype.ud.apply(this,arguments)}; -function Zv(a,b,c){function d(a){var b,c=a.Rc();c?b=c.call(a,r):(c=e.i)&&(b=c(a,r));if(b){Array.isArray(b)||(b=[b]);var c=B,d=A;if(b){var f=!1;if(Array.isArray(b))for(var g=0,h=b.length;g<h;++g)f=Ft(d,a,b[g],c,this.yi,this)||f;else f=Ft(d,a,b,c,this.yi,this)||f;a=f}else a=!1;this.G=this.G||a;l.Od=l.Od||a}}var e=a.a,f=c.pixelRatio;c=c.viewState.projection;var g=e.g,h=e.get(It)||null,l=b.g;if(l.Od||l.kf!=g||l.Eg!=h){l.zd=null;l.Od=!1;var m=e.ka(),n=m.tileGrid,p=b.Ga,q=b.j,r=n.La(p[0]),v,x,y;"tile-pixels"== -q.Kb()?(v=y=m.pb(),n=Ha(n.eb(p[0])),v=[0,0,n[0]*v,n[1]*v]):(y=r,v=n.Ua(p),bc(c,q)||(x=!0,b.dg(c)));l.Od=!1;var A=new it(0,v,y,m.f,e.c),B=Et(y,f);b=b.f;h&&h!==l.Eg&&b.sort(h);m=0;for(y=b.length;m<y;++m)f=b[m],x&&f.U().tb(q,c),d.call(a,f);mt(A);l.kf=g;l.Eg=h;l.zd=A;l.resolution=NaN}} -k.Kf=function(a,b,c,d,e,f,g,h){var l=a;Zv(this,l,b);if(this.c){var m=l,n=b,p=this.a,l=m.g,q=p.g,r=Xv[p.u];if(r&&l.Fg!==q){l.Fg=q;var v=m.Ga,x=m.Ga[0],q=n.pixelRatio,y=p.ka(),A=y.tileGrid,B=y.pb(),p=zh(this.Z);"tile-pixels"==m.j.Kb()?(v=q/B,Fh(p,v,v)):(B=q/A.La(x),v=A.Ua(v,this.o),Fh(p,B,-B),Gh(p,-v[0],-v[3]));m.c||(m.c=hd());m=m.c;n=y.Vd(x,q,n.viewState.projection);m.canvas.width=n[0];m.canvas.height=n[1];l.zd.i(m,q,p,0,{},r)}Nv.prototype.Kf.apply(this,arguments)}}; -k.Ba=function(a,b,c,d,e){var f=b.viewState.resolution;b=b.viewState.rotation;c=void 0==c?0:c;var g=this.a,h={},l=this.i,m=g.ka(),n=m.tileGrid,p,q,r,v,x,y;r=0;for(v=l.length;r<v;++r)y=l[r],q=y.Ga,x=m.tileGrid.Ua(q,this.o),Qa(Ma(x,c*f),a)&&("tile-pixels"===y.j.Kb()?(x=fb(x),f=m.pb(),q=n.La(q[0])/f,q=[(a[0]-x[0])/q,(x[1]-a[1])/q]):q=a,y=y.g.zd,p=p||y.Ba(q,f,b,c,{},function(a){var b=w(a).toString();if(!(b in h))return h[b]=!0,d.call(e,a,g)}));return p};k.yi=function(){st(this)}; -k.cf=function(a,b,c){var d=Yv[this.a.u];if(d)for(var e=b.pixelRatio,f=b.viewState.rotation,g=b.size,h=Math.round(e*g[0]/2),g=Math.round(e*g[1]/2),l=this.i,m=[],n=[],p=l.length-1;0<=p;--p){var q=l[p],r;var v=q;r=b;if("tile-pixels"==v.j.Kb()){var x=this.a.ka(),y=x.tileGrid,A=v.Ga,x=y.La(A[0])/x.pb(),v=r.viewState,B=r.pixelRatio,aa=v.resolution/B,A=y.Ua(A,this.o),y=v.center,A=fb(A);r=r.size;r=Hh(this.Z,Math.round(B*r[0]/2),Math.round(B*r[1]/2),x/aa,x/aa,v.rotation,(A[0]-y[0])/x,(y[1]-A[1])/x)}else r= -Ct(this,r,0);x=ot(q.g.zd,r);v=q.Ga[0];a.save();a.globalAlpha=c.opacity;Sh(a,-f,h,g);B=0;for(aa=m.length;B<aa;++B)y=m[B],v<n[B]&&(a.beginPath(),a.moveTo(x[0],x[1]),a.lineTo(x[2],x[3]),a.lineTo(x[4],x[5]),a.lineTo(x[6],x[7]),a.moveTo(y[6],y[7]),a.lineTo(y[4],y[5]),a.lineTo(y[2],y[3]),a.lineTo(y[0],y[1]),a.clip());q.g.zd.i(a,e,r,f,{},d);a.restore();m.push(x);n.push(v)}Nv.prototype.cf.apply(this,arguments)};function V(a){a=a?a:{};var b=qb({},a);delete b.preload;delete b.useInterimTilesOnError;S.call(this,b);this.ui(a.preload?a.preload:0);this.vi(a.useInterimTilesOnError?a.useInterimTilesOnError:!0);sa(void 0==a.renderMode||"image"==a.renderMode||"hybrid"==a.renderMode||"vector"==a.renderMode,28);this.u=a.renderMode||"hybrid"}u(V,S);k=V.prototype;k.Gd=function(a){var b=null;"canvas"===a.S()&&(b=new Wv(this));return b};k.Sd=function(){return this.get("preload")};k.Wd=function(){return this.get("useInterimTilesOnError")}; -k.ui=function(a){this.set("preload",a)};k.vi=function(a){this.set("useInterimTilesOnError",a)};function $v(a,b,c,d){function e(){delete window[g];f.parentNode.removeChild(f)}var f=document.createElement("script"),g="olc_"+w(b);f.async=!0;f.src=a+(-1==a.indexOf("?")?"?":"&")+(d||"callback")+"="+g;var h=setTimeout(function(){e();c&&c()},1E4);window[g]=function(a){clearTimeout(h);e();b(a)};document.getElementsByTagName("head")[0].appendChild(f)};function aw(a,b,c,d,e,f,g,h,l,m,n){Is.call(this,e,0);this.C=void 0!==n?n:!1;this.A=g;this.O=h;this.v=null;this.c=b;this.l=d;this.o=f?f:e;this.g=[];this.Ad=null;this.f=0;f=d.Ua(this.o);h=this.l.D();e=this.c.D();f=h?mb(f,h):f;if(gb(f))if((h=a.D())&&(e?e=mb(e,h):e=h),d=sv(a,c,kb(f),d.La(this.o[0])),!isFinite(d)||0>=d)this.state=4;else if(this.u=new vv(a,c,f,e,d*(void 0!==m?m:.5)),this.u.c.length)if(this.f=b.Qc(d),c=xv(this.u),e&&(a.a?(c[1]=xa(c[1],e[1],e[3]),c[3]=xa(c[3],e[1],e[3])):c=mb(c,e)),gb(c)){a= -nc(b,c,this.f);for(b=a.da;b<=a.ba;b++)for(c=a.ga;c<=a.ja;c++)(m=l(this.f,b,c,g))&&this.g.push(m);this.g.length||(this.state=4)}else this.state=4;else this.state=4;else this.state=4}u(aw,Is);aw.prototype.ra=function(){1==this.state&&(this.Ad.forEach(Bc),this.Ad=null);Is.prototype.ra.call(this)};aw.prototype.Y=function(){return this.v}; -aw.prototype.ce=function(){var a=[];this.g.forEach(function(b){b&&2==b.V()&&a.push({extent:this.c.Ua(b.Ga),image:b.Y()})},this);this.g.length=0;if(a.length){var b=this.o[0],c=this.l.eb(b),d="number"===typeof c?c:c[0],c="number"===typeof c?c:c[1],b=this.l.La(b),e=this.c.La(this.f),f=this.l.Ua(this.o);this.v=uv(d,c,this.A,e,this.c.D(),b,f,this.u,a,this.O,this.C);this.state=2}else this.state=3;this.s()}; -aw.prototype.load=function(){if(0==this.state){this.state=1;this.s();var a=0;this.Ad=[];this.g.forEach(function(b){var c=b.V();if(0==c||1==c){a++;var d;d=z(b,"change",function(){var c=b.V();if(2==c||3==c||4==c)Bc(d),a--,a||(this.Ad.forEach(Bc),this.Ad=null,this.ce())},this);this.Ad.push(d)}},this);this.g.forEach(function(a){0==a.V()&&a.load()});a||setTimeout(this.ce.bind(this),0)}};function bw(a,b){var c=/\{z\}/g,d=/\{x\}/g,e=/\{y\}/g,f=/\{-y\}/g;return function(g){if(g)return a.replace(c,g[0].toString()).replace(d,g[1].toString()).replace(e,function(){return(-g[2]-1).toString()}).replace(f,function(){var a=b.a?b.a[g[0]]:null;sa(a,55);return(a.ja-a.ga+1+g[2]).toString()})}}function cw(a,b){for(var c=a.length,d=Array(c),e=0;e<c;++e)d[e]=bw(a[e],b);return dw(d)}function dw(a){return 1===a.length?a[0]:function(b,c,d){if(b)return a[Da((b[1]<<b[0])+b[2],a.length)](b,c,d)}} -function ew(){}function fw(a){var b=[],c=/\{([a-z])-([a-z])\}/.exec(a);if(c){var d=c[2].charCodeAt(0),e;for(e=c[1].charCodeAt(0);e<=d;++e)b.push(a.replace(c[0],String.fromCharCode(e)));return b}if(c=c=/\{(\d+)-(\d+)\}/.exec(a)){d=parseInt(c[2],10);for(e=parseInt(c[1],10);e<=d;e++)b.push(a.replace(c[0],e.toString()));return b}b.push(a);return b};function gw(a){lk.call(this);this.highWaterMark=void 0!==a?a:2048}u(gw,lk);function hw(a){return a.c>a.highWaterMark}gw.prototype.ld=function(a){for(var b,c;hw(this);){b=this.a.cd;c=b.Ga[0].toString();var d;if(d=c in a)b=b.Ga,d=ua(a[c],b[1],b[2]);if(d)break;else Kc(this.pop())}};function iw(a){Tt.call(this,{attributions:a.attributions,extent:a.extent,logo:a.logo,projection:a.projection,state:a.state,wrapX:a.wrapX});this.na=void 0!==a.opaque?a.opaque:!1;this.Va=void 0!==a.tilePixelRatio?a.tilePixelRatio:1;this.tileGrid=void 0!==a.tileGrid?a.tileGrid:null;this.a=new gw(a.cacheSize);this.l=[0,0];this.wc=""}u(iw,Tt);k=iw.prototype;k.Ei=function(){return hw(this.a)};k.ld=function(a,b){var c=this.Ud(a);c&&c.ld(b)}; -function rt(a,b,c,d,e){b=a.Ud(b);if(!b)return!1;for(var f=!0,g,h,l=d.da;l<=d.ba;++l)for(var m=d.ga;m<=d.ja;++m)g=a.Tb(c,l,m),h=!1,b.b.hasOwnProperty(g)&&(g=b.get(g),(h=2===g.V())&&(h=!1!==e(g))),h||(f=!1);return f}k.Rf=function(){return 0};function jw(a,b){a.wc!==b&&(a.wc=b,a.s())}k.Tb=function(a,b,c){return a+"/"+b+"/"+c};k.Uf=function(){return this.na};k.ab=function(){return this.tileGrid};k.Jb=function(a){return this.tileGrid?this.tileGrid:tc(a)}; -k.Ud=function(a){var b=this.c;return b&&!bc(b,a)?null:this.a};k.pb=function(){return this.Va};k.Vd=function(a,b,c){c=this.Jb(c);b=this.pb(b);a=Ha(c.eb(a),this.l);return 1==b?a:Ga(a,b,this.l)};function kw(a,b,c){var d=void 0!==c?c:a.c;c=a.Jb(d);if(a.G&&d.g){var e=b;b=e[0];a=sc(c,e);d=uc(d);Qa(d,a)?b=e:(e=ib(d),a[0]+=e*Math.ceil((d[0]-a[0])/e),b=c.Xf(a,b))}e=b[0];d=b[1];a=b[2];if(c.minZoom>e||e>c.maxZoom)c=!1;else{var f=c.D();c=(c=f?nc(c,f,e):c.a?c.a[e]:null)?ua(c,d,a):!0}return c?b:null} -k.va=function(){this.a.clear();this.s()};k.Mg=oa;function lw(a,b){Lc.call(this,a);this.tile=b}u(lw,Lc);function mw(a){iw.call(this,{attributions:a.attributions,cacheSize:a.cacheSize,extent:a.extent,logo:a.logo,opaque:a.opaque,projection:a.projection,state:a.state,tileGrid:a.tileGrid,tilePixelRatio:a.tilePixelRatio,wrapX:a.wrapX});this.tileLoadFunction=a.tileLoadFunction;this.tileUrlFunction=this.Hc?this.Hc.bind(this):ew;this.urls=null;a.urls?this.cb(a.urls):a.url&&this.ib(a.url);a.tileUrlFunction&&this.bb(a.tileUrlFunction)}u(mw,iw);k=mw.prototype;k.ob=function(){return this.tileLoadFunction}; -k.qb=function(){return this.tileUrlFunction};k.rb=function(){return this.urls};k.Fi=function(a){a=a.target;switch(a.V()){case 1:this.b(new lw("tileloadstart",a));break;case 2:this.b(new lw("tileloadend",a));break;case 3:this.b(new lw("tileloaderror",a))}};k.wb=function(a){this.a.clear();this.tileLoadFunction=a;this.s()};k.bb=function(a,b){this.tileUrlFunction=a;"undefined"!==typeof b?jw(this,b):this.s()}; -k.ib=function(a){var b=this.urls=fw(a);this.bb(this.Hc?this.Hc.bind(this):cw(b,this.tileGrid),a)};k.cb=function(a){this.urls=a;var b=a.join("\n");this.bb(this.Hc?this.Hc.bind(this):cw(a,this.tileGrid),b)};k.Mg=function(a,b,c){a=this.Tb(a,b,c);this.a.b.hasOwnProperty(a)&&this.a.get(a)};function W(a){mw.call(this,{attributions:a.attributions,cacheSize:a.cacheSize,extent:a.extent,logo:a.logo,opaque:a.opaque,projection:a.projection,state:a.state,tileGrid:a.tileGrid,tileLoadFunction:a.tileLoadFunction?a.tileLoadFunction:nw,tilePixelRatio:a.tilePixelRatio,tileUrlFunction:a.tileUrlFunction,url:a.url,urls:a.urls,wrapX:a.wrapX});this.crossOrigin=void 0!==a.crossOrigin?a.crossOrigin:null;this.tileClass=a.tileClass?a.tileClass:Ks;this.f={};this.u={};this.Ha=a.reprojectionErrorThreshold;this.C= -!1}u(W,mw);k=W.prototype;k.Ei=function(){if(hw(this.a))return!0;for(var a in this.f)if(hw(this.f[a]))return!0;return!1};k.ld=function(a,b){var c=this.Ud(a);this.a.ld(this.a==c?b:{});for(var d in this.f){var e=this.f[d];e.ld(e==c?b:{})}};k.Rf=function(a){return this.c&&a&&!bc(this.c,a)?0:this.Sf()};k.Sf=function(){return 0};k.Uf=function(a){return this.c&&a&&!bc(this.c,a)?!1:mw.prototype.Uf.call(this,a)}; -k.Jb=function(a){var b=this.c;return!this.tileGrid||b&&!bc(b,a)?(b=w(a).toString(),b in this.u||(this.u[b]=tc(a)),this.u[b]):this.tileGrid};k.Ud=function(a){var b=this.c;if(!b||bc(b,a))return this.a;a=w(a).toString();a in this.f||(this.f[a]=new gw(this.a.highWaterMark));return this.f[a]};function ow(a,b,c,d,e,f,g){b=[b,c,d];e=(c=kw(a,b,f))?a.tileUrlFunction(c,e,f):void 0;e=new a.tileClass(b,void 0!==e?0:4,void 0!==e?e:"",a.crossOrigin,a.tileLoadFunction);e.key=g;z(e,"change",a.Fi,a);return e} -k.Pc=function(a,b,c,d,e){if(this.c&&e&&!bc(this.c,e)){var f=this.Ud(e);c=[a,b,c];var g;a=this.Tb.apply(this,c);f.b.hasOwnProperty(a)&&(g=f.get(a));b=this.wc;if(g&&g.key==b)return g;var h=this.c,l=this.Jb(h),m=this.Jb(e),n=kw(this,c,e);d=new aw(h,l,e,m,c,n,this.pb(d),this.Sf(),function(a,b,c,d){return pw(this,a,b,c,d,h)}.bind(this),this.Ha,this.C);d.key=b;g?(d.a=g,f.replace(a,d)):f.set(a,d);return d}return pw(this,a,b,c,d,e)}; -function pw(a,b,c,d,e,f){var g,h=a.Tb(b,c,d),l=a.wc;if(a.a.b.hasOwnProperty(h)){if(g=a.a.get(h),g.key!=l){var m=g;g=ow(a,b,c,d,e,f,l);0==m.V()?g.a=m.a:g.a=m;if(g.a){b=g.a;c=g;do{if(2==b.V()){b.a=null;break}else 1==b.V()?c=b:0==b.V()?c.a=b.a:c=b;b=c.a}while(b)}a.a.replace(h,g)}}else g=ow(a,b,c,d,e,f,l),a.a.set(h,g);return g}k.Ob=function(a){if(this.C!=a){this.C=a;for(var b in this.f)this.f[b].clear();this.s()}};k.Pb=function(a,b){var c=Tb(a);c&&(c=w(c).toString(),c in this.u||(this.u[c]=b))}; -function nw(a,b){a.Y().src=b};function qw(a){this.A=void 0!==a.hidpi?a.hidpi:!1;W.call(this,{cacheSize:a.cacheSize,crossOrigin:"anonymous",opaque:!0,projection:Tb("EPSG:3857"),reprojectionErrorThreshold:a.reprojectionErrorThreshold,state:"loading",tileLoadFunction:a.tileLoadFunction,tilePixelRatio:this.A?2:1,wrapX:void 0!==a.wrapX?a.wrapX:!0});this.I=void 0!==a.culture?a.culture:"en-us";this.v=void 0!==a.maxZoom?a.maxZoom:-1;this.i=a.key;this.o=a.imagerySet;$v("https://dev.virtualearth.net/REST/v1/Imagery/Metadata/"+this.o+"?uriScheme=https&include=ImageryProviders&key="+ -this.i,this.fa.bind(this),void 0,"jsonp")}u(qw,W);var rw=new xc({html:'<a class="ol-attribution-bing-tos" href="http://www.microsoft.com/maps/product/terms.html">Terms of Use</a>'});qw.prototype.T=function(){return this.i};qw.prototype.ea=function(){return this.o}; -qw.prototype.fa=function(a){if(200!=a.statusCode||"OK"!=a.statusDescription||"ValidCredentials"!=a.authenticationResultCode||1!=a.resourceSets.length||1!=a.resourceSets[0].resources.length)Vt(this,"error");else{var b=a.brandLogoUri;-1==b.indexOf("https")&&(b=b.replace("http","https"));var c=a.resourceSets[0].resources[0],d=-1==this.v?c.zoomMax:this.v;a=uc(this.c);var e=wc({extent:a,minZoom:c.zoomMin,maxZoom:d,tileSize:(c.imageWidth==c.imageHeight?c.imageWidth:[c.imageWidth,c.imageHeight])/this.pb()}); -this.tileGrid=e;var f=this.I,g=this.A;this.tileUrlFunction=dw(c.imageUrlSubdomains.map(function(a){var b=[0,0,0],d=c.imageUrl.replace("{subdomain}",a).replace("{culture}",f);return function(a){if(a)return ic(a[0],a[1],-a[2]-1,b),a=d,g&&(a+="&dpi=d1&device=mobile"),a.replace("{quadkey}",jc(b))}}));if(c.imageryProviders){var h=Sb(Tb("EPSG:4326"),this.c);a=c.imageryProviders.map(function(a){var b=a.attribution,c={};a.coverageAreas.forEach(function(a){var b=a.zoomMin,f=Math.min(a.zoomMax,d);a=a.bbox; -a=pb([a[1],a[0],a[3],a[2]],h);var g,l;for(g=b;g<=f;++g)l=g.toString(),b=nc(e,a,g),l in c?c[l].push(b):c[l]=[b]});return new xc({html:b,tileRanges:c})});a.push(rw);this.ua(a)}this.Z=b;Vt(this,"ready")}};function sw(a){a=a||{};var b=void 0!==a.projection?a.projection:"EPSG:3857",c=void 0!==a.tileGrid?a.tileGrid:wc({extent:uc(b),maxZoom:a.maxZoom,minZoom:a.minZoom,tileSize:a.tileSize});W.call(this,{attributions:a.attributions,cacheSize:a.cacheSize,crossOrigin:a.crossOrigin,logo:a.logo,opaque:a.opaque,projection:b,reprojectionErrorThreshold:a.reprojectionErrorThreshold,tileGrid:c,tileLoadFunction:a.tileLoadFunction,tilePixelRatio:a.tilePixelRatio,tileUrlFunction:a.tileUrlFunction,url:a.url,urls:a.urls, -wrapX:void 0!==a.wrapX?a.wrapX:!0})}u(sw,W);function tw(a){this.v=a.account;this.A=a.map||"";this.i=a.config||{};this.o={};sw.call(this,{attributions:a.attributions,cacheSize:a.cacheSize,crossOrigin:a.crossOrigin,logo:a.logo,maxZoom:void 0!==a.maxZoom?a.maxZoom:18,minZoom:a.minZoom,projection:a.projection,state:"loading",wrapX:a.wrapX});uw(this)}u(tw,sw);k=tw.prototype;k.Gk=function(){return this.i};k.iq=function(a){qb(this.i,a);uw(this)};k.Np=function(a){this.i=a||{};uw(this)}; -function uw(a){var b=JSON.stringify(a.i);if(a.o[b])vw(a,a.o[b]);else{var c="https://"+a.v+".cartodb.com/api/v1/map";a.A&&(c+="/named/"+a.A);var d=new XMLHttpRequest;d.addEventListener("load",a.yl.bind(a,b));d.addEventListener("error",a.xl.bind(a));d.open("POST",c);d.setRequestHeader("Content-type","application/json");d.send(JSON.stringify(a.i))}} -k.yl=function(a,b){var c=b.target;if(!c.status||200<=c.status&&300>c.status){var d;try{d=JSON.parse(c.responseText)}catch(e){Vt(this,"error");return}vw(this,d);this.o[a]=d;Vt(this,"ready")}else Vt(this,"error")};k.xl=function(){Vt(this,"error")};function vw(a,b){a.ib("https://"+b.cdn_url.https+"/"+a.v+"/api/v1/map/"+b.layergroupid+"/{z}/{x}/{y}.png")};function X(a){T.call(this,{attributions:a.attributions,extent:a.extent,logo:a.logo,projection:a.projection,wrapX:a.wrapX});this.C=void 0;this.I=void 0!==a.distance?a.distance:20;this.A=[];this.Qa=a.geometryFunction||function(a){a=a.U();sa(a instanceof E,10);return a};this.v=a.source;this.v.J("change",X.prototype.bj,this)}u(X,T);k=X.prototype;k.Qn=function(){return this.I};k.Rn=function(){return this.v};k.Xd=function(a,b,c){this.v.Xd(a,b,c);b!==this.C&&(this.clear(),this.C=b,ww(this),this.gd(this.A))}; -k.Op=function(a){this.I=a;this.bj()};k.bj=function(){this.clear();ww(this);this.gd(this.A);this.s()};function ww(a){if(void 0!==a.C){a.A.length=0;for(var b=Ja(),c=a.I*a.C,d=a.v.We(),e={},f=0,g=d.length;f<g;f++){var h=d[f];w(h).toString()in e||!(h=a.Qa(h))||(h=h.W(),Xa(h,b),Ma(b,c,b),h=a.v.Pf(b),h=h.filter(function(a){a=w(a).toString();return a in e?!1:e[a]=!0}),a.A.push(xw(a,h)))}}} -function xw(a,b){for(var c=[0,0],d=b.length-1;0<=d;--d){var e=a.Qa(b[d]);e?Xe(c,e.W()):b.splice(d,1)}df(c,1/b.length);c=new I(new E(c));c.set("features",b);return c};function yw(a,b){var c=[];Object.keys(b).forEach(function(a){null!==b[a]&&void 0!==b[a]&&c.push(a+"="+encodeURIComponent(b[a]))});var d=c.join("&");a=a.replace(/[?&]$/,"");a=-1===a.indexOf("?")?a+"?":a+"&";return a+d};function zw(a){a=a||{};zv.call(this,{attributions:a.attributions,logo:a.logo,projection:a.projection,resolutions:a.resolutions});this.I=void 0!==a.crossOrigin?a.crossOrigin:null;this.T=void 0!==a.hidpi?a.hidpi:!0;this.i=a.url;this.f=a.imageLoadFunction?a.imageLoadFunction:Fv;this.u=a.params||{};this.N=null;this.o=[0,0];this.C=0;this.A=void 0!==a.ratio?a.ratio:1.5}u(zw,zv);k=zw.prototype;k.Tn=function(){return this.u}; -k.Lc=function(a,b,c,d){if(void 0===this.i)return null;b=Av(this,b);c=this.T?c:1;var e=this.N;if(e&&this.C==this.g&&e.resolution==b&&e.a==c&&Ua(e.D(),a))return e;e={F:"image",FORMAT:"PNG32",TRANSPARENT:!0};qb(e,this.u);a=a.slice();var f=(a[0]+a[2])/2,g=(a[1]+a[3])/2;if(1!=this.A){var h=this.A*ib(a)/2,l=this.A*jb(a)/2;a[0]=f-h;a[1]=g-l;a[2]=f+h;a[3]=g+l}var h=b/c,l=Math.ceil(ib(a)/h),m=Math.ceil(jb(a)/h);a[0]=f-h*l/2;a[2]=f+h*l/2;a[1]=g-h*m/2;a[3]=g+h*m/2;this.o[0]=l;this.o[1]=m;f=a;g=this.o;h=c;d= -d.nb.split(":").pop();e.SIZE=g[0]+","+g[1];e.BBOX=f.join(",");e.BBOXSR=d;e.IMAGESR=d;e.DPI=Math.round(90*h);d=this.i;f=d.replace(/MapServer\/?$/,"MapServer/export").replace(/ImageServer\/?$/,"ImageServer/exportImage");f==d&&sa(!1,50);e=yw(f,e);this.N=new Gs(a,b,c,this.j,e,this.I,this.f);this.C=this.g;z(this.N,"change",this.l,this);return this.N};k.Sn=function(){return this.f};k.Un=function(){return this.i};k.Vn=function(a){this.N=null;this.f=a;this.s()}; -k.Wn=function(a){a!=this.i&&(this.i=a,this.N=null,this.s())};k.Xn=function(a){qb(this.u,a);this.N=null;this.s()};function Aw(a){zv.call(this,{projection:a.projection,resolutions:a.resolutions});this.I=void 0!==a.crossOrigin?a.crossOrigin:null;this.o=void 0!==a.displayDpi?a.displayDpi:96;this.f=a.params||{};this.C=a.url;this.i=a.imageLoadFunction?a.imageLoadFunction:Fv;this.T=void 0!==a.hidpi?a.hidpi:!0;this.fa=void 0!==a.metersPerUnit?a.metersPerUnit:1;this.u=void 0!==a.ratio?a.ratio:1;this.na=void 0!==a.useOverlay?a.useOverlay:!1;this.N=null;this.A=0}u(Aw,zv);k=Aw.prototype;k.Zn=function(){return this.f}; -k.Lc=function(a,b,c){b=Av(this,b);c=this.T?c:1;var d=this.N;if(d&&this.A==this.g&&d.resolution==b&&d.a==c&&Ua(d.D(),a))return d;1!=this.u&&(a=a.slice(),ob(a,this.u));var e=[ib(a)/b*c,jb(a)/b*c];if(void 0!==this.C){var d=this.C,f=kb(a),g=this.fa,h=ib(a),l=jb(a),m=e[0],n=e[1],p=.0254/this.o,e={OPERATION:this.na?"GETDYNAMICMAPOVERLAYIMAGE":"GETMAPIMAGE",VERSION:"2.0.0",LOCALE:"en",CLIENTAGENT:"ol.source.ImageMapGuide source",CLIP:"1",SETDISPLAYDPI:this.o,SETDISPLAYWIDTH:Math.round(e[0]),SETDISPLAYHEIGHT:Math.round(e[1]), -SETVIEWSCALE:n*h>m*l?h*g/(m*p):l*g/(n*p),SETVIEWCENTERX:f[0],SETVIEWCENTERY:f[1]};qb(e,this.f);d=yw(d,e);d=new Gs(a,b,c,this.j,d,this.I,this.i);z(d,"change",this.l,this)}else d=null;this.N=d;this.A=this.g;return d};k.Yn=function(){return this.i};k.ao=function(a){qb(this.f,a);this.s()};k.$n=function(a){this.N=null;this.i=a;this.s()};function Bw(a){var b=a.imageExtent,c=void 0!==a.crossOrigin?a.crossOrigin:null,d=a.imageLoadFunction?a.imageLoadFunction:Fv;zv.call(this,{attributions:a.attributions,logo:a.logo,projection:Tb(a.projection)});this.N=new Gs(b,void 0,1,this.j,a.url,c,d);this.i=a.imageSize?a.imageSize:null;z(this.N,"change",this.l,this)}u(Bw,zv);Bw.prototype.Lc=function(a){return nb(a,this.N.D())?this.N:null}; -Bw.prototype.l=function(a){if(2==this.N.V()){var b=this.N.D(),c=this.N.Y(),d,e;this.i?(d=this.i[0],e=this.i[1]):(d=c.width,e=c.height);b=Math.ceil(ib(b)/(jb(b)/e));if(b!=d){var b=hd(b,e),f=b.canvas;b.drawImage(c,0,0,d,e,0,0,f.width,f.height);this.N.Hg(f)}}zv.prototype.l.call(this,a)};function Cw(a){a=a||{};zv.call(this,{attributions:a.attributions,logo:a.logo,projection:a.projection,resolutions:a.resolutions});this.fa=void 0!==a.crossOrigin?a.crossOrigin:null;this.f=a.url;this.u=a.imageLoadFunction?a.imageLoadFunction:Fv;this.i=a.params||{};this.o=!0;Dw(this);this.T=a.serverType;this.na=void 0!==a.hidpi?a.hidpi:!0;this.N=null;this.A=[0,0];this.I=0;this.C=void 0!==a.ratio?a.ratio:1.5}u(Cw,zv);var Ew=[101,101];k=Cw.prototype; -k.io=function(a,b,c,d){if(void 0!==this.f){var e=lb(a,b,0,Ew),f={SERVICE:"WMS",VERSION:"1.3.0",REQUEST:"GetFeatureInfo",FORMAT:"image/png",TRANSPARENT:!0,QUERY_LAYERS:this.i.LAYERS};qb(f,this.i,d);d=Math.floor((e[3]-a[1])/b);f[this.o?"I":"X"]=Math.floor((a[0]-e[0])/b);f[this.o?"J":"Y"]=d;return Fw(this,e,Ew,1,Tb(c),f)}};k.ko=function(){return this.i}; -k.Lc=function(a,b,c,d){if(void 0===this.f)return null;b=Av(this,b);1==c||this.na&&void 0!==this.T||(c=1);var e=b/c,f=kb(a),g=lb(f,e,0,[Math.ceil(ib(a)/e),Math.ceil(jb(a)/e)]);a=lb(f,e,0,[Math.ceil(this.C*ib(a)/e),Math.ceil(this.C*jb(a)/e)]);if((f=this.N)&&this.I==this.g&&f.resolution==b&&f.a==c&&Ua(f.D(),g))return f;g={SERVICE:"WMS",VERSION:"1.3.0",REQUEST:"GetMap",FORMAT:"image/png",TRANSPARENT:!0};qb(g,this.i);this.A[0]=Math.round(ib(a)/e);this.A[1]=Math.round(jb(a)/e);d=Fw(this,a,this.A,c,d,g); -this.N=new Gs(a,b,c,this.j,d,this.fa,this.u);this.I=this.g;z(this.N,"change",this.l,this);return this.N};k.jo=function(){return this.u}; -function Fw(a,b,c,d,e,f){sa(void 0!==a.f,9);f[a.o?"CRS":"SRS"]=e.nb;"STYLES"in a.i||(f.STYLES="");if(1!=d)switch(a.T){case "geoserver":d=90*d+.5|0;f.FORMAT_OPTIONS="FORMAT_OPTIONS"in f?f.FORMAT_OPTIONS+(";dpi:"+d):"dpi:"+d;break;case "mapserver":f.MAP_RESOLUTION=90*d;break;case "carmentaserver":case "qgis":f.DPI=90*d;break;default:sa(!1,8)}f.WIDTH=c[0];f.HEIGHT=c[1];c=e.b;var g;a.o&&"ne"==c.substr(0,2)?g=[b[1],b[0],b[3],b[2]]:g=b;f.BBOX=g.join(",");return yw(a.f,f)}k.lo=function(){return this.f}; -k.mo=function(a){this.N=null;this.u=a;this.s()};k.no=function(a){a!=this.f&&(this.f=a,this.N=null,this.s())};k.oo=function(a){qb(this.i,a);Dw(this);this.N=null;this.s()};function Dw(a){a.o=0<=We(a.i.VERSION||"1.3.0")};function Gw(a){a=a||{};var b;void 0!==a.attributions?b=a.attributions:b=[Hw];sw.call(this,{attributions:b,cacheSize:a.cacheSize,crossOrigin:void 0!==a.crossOrigin?a.crossOrigin:"anonymous",opaque:void 0!==a.opaque?a.opaque:!0,maxZoom:void 0!==a.maxZoom?a.maxZoom:19,reprojectionErrorThreshold:a.reprojectionErrorThreshold,tileLoadFunction:a.tileLoadFunction,url:void 0!==a.url?a.url:"https://{a-c}.tile.openstreetmap.org/{z}/{x}/{y}.png",wrapX:a.wrapX})}u(Gw,sw);var Hw=new xc({html:'© <a href="https://www.openstreetmap.org/copyright">OpenStreetMap</a> contributors.'});(function(){var a={},b={ma:a};(function(c){if("object"===typeof a&&"undefined"!==typeof b)b.ma=c();else{var d;"undefined"!==typeof window?d=window:"undefined"!==typeof global?d=global:"undefined"!==typeof self?d=self:d=this;d.Cq=c()}})(function(){return function d(a,b,g){function e(h,l){if(!b[h]){if(!a[h]){var m="function"==typeof require&&require;if(!l&&m)return m(h,!0);if(f)return f(h,!0);m=Error("Cannot find module '"+h+"'");throw m.code="MODULE_NOT_FOUND",m;}m=b[h]={ma:{}};a[h][0].call(m.ma,function(b){var d= -a[h][1][b];return e(d?d:b)},m,m.ma,d,a,b,g)}return b[h].ma}for(var f="function"==typeof require&&require,m=0;m<g.length;m++)e(g[m]);return e}({1:[function(a,b,f){a=a("./processor");f.Pj=a},{"./processor":2}],2:[function(a,b){function d(a){var b=!0;try{new ImageData(10,10)}catch(q){b=!1}return function(d){var e=d.buffers,f=d.meta,g=d.width,h=d.height,l=e.length,m=e[0].byteLength;if(d.imageOps){m=Array(l);for(d=0;d<l;++d){var n=m,p=d,q;q=new Uint8ClampedArray(e[d]);var Ka=g,C=h;q=b?new ImageData(q, -Ka,C):{data:q,width:Ka,height:C};n[p]=q}g=a(m,f).data}else{g=new Uint8ClampedArray(m);h=Array(l);n=Array(l);for(d=0;d<l;++d)h[d]=new Uint8ClampedArray(e[d]),n[d]=[0,0,0,0];for(e=0;e<m;e+=4){for(d=0;d<l;++d)p=h[d],n[d][0]=p[e],n[d][1]=p[e+1],n[d][2]=p[e+2],n[d][3]=p[e+3];d=a(n,f);g[e]=d[0];g[e+1]=d[1];g[e+2]=d[2];g[e+3]=d[3]}}return g.buffer}}function e(a,b){var e=Object.keys(a.lib||{}).map(function(b){return"var "+b+" = "+a.lib[b].toString()+";"}).concat(["var __minion__ = ("+d.toString()+")(",a.operation.toString(), -");",'self.addEventListener("message", function(event) {'," var buffer = __minion__(event.data);"," self.postMessage({buffer: buffer, meta: event.data.meta}, [buffer]);","});"]),e=URL.createObjectURL(new Blob(e,{type:"text/javascript"})),e=new Worker(e);e.addEventListener("message",b);return e}function h(a,b){var e=d(a.operation);return{postMessage:function(a){setTimeout(function(){b({data:{buffer:e(a),meta:a.meta}})},0)}}}function l(a){this.Bf=!!a.Vl;var b;0===a.threads?b=0:this.Bf?b=1:b=a.threads|| -1;var d=[];if(b)for(var f=0;f<b;++f)d[f]=e(a,this.Yg.bind(this,f));else d[0]=h(a,this.Yg.bind(this,0));this.qe=d;this.Fd=[];this.bk=a.hp||Infinity;this.oe=0;this.fd={};this.Cf=null}var m=a("./util").om;l.prototype.fp=function(a,b,d){this.$j({inputs:a,Jh:b,jd:d});this.Vg()};l.prototype.$j=function(a){for(this.Fd.push(a);this.Fd.length>this.bk;)this.Fd.shift().jd(null,null)};l.prototype.Vg=function(){if(0===this.oe&&0<this.Fd.length){var a=this.Cf=this.Fd.shift(),b=a.inputs[0].width,d=a.inputs[0].height, -e=a.inputs.map(function(a){return a.data.buffer}),f=this.qe.length;this.oe=f;if(1===f)this.qe[0].postMessage({buffers:e,meta:a.Jh,imageOps:this.Bf,width:b,height:d},e);else for(var g=4*Math.ceil(a.inputs[0].data.length/4/f),h=0;h<f;++h){for(var l=h*g,m=[],aa=0,Ra=e.length;aa<Ra;++aa)m.push(e[h].slice(l,l+g));this.qe[h].postMessage({buffers:m,meta:a.Jh,imageOps:this.Bf,width:b,height:d},m)}}};l.prototype.Yg=function(a,b){this.Aq||(this.fd[a]=b.data,--this.oe,0===this.oe&&this.ck())};l.prototype.ck= -function(){var a=this.Cf,b=this.qe.length,d,e;if(1===b)d=new Uint8ClampedArray(this.fd[0].buffer),e=this.fd[0].meta;else{var f=a.inputs[0].data.length;d=new Uint8ClampedArray(f);e=Array(f);for(var f=4*Math.ceil(f/4/b),g=0;g<b;++g){var h=g*f;d.set(new Uint8ClampedArray(this.fd[g].buffer),h);e[g]=this.fd[g].meta}}this.Cf=null;this.fd={};a.jd(null,m(d,a.inputs[0].width,a.inputs[0].height),e);this.Vg()};b.ma=l},{"./util":3}],3:[function(a,b,f){var d=!0;try{new ImageData(10,10)}catch(l){d=!1}var e=document.createElement("canvas").getContext("2d"); -f.om=function(a,b,f){if(d)return new ImageData(a,b,f);b=e.createImageData(b,f);b.data.set(a);return b}},{}]},{},[1])(1)});Fj=b.ma})();function Iw(a){this.A=null;this.na=void 0!==a.operationType?a.operationType:"pixel";this.Ha=void 0!==a.threads?a.threads:1;this.f=Jw(a.sources);for(var b=0,c=this.f.length;b<c;++b)z(this.f[b],"change",this.s,this);this.T=new Ne(function(){return 1},this.s.bind(this));for(var b=Kw(this.f),c={},d=0,e=b.length;d<e;++d)c[w(b[d].layer)]=b[d];this.i=null;this.C={animate:!1,attributions:{},coordinateToPixelTransform:yh(),extent:null,focus:null,index:0,layerStates:c,layerStatesArray:b,logos:{},pixelRatio:1, -pixelToCoordinateTransform:yh(),postRenderFunctions:[],size:[0,0],skippedFeatureUids:{},tileQueue:this.T,time:Date.now(),usedTiles:{},viewState:{rotation:0},viewHints:[],wantedTiles:{}};zv.call(this,{});a.operation&&this.u(a.operation,a.lib)}u(Iw,zv);Iw.prototype.u=function(a,b){this.A=new Fj.Pj({operation:a,Vl:"image"===this.na,hp:1,lib:b,threads:this.Ha});this.s()}; -Iw.prototype.Y=function(a,b,c,d){c=!0;for(var e,f=0,g=this.f.length;f<g;++f)if(e=this.f[f].a.ka(),"ready"!==e.V()){c=!1;break}if(!c)return null;c=qb({},this.C);c.viewState=qb({},c.viewState);e=kb(a);c.extent=a.slice();c.focus=e;c.size[0]=Math.round(ib(a)/b);c.size[1]=Math.round(jb(a)/b);f=c.viewState;f.center=e;f.projection=d;f.resolution=b;this.o=c;Oe(c.tileQueue,16,16);this.i&&(d=this.i.resolution,c=this.i.D(),b===d&&$a(a,c)||(this.i=null));if(!this.i||this.g!==this.I)a:{a=this.o;d=this.f.length; -b=Array(d);for(c=0;c<d;++c){e=this.f[c];f=a;g=a.layerStatesArray[c];if(e.ud(f,g)){var h=f.size[0],l=f.size[1];if(Lw){var m=Lw.canvas;m.width!==h||m.height!==l?Lw=hd(h,l):Lw.clearRect(0,0,h,l)}else Lw=hd(h,l);e.O(f,g,Lw);e=Lw.getImageData(0,0,h,l)}else e=null;if(e)b[c]=e;else break a}d={};this.b(new Mw(Nw,a,d));this.A.fp(b,d,this.fa.bind(this,a))}return this.i}; -Iw.prototype.fa=function(a,b,c,d){if(!b&&c){b=a.extent;var e=a.viewState.resolution;if(e===this.o.viewState.resolution&&$a(b,this.o.extent)){var f;this.i?f=this.i.Y().getContext("2d"):(f=hd(Math.round(ib(b)/e),Math.round(jb(b)/e)),this.i=new Hs(b,e,1,this.j,f.canvas));f.putImageData(c,0,0);this.s();this.I=this.g;this.b(new Mw(Ow,a,d))}}};var Lw=null;function Kw(a){return a.map(function(a){return qh(a.a)})} -function Jw(a){for(var b=a.length,c=Array(b),d=0;d<b;++d){var e=d,f=a[d],g=null;f instanceof iw?(f=new Vv({source:f}),g=new Nv(f)):f instanceof zv&&(f=new Mv({source:f}),g=new rv(f));c[e]=g}return c}function Mw(a,b,c){Lc.call(this,a);this.extent=b.extent;this.resolution=b.viewState.resolution/b.pixelRatio;this.data=c}u(Mw,Lc);Iw.prototype.Lc=function(){return null};var Nw="beforeoperations",Ow="afteroperations";function Pw(a){var b=a.layer.indexOf("-"),b=Qw[-1==b?a.layer:a.layer.slice(0,b)],c=Rw[a.layer];sw.call(this,{attributions:Sw,cacheSize:a.cacheSize,crossOrigin:"anonymous",maxZoom:void 0!=a.maxZoom?a.maxZoom:b.maxZoom,minZoom:void 0!=a.minZoom?a.minZoom:b.minZoom,opaque:c.opaque,reprojectionErrorThreshold:a.reprojectionErrorThreshold,tileLoadFunction:a.tileLoadFunction,url:void 0!==a.url?a.url:"https://stamen-tiles-{a-d}.a.ssl.fastly.net/"+a.layer+"/{z}/{x}/{y}."+c.Ib})}u(Pw,sw); -var Sw=[new xc({html:'Map tiles by <a href="http://stamen.com/">Stamen Design</a>, under <a href="http://creativecommons.org/licenses/by/3.0/">CC BY 3.0</a>.'}),Hw],Rw={terrain:{Ib:"jpg",opaque:!0},"terrain-background":{Ib:"jpg",opaque:!0},"terrain-labels":{Ib:"png",opaque:!1},"terrain-lines":{Ib:"png",opaque:!1},"toner-background":{Ib:"png",opaque:!0},toner:{Ib:"png",opaque:!0},"toner-hybrid":{Ib:"png",opaque:!1},"toner-labels":{Ib:"png",opaque:!1},"toner-lines":{Ib:"png",opaque:!1},"toner-lite":{Ib:"png", -opaque:!0},watercolor:{Ib:"jpg",opaque:!0}},Qw={terrain:{minZoom:4,maxZoom:18},toner:{minZoom:0,maxZoom:20},watercolor:{minZoom:1,maxZoom:16}};function Tw(a){a=a||{};W.call(this,{attributions:a.attributions,cacheSize:a.cacheSize,crossOrigin:a.crossOrigin,logo:a.logo,projection:a.projection,reprojectionErrorThreshold:a.reprojectionErrorThreshold,tileGrid:a.tileGrid,tileLoadFunction:a.tileLoadFunction,url:a.url,urls:a.urls,wrapX:void 0!==a.wrapX?a.wrapX:!0});this.i=a.params||{};this.o=Ja();jw(this,Uw(this))}u(Tw,W);function Uw(a){var b=0,c=[],d;for(d in a.i)c[b++]=d+"-"+a.i[d];return c.join("/")}Tw.prototype.v=function(){return this.i}; -Tw.prototype.pb=function(a){return a}; -Tw.prototype.Hc=function(a,b,c){var d=this.tileGrid;d||(d=this.Jb(c));if(!(d.b.length<=a[0])){var e=d.Ua(a,this.o),f=Ha(d.eb(a[0]),this.l);1!=b&&(f=Ga(f,b,this.l));d={F:"image",FORMAT:"PNG32",TRANSPARENT:!0};qb(d,this.i);var g=this.urls;g?(c=c.nb.split(":").pop(),d.SIZE=f[0]+","+f[1],d.BBOX=e.join(","),d.BBOXSR=c,d.IMAGESR=c,d.DPI=Math.round(d.DPI?d.DPI*b:90*b),a=(1==g.length?g[0]:g[Da((a[1]<<a[0])+a[2],g.length)]).replace(/MapServer\/?$/,"MapServer/export").replace(/ImageServer\/?$/,"ImageServer/exportImage"), -a=yw(a,d)):a=void 0;return a}};Tw.prototype.A=function(a){qb(this.i,a);jw(this,Uw(this))};function Vw(a){iw.call(this,{opaque:!1,projection:a.projection,tileGrid:a.tileGrid,wrapX:void 0!==a.wrapX?a.wrapX:!0})}u(Vw,iw);Vw.prototype.Pc=function(a,b,c){var d=this.Tb(a,b,c);if(this.a.b.hasOwnProperty(d))return this.a.get(d);var e=Ha(this.tileGrid.eb(a));a=[a,b,c];b=(b=kw(this,a))?kw(this,b).toString():"";e=new Ww(a,e,b);this.a.set(d,e);return e};function Ww(a,b,c){Is.call(this,a,2);this.c=b;this.Fa=c;this.g=null}u(Ww,Is); -Ww.prototype.Y=function(){if(this.g)return this.g;var a=this.c,b=hd(a[0],a[1]);b.strokeStyle="black";b.strokeRect(.5,.5,a[0]+.5,a[1]+.5);b.fillStyle="black";b.textAlign="center";b.textBaseline="middle";b.font="24px sans-serif";b.fillText(this.Fa,a[0]/2,a[1]/2);return this.g=b.canvas};Ww.prototype.load=function(){};function Xw(a){this.i=null;W.call(this,{attributions:a.attributions,cacheSize:a.cacheSize,crossOrigin:a.crossOrigin,projection:Tb("EPSG:3857"),reprojectionErrorThreshold:a.reprojectionErrorThreshold,state:"loading",tileLoadFunction:a.tileLoadFunction,wrapX:void 0!==a.wrapX?a.wrapX:!0});if(a.jsonp)$v(a.url,this.Ci.bind(this),this.Ue.bind(this));else{var b=new XMLHttpRequest;b.addEventListener("load",this.qo.bind(this));b.addEventListener("error",this.po.bind(this));b.open("GET",a.url);b.send()}} -u(Xw,W);k=Xw.prototype;k.qo=function(a){a=a.target;if(!a.status||200<=a.status&&300>a.status){var b;try{b=JSON.parse(a.responseText)}catch(c){this.Ue();return}this.Ci(b)}else this.Ue()};k.po=function(){this.Ue()};k.kl=function(){return this.i}; -k.Ci=function(a){var b=Tb("EPSG:4326"),c=this.c,d;if(a.bounds){var e=Sb(b,c);d=pb(a.bounds,e)}var f=a.minzoom||0,e=a.maxzoom||22;this.tileGrid=c=wc({extent:uc(c),maxZoom:e,minZoom:f});this.tileUrlFunction=cw(a.tiles,c);if(void 0!==a.attribution&&!this.j){b=void 0!==d?d:b.D();d={};for(var g;f<=e;++f)g=f.toString(),d[g]=[nc(c,b,f)];this.ua([new xc({html:a.attribution,tileRanges:d})])}this.i=a;Vt(this,"ready")};k.Ue=function(){Vt(this,"error")};function Yw(a){iw.call(this,{projection:Tb("EPSG:3857"),state:"loading"});this.u=void 0!==a.preemptive?a.preemptive:!0;this.o=ew;this.f=void 0;this.i=a.jsonp||!1;if(a.url)if(this.i)$v(a.url,this.jg.bind(this),this.Ve.bind(this));else{var b=new XMLHttpRequest;b.addEventListener("load",this.uo.bind(this));b.addEventListener("error",this.to.bind(this));b.open("GET",a.url);b.send()}else a.tileJSON?this.jg(a.tileJSON):sa(!1,51)}u(Yw,iw);k=Yw.prototype; -k.uo=function(a){a=a.target;if(!a.status||200<=a.status&&300>a.status){var b;try{b=JSON.parse(a.responseText)}catch(c){this.Ve();return}this.jg(b)}else this.Ve()};k.to=function(){this.Ve()};k.hl=function(){return this.f};k.vk=function(a,b,c,d,e){this.tileGrid?(b=this.tileGrid.Ae(a,b),Zw(this.Pc(b[0],b[1],b[2],1,this.c),a,c,d,e)):!0===e?setTimeout(function(){c.call(d,null)},0):c.call(d,null)};k.Ve=function(){Vt(this,"error")}; -k.jg=function(a){var b=Tb("EPSG:4326"),c=this.c,d;if(a.bounds){var e=Sb(b,c);d=pb(a.bounds,e)}var f=a.minzoom||0,e=a.maxzoom||22;this.tileGrid=c=wc({extent:uc(c),maxZoom:e,minZoom:f});this.f=a.template;var g=a.grids;if(g){this.o=cw(g,c);if(void 0!==a.attribution){b=void 0!==d?d:b.D();for(d={};f<=e;++f)g=f.toString(),d[g]=[nc(c,b,f)];this.ua([new xc({html:a.attribution,tileRanges:d})])}Vt(this,"ready")}else Vt(this,"error")}; -k.Pc=function(a,b,c,d,e){var f=this.Tb(a,b,c);if(this.a.b.hasOwnProperty(f))return this.a.get(f);a=[a,b,c];b=kw(this,a,e);d=this.o(b,d,e);d=new $w(a,void 0!==d?0:4,void 0!==d?d:"",this.tileGrid.Ua(a),this.u,this.i);this.a.set(f,d);return d};k.Mg=function(a,b,c){a=this.Tb(a,b,c);this.a.b.hasOwnProperty(a)&&this.a.get(a)};function $w(a,b,c,d,e,f){Is.call(this,a,b);this.o=c;this.g=d;this.v=e;this.c=this.l=this.f=null;this.u=f}u($w,Is);k=$w.prototype;k.Y=function(){return null}; -k.getData=function(a){if(!this.f||!this.l)return null;var b=this.f[Math.floor((1-(a[1]-this.g[1])/(this.g[3]-this.g[1]))*this.f.length)];if("string"!==typeof b)return null;b=b.charCodeAt(Math.floor((a[0]-this.g[0])/(this.g[2]-this.g[0])*b.length));93<=b&&b--;35<=b&&b--;b-=32;a=null;b in this.l&&(b=this.l[b],this.c&&b in this.c?a=this.c[b]:a=b);return a}; -function Zw(a,b,c,d,e){0==a.state&&!0===e?(Gc(a,"change",function(){c.call(d,this.getData(b))},a),ax(a)):!0===e?setTimeout(function(){c.call(d,this.getData(b))}.bind(a),0):c.call(d,a.getData(b))}k.hb=function(){return this.o};k.Ce=function(){this.state=3;this.s()};k.Di=function(a){this.f=a.grid;this.l=a.keys;this.c=a.data;this.state=4;this.s()}; -function ax(a){if(0==a.state)if(a.state=1,a.u)$v(a.o,a.Di.bind(a),a.Ce.bind(a));else{var b=new XMLHttpRequest;b.addEventListener("load",a.so.bind(a));b.addEventListener("error",a.ro.bind(a));b.open("GET",a.o);b.send()}}k.so=function(a){a=a.target;if(!a.status||200<=a.status&&300>a.status){var b;try{b=JSON.parse(a.responseText)}catch(c){this.Ce();return}this.Di(b)}else this.Ce()};k.ro=function(){this.Ce()};k.load=function(){this.v&&ax(this)};function bx(a){a=a||{};var b=a.params||{};W.call(this,{attributions:a.attributions,cacheSize:a.cacheSize,crossOrigin:a.crossOrigin,logo:a.logo,opaque:!("TRANSPARENT"in b?b.TRANSPARENT:1),projection:a.projection,reprojectionErrorThreshold:a.reprojectionErrorThreshold,tileGrid:a.tileGrid,tileLoadFunction:a.tileLoadFunction,url:a.url,urls:a.urls,wrapX:void 0!==a.wrapX?a.wrapX:!0});this.v=void 0!==a.gutter?a.gutter:0;this.i=b;this.o=!0;this.A=a.serverType;this.T=void 0!==a.hidpi?a.hidpi:!0;this.I=""; -cx(this);this.ea=Ja();dx(this);jw(this,ex(this))}u(bx,W);k=bx.prototype; -k.vo=function(a,b,c,d){c=Tb(c);var e=this.tileGrid;e||(e=this.Jb(c));b=e.Ae(a,b);if(!(e.b.length<=b[0])){var f=e.La(b[0]),g=e.Ua(b,this.ea),e=Ha(e.eb(b[0]),this.l),h=this.v;h&&(e=Fa(e,h,this.l),g=Ma(g,f*h,g));h={SERVICE:"WMS",VERSION:"1.3.0",REQUEST:"GetFeatureInfo",FORMAT:"image/png",TRANSPARENT:!0,QUERY_LAYERS:this.i.LAYERS};qb(h,this.i,d);d=Math.floor((g[3]-a[1])/f);h[this.o?"I":"X"]=Math.floor((a[0]-g[0])/f);h[this.o?"J":"Y"]=d;return fx(this,b,e,g,1,c,h)}};k.Sf=function(){return this.v}; -k.Tb=function(a,b,c){return this.I+W.prototype.Tb.call(this,a,b,c)};k.wo=function(){return this.i}; -function fx(a,b,c,d,e,f,g){var h=a.urls;if(h){g.WIDTH=c[0];g.HEIGHT=c[1];g[a.o?"CRS":"SRS"]=f.nb;"STYLES"in a.i||(g.STYLES="");if(1!=e)switch(a.A){case "geoserver":c=90*e+.5|0;g.FORMAT_OPTIONS="FORMAT_OPTIONS"in g?g.FORMAT_OPTIONS+(";dpi:"+c):"dpi:"+c;break;case "mapserver":g.MAP_RESOLUTION=90*e;break;case "carmentaserver":case "qgis":g.DPI=90*e;break;default:sa(!1,52)}f=f.b;a.o&&"ne"==f.substr(0,2)&&(a=d[0],d[0]=d[1],d[1]=a,a=d[2],d[2]=d[3],d[3]=a);g.BBOX=d.join(",");return yw(1==h.length?h[0]:h[Da((b[1]<< -b[0])+b[2],h.length)],g)}}k.pb=function(a){return this.T&&void 0!==this.A?a:1};function cx(a){var b=0,c=[];if(a.urls){var d,e;d=0;for(e=a.urls.length;d<e;++d)c[b++]=a.urls[d]}a.I=c.join("#")}function ex(a){var b=0,c=[],d;for(d in a.i)c[b++]=d+"-"+a.i[d];return c.join("/")} -k.Hc=function(a,b,c){var d=this.tileGrid;d||(d=this.Jb(c));if(!(d.b.length<=a[0])){1==b||this.T&&void 0!==this.A||(b=1);var e=d.La(a[0]),f=d.Ua(a,this.ea),d=Ha(d.eb(a[0]),this.l),g=this.v;g&&(d=Fa(d,g,this.l),f=Ma(f,e*g,f));1!=b&&(d=Ga(d,b,this.l));e={SERVICE:"WMS",VERSION:"1.3.0",REQUEST:"GetMap",FORMAT:"image/png",TRANSPARENT:!0};qb(e,this.i);return fx(this,a,d,f,b,c,e)}};k.cb=function(a){W.prototype.cb.call(this,a);cx(this)};k.xo=function(a){qb(this.i,a);cx(this);dx(this);jw(this,ex(this))}; -function dx(a){a.o=0<=We(a.i.VERSION||"1.3.0")};function gx(a,b,c,d,e){Is.call(this,a,b);this.c=null;this.l=d;this.f=null;this.g={Od:!1,Eg:null,kf:-1,Fg:-1,zd:null};this.v=e;this.o=c}u(gx,Is);k=gx.prototype;k.Y=function(){return-1==this.g.Fg?null:this.c.canvas};k.Gm=function(){return this.l};k.hb=function(){return this.o};k.load=function(){0==this.state&&(this.state=1,this.s(),this.v(this,this.o),this.u(null,NaN,null))};k.Qo=function(a,b){this.dg(b);this.hj(a)};k.Po=function(){this.state=3;this.s()};k.hj=function(a){this.f=a;this.state=2;this.s()}; -k.dg=function(a){this.j=a};k.mj=function(a){this.u=a};function hx(a,b){a.mj(Cl(b,a.l,a.Qo.bind(a),a.Po.bind(a)))};function ix(a){mw.call(this,{attributions:a.attributions,cacheSize:void 0!==a.cacheSize?a.cacheSize:128,extent:a.extent,logo:a.logo,opaque:!1,projection:a.projection,state:a.state,tileGrid:a.tileGrid,tileLoadFunction:a.tileLoadFunction?a.tileLoadFunction:hx,tileUrlFunction:a.tileUrlFunction,tilePixelRatio:a.tilePixelRatio,url:a.url,urls:a.urls,wrapX:void 0===a.wrapX?!0:a.wrapX});this.i=a.format?a.format:null;this.f=void 0==a.overlaps?!0:a.overlaps;this.tileClass=a.tileClass?a.tileClass:gx}u(ix,mw); -ix.prototype.Pc=function(a,b,c,d,e){var f=this.Tb(a,b,c);if(this.a.b.hasOwnProperty(f))return this.a.get(f);a=[a,b,c];d=(b=kw(this,a,e))?this.tileUrlFunction(b,d,e):void 0;d=new this.tileClass(a,void 0!==d?0:4,void 0!==d?d:"",this.i,this.tileLoadFunction);z(d,"change",this.Fi,this);this.a.set(f,d);return d};ix.prototype.pb=function(a){return void 0==a?mw.prototype.pb.call(this,a):a};ix.prototype.Vd=function(a,b){var c=Ha(this.tileGrid.eb(a));return[Math.round(c[0]*b),Math.round(c[1]*b)]};function jx(a){this.l=a.matrixIds;kc.call(this,{extent:a.extent,origin:a.origin,origins:a.origins,resolutions:a.resolutions,tileSize:a.tileSize,tileSizes:a.tileSizes,sizes:a.sizes})}u(jx,kc);jx.prototype.o=function(){return this.l}; -function kx(a,b,c){var d=[],e=[],f=[],g=[],h=[],l=void 0!==c?c:[];c=Tb(a.SupportedCRS.replace(/urn:ogc:def:crs:(\w+):(.*:)?(\w+)$/,"$1:$3"));var m=c.uc(),n="ne"==c.b.substr(0,2);a.TileMatrix.sort(function(a,b){return b.ScaleDenominator-a.ScaleDenominator});a.TileMatrix.forEach(function(a){var b;0<l.length?b=ia(l,function(b){return a.Identifier==b.TileMatrix}):b=!0;if(b){e.push(a.Identifier);b=2.8E-4*a.ScaleDenominator/m;var c=a.TileWidth,p=a.TileHeight;n?f.push([a.TopLeftCorner[1],a.TopLeftCorner[0]]): -f.push(a.TopLeftCorner);d.push(b);g.push(c==p?c:[c,p]);h.push([a.MatrixWidth,-a.MatrixHeight])}});return new jx({extent:b,origins:f,resolutions:d,matrixIds:e,tileSizes:g,sizes:h})};function Y(a){function b(a){a="KVP"==d?yw(a,f):a.replace(/\{(\w+?)\}/g,function(a,b){return b.toLowerCase()in f?f[b.toLowerCase()]:a});return function(b){if(b){var c={TileMatrix:e.l[b[0]],TileCol:b[1],TileRow:-b[2]-1};qb(c,g);b=a;return b="KVP"==d?yw(b,c):b.replace(/\{(\w+?)\}/g,function(a,b){return c[b]})}}}this.ea=void 0!==a.version?a.version:"1.0.0";this.v=void 0!==a.format?a.format:"image/jpeg";this.i=a.dimensions?a.dimensions:{};this.A=a.layer;this.o=a.matrixSet;this.I=a.style;var c=a.urls;void 0=== -c&&void 0!==a.url&&(c=fw(a.url));var d=this.T=void 0!==a.requestEncoding?a.requestEncoding:"KVP",e=a.tileGrid,f={layer:this.A,style:this.I,tilematrixset:this.o};"KVP"==d&&qb(f,{Service:"WMTS",Request:"GetTile",Version:this.ea,Format:this.v});var g=this.i,h=c&&0<c.length?dw(c.map(b)):ew;W.call(this,{attributions:a.attributions,cacheSize:a.cacheSize,crossOrigin:a.crossOrigin,logo:a.logo,projection:a.projection,reprojectionErrorThreshold:a.reprojectionErrorThreshold,tileClass:a.tileClass,tileGrid:e, -tileLoadFunction:a.tileLoadFunction,tilePixelRatio:a.tilePixelRatio,tileUrlFunction:h,urls:c,wrapX:void 0!==a.wrapX?a.wrapX:!1});jw(this,lx(this))}u(Y,W);k=Y.prototype;k.Ik=function(){return this.i};k.yo=function(){return this.v};k.zo=function(){return this.A};k.Vk=function(){return this.o};k.fl=function(){return this.T};k.Ao=function(){return this.I};k.ml=function(){return this.ea};function lx(a){var b=0,c=[],d;for(d in a.i)c[b++]=d+"-"+a.i[d];return c.join("/")} -k.jq=function(a){qb(this.i,a);jw(this,lx(this))};function mx(a){a=a||{};var b=a.size,c=b[0],d=b[1],e=[],f=256;switch(void 0!==a.tierSizeCalculation?a.tierSizeCalculation:nx){case nx:for(;c>f||d>f;)e.push([Math.ceil(c/f),Math.ceil(d/f)]),f+=f;break;case ox:for(;c>f||d>f;)e.push([Math.ceil(c/f),Math.ceil(d/f)]),c>>=1,d>>=1;break;default:sa(!1,53)}e.push([1,1]);e.reverse();for(var f=[1],g=[0],d=1,c=e.length;d<c;d++)f.push(1<<d),g.push(e[d-1][0]*e[d-1][1]+g[d-1]);f.reverse();b=[0,-b[1],b[0],0];b=new kc({extent:b,origin:fb(b),resolutions:f});(f=a.url)&& --1==f.indexOf("{TileGroup}")&&(f+="{TileGroup}/{z}-{x}-{y}.jpg");f=fw(f);f=dw(f.map(function(a){return function(b){if(b){var c=b[0],d=b[1];b=-b[2]-1;var f={z:c,x:d,y:b,TileGroup:"TileGroup"+((d+b*e[c][0]+g[c])/256|0)};return a.replace(/\{(\w+?)\}/g,function(a,b){return f[b]})}}}));W.call(this,{attributions:a.attributions,cacheSize:a.cacheSize,crossOrigin:a.crossOrigin,logo:a.logo,projection:a.projection,reprojectionErrorThreshold:a.reprojectionErrorThreshold,tileClass:px,tileGrid:b,tileUrlFunction:f})} -u(mx,W);function px(a,b,c,d,e){Ks.call(this,a,b,c,d,e);this.g=null}u(px,Ks);px.prototype.Y=function(){if(this.g)return this.g;var a=Ks.prototype.Y.call(this);if(2==this.state){if(256==a.width&&256==a.height)return this.g=a;var b=hd(256,256);b.drawImage(a,0,0);return this.g=b.canvas}return a};var nx="default",ox="truncated";function qx(a,b){this.b=b;this.a=[{x:0,y:0,width:a,height:a}];this.c={};this.g=hd(a,a);this.i=this.g.canvas}qx.prototype.get=function(a){return this.c[a]||null}; -qx.prototype.add=function(a,b,c,d,e){var f,g,h;g=0;for(h=this.a.length;g<h;++g)if(f=this.a[g],f.width>=b+this.b&&f.height>=c+this.b)return h={offsetX:f.x+this.b,offsetY:f.y+this.b,image:this.i},this.c[a]=h,d.call(e,this.g,f.x+this.b,f.y+this.b),a=g,b+=this.b,d=c+this.b,f.width-b>f.height-d?(c={x:f.x+b,y:f.y,width:f.width-b,height:f.height},b={x:f.x,y:f.y+d,width:b,height:f.height-d},rx(this,a,c,b)):(c={x:f.x+b,y:f.y,width:f.width-b,height:d},b={x:f.x,y:f.y+d,width:f.width,height:f.height-d},rx(this, -a,c,b)),h;return null};function rx(a,b,c,d){b=[b,1];0<c.width&&0<c.height&&b.push(c);0<d.width&&0<d.height&&b.push(d);a.a.splice.apply(a.a,b)};function sx(a){a=a||{};this.a=void 0!==a.initialSize?a.initialSize:256;this.g=void 0!==a.maxSize?a.maxSize:void 0!==ca?ca:2048;this.b=void 0!==a.space?a.space:1;this.i=[new qx(this.a,this.b)];this.c=this.a;this.f=[new qx(this.c,this.b)]}sx.prototype.add=function(a,b,c,d,e,f){if(b+this.b>this.g||c+this.b>this.g)return null;d=tx(this,!1,a,b,c,d,f);if(!d)return null;a=tx(this,!0,a,b,c,e?e:oa,f);return{offsetX:d.offsetX,offsetY:d.offsetY,image:d.image,Ul:a.image}}; -function tx(a,b,c,d,e,f,g){var h=b?a.f:a.i,l,m,n;m=0;for(n=h.length;m<n;++m){l=h[m];if(l=l.add(c,d,e,f,g))return l;l||m!==n-1||(b?(l=Math.min(2*a.c,a.g),a.c=l):(l=Math.min(2*a.a,a.g),a.a=l),l=new qx(l,a.b),h.push(l),++n)}return null};qa.prototype.code=qa.prototype.code;t("ol.Attribution",xc);xc.prototype.getHTML=xc.prototype.g;t("ol.Collection",D);D.prototype.clear=D.prototype.clear;D.prototype.extend=D.prototype.ag;D.prototype.forEach=D.prototype.forEach;D.prototype.getArray=D.prototype.pm;D.prototype.item=D.prototype.item;D.prototype.getLength=D.prototype.fc;D.prototype.insertAt=D.prototype.Ge;D.prototype.pop=D.prototype.pop;D.prototype.push=D.prototype.push;D.prototype.remove=D.prototype.remove;D.prototype.removeAt=D.prototype.Bg; -D.prototype.setAt=D.prototype.Mp;Yc.prototype.element=Yc.prototype.element;t("ol.color.asArray",bd);t("ol.color.asString",dd);t("ol.colorlike.asColorLike",fd);t("ol.control.defaults",vd);t("ol.coordinate.add",Xe);t("ol.coordinate.createStringXY",function(a){return function(b){return hf(b,a)}});t("ol.coordinate.format",$e);t("ol.coordinate.rotate",cf);t("ol.coordinate.toStringHDMS",function(a,b){return a?Ze(a[1],"NS",b)+" "+Ze(a[0],"EW",b):""});t("ol.coordinate.toStringXY",hf); -t("ol.DeviceOrientation",Rk);Rk.prototype.getAlpha=Rk.prototype.Bk;Rk.prototype.getBeta=Rk.prototype.Ek;Rk.prototype.getGamma=Rk.prototype.Kk;Rk.prototype.getHeading=Rk.prototype.qm;Rk.prototype.getTracking=Rk.prototype.Mh;Rk.prototype.setTracking=Rk.prototype.bg;t("ol.easing.easeIn",od);t("ol.easing.easeOut",pd);t("ol.easing.inAndOut",qd);t("ol.easing.linear",rd);t("ol.easing.upAndDown",function(a){return.5>a?qd(2*a):1-qd(2*(a-.5))});t("ol.extent.boundingExtent",Ia);t("ol.extent.buffer",Ma); -t("ol.extent.containsCoordinate",Qa);t("ol.extent.containsExtent",Ua);t("ol.extent.containsXY",Sa);t("ol.extent.createEmpty",Ja);t("ol.extent.equals",$a);t("ol.extent.extend",ab);t("ol.extent.getBottomLeft",cb);t("ol.extent.getBottomRight",db);t("ol.extent.getCenter",kb);t("ol.extent.getHeight",jb);t("ol.extent.getIntersection",mb);t("ol.extent.getSize",function(a){return[a[2]-a[0],a[3]-a[1]]});t("ol.extent.getTopLeft",fb);t("ol.extent.getTopRight",eb);t("ol.extent.getWidth",ib); -t("ol.extent.intersects",nb);t("ol.extent.isEmpty",hb);t("ol.extent.applyTransform",pb);t("ol.Feature",I);I.prototype.clone=I.prototype.clone;I.prototype.getGeometry=I.prototype.U;I.prototype.getId=I.prototype.sm;I.prototype.getGeometryName=I.prototype.Mk;I.prototype.getStyle=I.prototype.tm;I.prototype.getStyleFunction=I.prototype.Rc;I.prototype.setGeometry=I.prototype.Ta;I.prototype.setStyle=I.prototype.cg;I.prototype.setId=I.prototype.lc;I.prototype.setGeometryName=I.prototype.Yc; -t("ol.featureloader.xhr",Dl);t("ol.Geolocation",us);us.prototype.getAccuracy=us.prototype.zk;us.prototype.getAccuracyGeometry=us.prototype.Ak;us.prototype.getAltitude=us.prototype.Ck;us.prototype.getAltitudeAccuracy=us.prototype.Dk;us.prototype.getHeading=us.prototype.um;us.prototype.getPosition=us.prototype.vm;us.prototype.getProjection=us.prototype.Nh;us.prototype.getSpeed=us.prototype.gl;us.prototype.getTracking=us.prototype.Oh;us.prototype.getTrackingOptions=us.prototype.zh; -us.prototype.setProjection=us.prototype.Ph;us.prototype.setTracking=us.prototype.Je;us.prototype.setTrackingOptions=us.prototype.sj;t("ol.Graticule",As);As.prototype.getMap=As.prototype.ym;As.prototype.getMeridians=As.prototype.Wk;As.prototype.getParallels=As.prototype.cl;As.prototype.setMap=As.prototype.setMap;t("ol.has.DEVICE_PIXEL_RATIO",Td);t("ol.has.CANVAS",Vd);t("ol.has.DEVICE_ORIENTATION",Wd);t("ol.has.GEOLOCATION",Xd);t("ol.has.TOUCH",Yd);t("ol.has.WEBGL",Nd);Gs.prototype.getImage=Gs.prototype.Y; -Gs.prototype.load=Gs.prototype.load;Ks.prototype.getImage=Ks.prototype.Y;t("ol.inherits",u);t("ol.interaction.defaults",oh);t("ol.Kinetic",ig);t("ol.loadingstrategy.all",St);t("ol.loadingstrategy.bbox",function(a){return[a]});t("ol.loadingstrategy.tile",function(a){return function(b,c){var d=a.Qc(c),e=nc(a,b,d),f=[],d=[d,0,0];for(d[1]=e.da;d[1]<=e.ba;++d[1])for(d[2]=e.ga;d[2]<=e.ja;++d[2])f.push(a.Ua(d));return f}});t("ol.Map",H);H.prototype.addControl=H.prototype.gk;H.prototype.addInteraction=H.prototype.hk; -H.prototype.addLayer=H.prototype.$g;H.prototype.addOverlay=H.prototype.ah;H.prototype.forEachFeatureAtPixel=H.prototype.we;H.prototype.forEachLayerAtPixel=H.prototype.Em;H.prototype.hasFeatureAtPixel=H.prototype.Tl;H.prototype.getEventCoordinate=H.prototype.Of;H.prototype.getEventPixel=H.prototype.xe;H.prototype.getTarget=H.prototype.Wf;H.prototype.getTargetElement=H.prototype.vc;H.prototype.getCoordinateFromPixel=H.prototype.Xa;H.prototype.getControls=H.prototype.Hk;H.prototype.getOverlays=H.prototype.al; -H.prototype.getOverlayById=H.prototype.$k;H.prototype.getInteractions=H.prototype.Nk;H.prototype.getLayerGroup=H.prototype.Mc;H.prototype.getLayers=H.prototype.Qh;H.prototype.getPixelFromCoordinate=H.prototype.Ka;H.prototype.getSize=H.prototype.Nb;H.prototype.getView=H.prototype.$;H.prototype.getViewport=H.prototype.nl;H.prototype.renderSync=H.prototype.Jp;H.prototype.render=H.prototype.render;H.prototype.removeControl=H.prototype.Cp;H.prototype.removeInteraction=H.prototype.Dp; -H.prototype.removeLayer=H.prototype.Fp;H.prototype.removeOverlay=H.prototype.Gp;H.prototype.setLayerGroup=H.prototype.lj;H.prototype.setSize=H.prototype.Ig;H.prototype.setTarget=H.prototype.Ke;H.prototype.setView=H.prototype.Yp;H.prototype.updateSize=H.prototype.Cd;Hd.prototype.originalEvent=Hd.prototype.originalEvent;Hd.prototype.pixel=Hd.prototype.pixel;Hd.prototype.coordinate=Hd.prototype.coordinate;Hd.prototype.dragging=Hd.prototype.dragging;Gd.prototype.map=Gd.prototype.map; -Gd.prototype.frameState=Gd.prototype.frameState;t("ol.Object",Qc);Qc.prototype.get=Qc.prototype.get;Qc.prototype.getKeys=Qc.prototype.P;Qc.prototype.getProperties=Qc.prototype.M;Qc.prototype.set=Qc.prototype.set;Qc.prototype.setProperties=Qc.prototype.H;Qc.prototype.unset=Qc.prototype.R;Uc.prototype.key=Uc.prototype.key;Uc.prototype.oldValue=Uc.prototype.oldValue;t("ol.Observable",Pc);t("ol.Observable.unByKey",function(a){if(Array.isArray(a))for(var b=0,c=a.length;b<c;++b)Bc(a[b]);else Bc(a)}); -Pc.prototype.changed=Pc.prototype.s;Pc.prototype.dispatchEvent=Pc.prototype.b;Pc.prototype.getRevision=Pc.prototype.L;Pc.prototype.on=Pc.prototype.J;Pc.prototype.once=Pc.prototype.once;Pc.prototype.un=Pc.prototype.K;t("ol.Overlay",sk);sk.prototype.getElement=sk.prototype.Rd;sk.prototype.getId=sk.prototype.Fm;sk.prototype.getMap=sk.prototype.Le;sk.prototype.getOffset=sk.prototype.wh;sk.prototype.getPosition=sk.prototype.Rh;sk.prototype.getPositioning=sk.prototype.xh;sk.prototype.setElement=sk.prototype.gj; -sk.prototype.setMap=sk.prototype.setMap;sk.prototype.setOffset=sk.prototype.nj;sk.prototype.setPosition=sk.prototype.Me;sk.prototype.setPositioning=sk.prototype.qj;t("ol.proj.METERS_PER_UNIT",xb);t("ol.proj.setProj4",function(a){yb=a});t("ol.proj.getPointResolution",Rb);t("ol.proj.addEquivalentProjections",Ub);t("ol.proj.addProjection",Yb);t("ol.proj.addCoordinateTransforms",$b);t("ol.proj.fromLonLat",function(a,b){return fc(a,"EPSG:4326",void 0!==b?b:"EPSG:3857")}); -t("ol.proj.toLonLat",function(a,b){return fc(a,void 0!==b?b:"EPSG:3857","EPSG:4326")});t("ol.proj.get",Tb);t("ol.proj.equivalent",bc);t("ol.proj.getTransform",dc);t("ol.proj.transform",fc);t("ol.proj.transformExtent",gc);t("ol.render.toContext",function(a,b){var c=a.canvas,d=b?b:{},e=d.pixelRatio||Td;if(d=d.size)c.width=d[0]*e,c.height=d[1]*e,c.style.width=d[0]+"px",c.style.height=d[1]+"px";c=[0,0,c.width,c.height];d=Fh(yh(),e,e);return new Uh(a,e,c,d,0)});t("ol.size.toSize",Ha);t("ol.Sphere",ub); -ub.prototype.geodesicArea=ub.prototype.a;ub.prototype.haversineDistance=ub.prototype.b;Is.prototype.getTileCoord=Is.prototype.i;Is.prototype.load=Is.prototype.load;t("ol.tilegrid.createXYZ",wc);gx.prototype.getFormat=gx.prototype.Gm;gx.prototype.setFeatures=gx.prototype.hj;gx.prototype.setProjection=gx.prototype.dg;gx.prototype.setLoader=gx.prototype.mj;t("ol.View",G);G.prototype.animate=G.prototype.animate;G.prototype.getAnimating=G.prototype.Kc;G.prototype.cancelAnimations=G.prototype.kd; -G.prototype.constrainCenter=G.prototype.Gc;G.prototype.constrainResolution=G.prototype.constrainResolution;G.prototype.constrainRotation=G.prototype.constrainRotation;G.prototype.getCenter=G.prototype.za;G.prototype.calculateExtent=G.prototype.hd;G.prototype.getMaxResolution=G.prototype.Hm;G.prototype.getMinResolution=G.prototype.Jm;G.prototype.getMaxZoom=G.prototype.Im;G.prototype.setMaxZoom=G.prototype.Up;G.prototype.getMinZoom=G.prototype.Km;G.prototype.setMinZoom=G.prototype.Vp; -G.prototype.getProjection=G.prototype.Lm;G.prototype.getResolution=G.prototype.Ra;G.prototype.getResolutions=G.prototype.Mm;G.prototype.getRotation=G.prototype.Sa;G.prototype.getZoom=G.prototype.Ah;G.prototype.getZoomForResolution=G.prototype.Be;G.prototype.fit=G.prototype.Mf;G.prototype.centerOn=G.prototype.qk;G.prototype.rotate=G.prototype.rotate;G.prototype.setCenter=G.prototype.lb;G.prototype.setResolution=G.prototype.$c;G.prototype.setRotation=G.prototype.Ne;G.prototype.setZoom=G.prototype.aq; -t("ol.xml.getAllTextContent",ll);t("ol.xml.parse",ql);Li.prototype.getGL=Li.prototype.Mo;Li.prototype.useProgram=Li.prototype.Vc;t("ol.tilegrid.TileGrid",kc);kc.prototype.forEachTileCoord=kc.prototype.mh;kc.prototype.getMaxZoom=kc.prototype.Ni;kc.prototype.getMinZoom=kc.prototype.Oi;kc.prototype.getOrigin=kc.prototype.Uc;kc.prototype.getResolution=kc.prototype.La;kc.prototype.getResolutions=kc.prototype.Pi;kc.prototype.getTileCoordExtent=kc.prototype.Ua; -kc.prototype.getTileCoordForCoordAndResolution=kc.prototype.Ae;kc.prototype.getTileCoordForCoordAndZ=kc.prototype.Xf;kc.prototype.getTileSize=kc.prototype.eb;kc.prototype.getZForResolution=kc.prototype.Qc;t("ol.tilegrid.WMTS",jx);jx.prototype.getMatrixIds=jx.prototype.o;t("ol.tilegrid.WMTS.createFromCapabilitiesMatrixSet",kx);t("ol.style.AtlasManager",sx);t("ol.style.Circle",$k);$k.prototype.setRadius=$k.prototype.Zc;t("ol.style.Fill",al);al.prototype.clone=al.prototype.clone; -al.prototype.getColor=al.prototype.g;al.prototype.setColor=al.prototype.c;t("ol.style.Icon",co);co.prototype.clone=co.prototype.clone;co.prototype.getAnchor=co.prototype.Jc;co.prototype.getColor=co.prototype.Bo;co.prototype.getImage=co.prototype.Y;co.prototype.getOrigin=co.prototype.Tc;co.prototype.getSrc=co.prototype.Co;co.prototype.getSize=co.prototype.kc;co.prototype.load=co.prototype.load;t("ol.style.Image",Xk);Xk.prototype.getOpacity=Xk.prototype.Ye;Xk.prototype.getRotateWithView=Xk.prototype.Ze; -Xk.prototype.getRotation=Xk.prototype.$e;Xk.prototype.getScale=Xk.prototype.af;Xk.prototype.getSnapToPixel=Xk.prototype.ze;Xk.prototype.setOpacity=Xk.prototype.vd;Xk.prototype.setRotation=Xk.prototype.bf;Xk.prototype.setScale=Xk.prototype.wd;t("ol.style.RegularShape",Yk);Yk.prototype.clone=Yk.prototype.clone;Yk.prototype.getAnchor=Yk.prototype.Jc;Yk.prototype.getAngle=Yk.prototype.Ji;Yk.prototype.getFill=Yk.prototype.Ca;Yk.prototype.getImage=Yk.prototype.Y;Yk.prototype.getOrigin=Yk.prototype.Tc; -Yk.prototype.getPoints=Yk.prototype.Ki;Yk.prototype.getRadius=Yk.prototype.Li;Yk.prototype.getRadius2=Yk.prototype.yh;Yk.prototype.getSize=Yk.prototype.kc;Yk.prototype.getStroke=Yk.prototype.Da;t("ol.style.Stroke",tj);tj.prototype.clone=tj.prototype.clone;tj.prototype.getColor=tj.prototype.Do;tj.prototype.getLineCap=tj.prototype.Qk;tj.prototype.getLineDash=tj.prototype.Eo;tj.prototype.getLineDashOffset=tj.prototype.Rk;tj.prototype.getLineJoin=tj.prototype.Sk;tj.prototype.getMiterLimit=tj.prototype.Xk; -tj.prototype.getWidth=tj.prototype.Fo;tj.prototype.setColor=tj.prototype.Go;tj.prototype.setLineCap=tj.prototype.Rp;tj.prototype.setLineDash=tj.prototype.setLineDash;tj.prototype.setLineDashOffset=tj.prototype.Sp;tj.prototype.setLineJoin=tj.prototype.Tp;tj.prototype.setMiterLimit=tj.prototype.Wp;tj.prototype.setWidth=tj.prototype.Zp;t("ol.style.Style",bl);bl.prototype.clone=bl.prototype.clone;bl.prototype.getGeometry=bl.prototype.U;bl.prototype.getGeometryFunction=bl.prototype.Lk; -bl.prototype.getFill=bl.prototype.Ca;bl.prototype.setFill=bl.prototype.mf;bl.prototype.getImage=bl.prototype.Y;bl.prototype.setImage=bl.prototype.Hg;bl.prototype.getStroke=bl.prototype.Da;bl.prototype.setStroke=bl.prototype.nf;bl.prototype.getText=bl.prototype.Oa;bl.prototype.setText=bl.prototype.pf;bl.prototype.getZIndex=bl.prototype.Aa;bl.prototype.setGeometry=bl.prototype.Ta;bl.prototype.setZIndex=bl.prototype.Xb;t("ol.style.Text",eo);eo.prototype.clone=eo.prototype.clone; -eo.prototype.getFont=eo.prototype.Jk;eo.prototype.getOffsetX=eo.prototype.Yk;eo.prototype.getOffsetY=eo.prototype.Zk;eo.prototype.getFill=eo.prototype.Ca;eo.prototype.getRotateWithView=eo.prototype.Ho;eo.prototype.getRotation=eo.prototype.Io;eo.prototype.getScale=eo.prototype.Jo;eo.prototype.getStroke=eo.prototype.Da;eo.prototype.getText=eo.prototype.Oa;eo.prototype.getTextAlign=eo.prototype.il;eo.prototype.getTextBaseline=eo.prototype.jl;eo.prototype.setFont=eo.prototype.ij; -eo.prototype.setOffsetX=eo.prototype.oj;eo.prototype.setOffsetY=eo.prototype.pj;eo.prototype.setFill=eo.prototype.mf;eo.prototype.setRotation=eo.prototype.Ko;eo.prototype.setScale=eo.prototype.Mi;eo.prototype.setStroke=eo.prototype.nf;eo.prototype.setText=eo.prototype.pf;eo.prototype.setTextAlign=eo.prototype.rj;eo.prototype.setTextBaseline=eo.prototype.Xp;t("ol.source.BingMaps",qw);t("ol.source.BingMaps.TOS_ATTRIBUTION",rw);qw.prototype.getApiKey=qw.prototype.T;qw.prototype.getImagerySet=qw.prototype.ea; -t("ol.source.CartoDB",tw);tw.prototype.getConfig=tw.prototype.Gk;tw.prototype.updateConfig=tw.prototype.iq;tw.prototype.setConfig=tw.prototype.Np;t("ol.source.Cluster",X);X.prototype.getDistance=X.prototype.Qn;X.prototype.getSource=X.prototype.Rn;X.prototype.setDistance=X.prototype.Op;t("ol.source.Image",zv);Bv.prototype.image=Bv.prototype.image;t("ol.source.ImageArcGISRest",zw);zw.prototype.getParams=zw.prototype.Tn;zw.prototype.getImageLoadFunction=zw.prototype.Sn;zw.prototype.getUrl=zw.prototype.Un; -zw.prototype.setImageLoadFunction=zw.prototype.Vn;zw.prototype.setUrl=zw.prototype.Wn;zw.prototype.updateParams=zw.prototype.Xn;t("ol.source.ImageCanvas",Gv);t("ol.source.ImageMapGuide",Aw);Aw.prototype.getParams=Aw.prototype.Zn;Aw.prototype.getImageLoadFunction=Aw.prototype.Yn;Aw.prototype.updateParams=Aw.prototype.ao;Aw.prototype.setImageLoadFunction=Aw.prototype.$n;t("ol.source.ImageStatic",Bw);t("ol.source.ImageVector",Hv);Hv.prototype.getSource=Hv.prototype.bo;Hv.prototype.getStyle=Hv.prototype.co; -Hv.prototype.getStyleFunction=Hv.prototype.eo;Hv.prototype.setStyle=Hv.prototype.Bi;t("ol.source.ImageWMS",Cw);Cw.prototype.getGetFeatureInfoUrl=Cw.prototype.io;Cw.prototype.getParams=Cw.prototype.ko;Cw.prototype.getImageLoadFunction=Cw.prototype.jo;Cw.prototype.getUrl=Cw.prototype.lo;Cw.prototype.setImageLoadFunction=Cw.prototype.mo;Cw.prototype.setUrl=Cw.prototype.no;Cw.prototype.updateParams=Cw.prototype.oo;t("ol.source.OSM",Gw);t("ol.source.OSM.ATTRIBUTION",Hw);t("ol.source.Raster",Iw); -Iw.prototype.setOperation=Iw.prototype.u;Mw.prototype.extent=Mw.prototype.extent;Mw.prototype.resolution=Mw.prototype.resolution;Mw.prototype.data=Mw.prototype.data;t("ol.source.Source",Tt);Tt.prototype.getAttributions=Tt.prototype.xa;Tt.prototype.getLogo=Tt.prototype.wa;Tt.prototype.getProjection=Tt.prototype.ya;Tt.prototype.getState=Tt.prototype.V;Tt.prototype.refresh=Tt.prototype.va;Tt.prototype.setAttributions=Tt.prototype.ua;t("ol.source.Stamen",Pw);t("ol.source.Tile",iw); -iw.prototype.getTileGrid=iw.prototype.ab;lw.prototype.tile=lw.prototype.tile;t("ol.source.TileArcGISRest",Tw);Tw.prototype.getParams=Tw.prototype.v;Tw.prototype.updateParams=Tw.prototype.A;t("ol.source.TileDebug",Vw);t("ol.source.TileImage",W);W.prototype.setRenderReprojectionEdges=W.prototype.Ob;W.prototype.setTileGridForProjection=W.prototype.Pb;t("ol.source.TileJSON",Xw);Xw.prototype.getTileJSON=Xw.prototype.kl;t("ol.source.TileUTFGrid",Yw);Yw.prototype.getTemplate=Yw.prototype.hl; -Yw.prototype.forDataAtCoordinateAndResolution=Yw.prototype.vk;t("ol.source.TileWMS",bx);bx.prototype.getGetFeatureInfoUrl=bx.prototype.vo;bx.prototype.getParams=bx.prototype.wo;bx.prototype.updateParams=bx.prototype.xo;mw.prototype.getTileLoadFunction=mw.prototype.ob;mw.prototype.getTileUrlFunction=mw.prototype.qb;mw.prototype.getUrls=mw.prototype.rb;mw.prototype.setTileLoadFunction=mw.prototype.wb;mw.prototype.setTileUrlFunction=mw.prototype.bb;mw.prototype.setUrl=mw.prototype.ib; -mw.prototype.setUrls=mw.prototype.cb;t("ol.source.Vector",T);T.prototype.addFeature=T.prototype.zb;T.prototype.addFeatures=T.prototype.gd;T.prototype.clear=T.prototype.clear;T.prototype.forEachFeature=T.prototype.kh;T.prototype.forEachFeatureInExtent=T.prototype.bc;T.prototype.forEachFeatureIntersectingExtent=T.prototype.lh;T.prototype.getFeaturesCollection=T.prototype.th;T.prototype.getFeatures=T.prototype.We;T.prototype.getFeaturesAtCoordinate=T.prototype.sh;T.prototype.getFeaturesInExtent=T.prototype.Pf; -T.prototype.getClosestFeatureToCoordinate=T.prototype.oh;T.prototype.getExtent=T.prototype.D;T.prototype.getFeatureById=T.prototype.rh;T.prototype.getFormat=T.prototype.Gi;T.prototype.getUrl=T.prototype.Hi;T.prototype.removeFeature=T.prototype.Db;$t.prototype.feature=$t.prototype.feature;t("ol.source.VectorTile",ix);t("ol.source.WMTS",Y);Y.prototype.getDimensions=Y.prototype.Ik;Y.prototype.getFormat=Y.prototype.yo;Y.prototype.getLayer=Y.prototype.zo;Y.prototype.getMatrixSet=Y.prototype.Vk; -Y.prototype.getRequestEncoding=Y.prototype.fl;Y.prototype.getStyle=Y.prototype.Ao;Y.prototype.getVersion=Y.prototype.ml;Y.prototype.updateDimensions=Y.prototype.jq; -t("ol.source.WMTS.optionsFromCapabilities",function(a,b){var c=ia(a.Contents.Layer,function(a){return a.Identifier==b.layer});if(null===c)return null;var d=a.Contents.TileMatrixSet,e,f,g;e=1<c.TileMatrixSetLink.length?"projection"in b?ma(c.TileMatrixSetLink,function(a){var c=ia(d,function(b){return b.Identifier==a.TileMatrixSet}).SupportedCRS.replace(/urn:ogc:def:crs:(\w+):(.*:)?(\w+)$/,"$1:$3"),e=Tb(c),f=Tb(b.projection);return e&&f?bc(e,f):c==b.projection}):ma(c.TileMatrixSetLink,function(a){return a.TileMatrixSet== -b.matrixSet}):0;0>e&&(e=0);f=c.TileMatrixSetLink[e].TileMatrixSet;g=c.TileMatrixSetLink[e].TileMatrixSetLimits;var h=c.Format[0];"format"in b&&(h=b.format);e=ma(c.Style,function(a){return"style"in b?a.Title==b.style:a.isDefault});0>e&&(e=0);e=c.Style[e].Identifier;var l={};"Dimension"in c&&c.Dimension.forEach(function(a){var b=a.Identifier,c=a.Default;void 0===c&&(c=a.Value[0]);l[b]=c});var m=ia(a.Contents.TileMatrixSet,function(a){return a.Identifier==f}),n;n="projection"in b?Tb(b.projection):Tb(m.SupportedCRS.replace(/urn:ogc:def:crs:(\w+):(.*:)?(\w+)$/, -"$1:$3"));var p=c.WGS84BoundingBox,q,r;void 0!==p&&(r=Tb("EPSG:4326").D(),r=p[0]==r[0]&&p[2]==r[2],q=gc(p,"EPSG:4326",n),(p=n.D())&&(Ua(p,q)||(q=void 0)));g=kx(m,q,g);var v=[],m=b.requestEncoding,m=void 0!==m?m:"";if("OperationsMetadata"in a&&"GetTile"in a.OperationsMetadata){q=a.OperationsMetadata.GetTile.DCP.HTTP.Get;for(var p=0,x=q.length;p<x;++p){var y=ia(q[p].Constraint,function(a){return"GetEncoding"==a.name}).AllowedValues.Value;""===m&&(m=y[0]);if("KVP"===m)fa(y,"KVP")&&v.push(q[p].href); -else break}}v.length||(m="REST",c.ResourceURL.forEach(function(a){"tile"===a.resourceType&&(h=a.format,v.push(a.template))}));return{urls:v,layer:b.layer,matrixSet:f,format:h,projection:n,requestEncoding:m,tileGrid:g,style:e,dimensions:l,wrapX:r,crossOrigin:b.crossOrigin}});t("ol.source.XYZ",sw);t("ol.source.Zoomify",mx);Oh.prototype.vectorContext=Oh.prototype.vectorContext;Oh.prototype.frameState=Oh.prototype.frameState;Oh.prototype.context=Oh.prototype.context;Oh.prototype.glContext=Oh.prototype.glContext; -jq.prototype.get=jq.prototype.get;jq.prototype.getExtent=jq.prototype.D;jq.prototype.getGeometry=jq.prototype.U;jq.prototype.getProperties=jq.prototype.Nn;jq.prototype.getType=jq.prototype.S;t("ol.render.VectorContext",Th);kk.prototype.setStyle=kk.prototype.td;kk.prototype.drawGeometry=kk.prototype.oc;kk.prototype.drawFeature=kk.prototype.te;Uh.prototype.drawCircle=Uh.prototype.ac;Uh.prototype.setStyle=Uh.prototype.td;Uh.prototype.drawGeometry=Uh.prototype.oc;Uh.prototype.drawFeature=Uh.prototype.te; -t("ol.proj.common.add",hc);t("ol.proj.Projection",zb);zb.prototype.getCode=zb.prototype.Fk;zb.prototype.getExtent=zb.prototype.D;zb.prototype.getUnits=zb.prototype.Kb;zb.prototype.getMetersPerUnit=zb.prototype.uc;zb.prototype.getWorldExtent=zb.prototype.ol;zb.prototype.isGlobal=zb.prototype.Zl;zb.prototype.setGlobal=zb.prototype.Qp;zb.prototype.setExtent=zb.prototype.Mn;zb.prototype.setWorldExtent=zb.prototype.$p;zb.prototype.setGetPointResolution=zb.prototype.Pp; -t("ol.proj.Units.METERS_PER_UNIT",xb);t("ol.layer.Base",ph);ph.prototype.getExtent=ph.prototype.D;ph.prototype.getMaxResolution=ph.prototype.hc;ph.prototype.getMinResolution=ph.prototype.ic;ph.prototype.getOpacity=ph.prototype.jc;ph.prototype.getVisible=ph.prototype.Lb;ph.prototype.getZIndex=ph.prototype.Aa;ph.prototype.setExtent=ph.prototype.xc;ph.prototype.setMaxResolution=ph.prototype.Cc;ph.prototype.setMinResolution=ph.prototype.Dc;ph.prototype.setOpacity=ph.prototype.yc; -ph.prototype.setVisible=ph.prototype.zc;ph.prototype.setZIndex=ph.prototype.Xb;t("ol.layer.Group",rh);rh.prototype.getLayers=rh.prototype.sd;rh.prototype.setLayers=rh.prototype.pi;t("ol.layer.Heatmap",U);U.prototype.getBlur=U.prototype.nh;U.prototype.getGradient=U.prototype.uh;U.prototype.getRadius=U.prototype.ri;U.prototype.setBlur=U.prototype.ej;U.prototype.setGradient=U.prototype.kj;U.prototype.setRadius=U.prototype.Zc;t("ol.layer.Image",Mv);Mv.prototype.getSource=Mv.prototype.ka; -t("ol.layer.Layer",th);th.prototype.getSource=th.prototype.ka;th.prototype.setMap=th.prototype.setMap;th.prototype.setSource=th.prototype.ad;t("ol.layer.Tile",Vv);Vv.prototype.getPreload=Vv.prototype.Sd;Vv.prototype.getSource=Vv.prototype.ka;Vv.prototype.setPreload=Vv.prototype.si;Vv.prototype.getUseInterimTilesOnError=Vv.prototype.Wd;Vv.prototype.setUseInterimTilesOnError=Vv.prototype.ti;t("ol.layer.Vector",S);S.prototype.getSource=S.prototype.ka;S.prototype.getStyle=S.prototype.C; -S.prototype.getStyleFunction=S.prototype.G;S.prototype.setStyle=S.prototype.f;t("ol.layer.VectorTile",V);V.prototype.getPreload=V.prototype.Sd;V.prototype.getUseInterimTilesOnError=V.prototype.Wd;V.prototype.setPreload=V.prototype.ui;V.prototype.setUseInterimTilesOnError=V.prototype.vi;t("ol.interaction.DoubleClickZoom",og);t("ol.interaction.DoubleClickZoom.handleEvent",pg);t("ol.interaction.DragAndDrop",Ms);t("ol.interaction.DragAndDrop.handleEvent",jf);Ps.prototype.features=Ps.prototype.features; -Ps.prototype.file=Ps.prototype.file;Ps.prototype.projection=Ps.prototype.projection;t("ol.interaction.DragBox",Og);Og.prototype.getGeometry=Og.prototype.U;Tg.prototype.coordinate=Tg.prototype.coordinate;Tg.prototype.mapBrowserEvent=Tg.prototype.mapBrowserEvent;t("ol.interaction.DragPan",Dg);t("ol.interaction.DragRotate",Hg);t("ol.interaction.DragRotateAndZoom",Rs);t("ol.interaction.DragZoom",Xg);t("ol.interaction.Draw",cu);t("ol.interaction.Draw.handleEvent",eu);cu.prototype.removeLastPoint=cu.prototype.Ep; -cu.prototype.finishDrawing=cu.prototype.Qd;cu.prototype.extend=cu.prototype.nn;t("ol.interaction.Draw.createRegularPolygon",function(a,b){return function(c,d){var e=c[0],f=c[1],g=Math.sqrt(ef(e,f)),h=d?d:Wf(new vs(e),a);Xf(h,e,g,b?b:Math.atan((f[1]-e[1])/(f[0]-e[0])));return h}});t("ol.interaction.Draw.createBox",function(){return function(a,b){var c=Ia(a),d=b||new F(null);d.pa([[cb(c),db(c),eb(c),fb(c),cb(c)]]);return d}});su.prototype.feature=su.prototype.feature;t("ol.interaction.Extent",tu); -tu.prototype.getExtent=tu.prototype.D;tu.prototype.setExtent=tu.prototype.f;Eu.prototype.extent_=Eu.prototype.b;t("ol.interaction.Interaction",kg);kg.prototype.getActive=kg.prototype.c;kg.prototype.getMap=kg.prototype.i;kg.prototype.setActive=kg.prototype.Ia;t("ol.interaction.KeyboardPan",Yg);t("ol.interaction.KeyboardPan.handleEvent",Zg);t("ol.interaction.KeyboardZoom",$g);t("ol.interaction.KeyboardZoom.handleEvent",ah);t("ol.interaction.Modify",Gu);t("ol.interaction.Modify.handleEvent",Ju); -Gu.prototype.removePoint=Gu.prototype.cj;Ou.prototype.features=Ou.prototype.features;Ou.prototype.mapBrowserEvent=Ou.prototype.mapBrowserEvent;t("ol.interaction.MouseWheelZoom",bh);t("ol.interaction.MouseWheelZoom.handleEvent",ch);bh.prototype.setMouseAnchor=bh.prototype.T;t("ol.interaction.PinchRotate",fh);t("ol.interaction.PinchZoom",jh);t("ol.interaction.Pointer",Ag);t("ol.interaction.Pointer.handleEvent",Bg);t("ol.interaction.Select",Wu);Wu.prototype.getFeatures=Wu.prototype.zn; -Wu.prototype.getHitTolerance=Wu.prototype.An;Wu.prototype.getLayer=Wu.prototype.Bn;t("ol.interaction.Select.handleEvent",Xu);Wu.prototype.setHitTolerance=Wu.prototype.Dn;Wu.prototype.setMap=Wu.prototype.setMap;Zu.prototype.selected=Zu.prototype.selected;Zu.prototype.deselected=Zu.prototype.deselected;Zu.prototype.mapBrowserEvent=Zu.prototype.mapBrowserEvent;t("ol.interaction.Snap",av);av.prototype.addFeature=av.prototype.zb;av.prototype.removeFeature=av.prototype.Db;t("ol.interaction.Translate",ev); -ev.prototype.getHitTolerance=ev.prototype.I;ev.prototype.setHitTolerance=ev.prototype.Z;kv.prototype.features=kv.prototype.features;kv.prototype.coordinate=kv.prototype.coordinate;t("ol.geom.Circle",vs);vs.prototype.clone=vs.prototype.clone;vs.prototype.getCenter=vs.prototype.za;vs.prototype.getRadius=vs.prototype.Yd;vs.prototype.getType=vs.prototype.S;vs.prototype.intersectsExtent=vs.prototype.Ya;vs.prototype.setCenter=vs.prototype.lb;vs.prototype.setCenterAndRadius=vs.prototype.Gg; -vs.prototype.setRadius=vs.prototype.Zc;vs.prototype.transform=vs.prototype.tb;t("ol.geom.Geometry",lf);lf.prototype.getClosestPoint=lf.prototype.Ab;lf.prototype.intersectsCoordinate=lf.prototype.sb;lf.prototype.getExtent=lf.prototype.D;lf.prototype.rotate=lf.prototype.rotate;lf.prototype.scale=lf.prototype.scale;lf.prototype.simplify=lf.prototype.Qb;lf.prototype.transform=lf.prototype.tb;t("ol.geom.GeometryCollection",sm);sm.prototype.clone=sm.prototype.clone;sm.prototype.getGeometries=sm.prototype.Qf; -sm.prototype.getType=sm.prototype.S;sm.prototype.intersectsExtent=sm.prototype.Ya;sm.prototype.setGeometries=sm.prototype.jj;sm.prototype.applyTransform=sm.prototype.Fc;sm.prototype.translate=sm.prototype.translate;t("ol.geom.LinearRing",Gf);Gf.prototype.clone=Gf.prototype.clone;Gf.prototype.getArea=Gf.prototype.jn;Gf.prototype.getCoordinates=Gf.prototype.W;Gf.prototype.getType=Gf.prototype.S;Gf.prototype.setCoordinates=Gf.prototype.pa;t("ol.geom.LineString",N);N.prototype.appendCoordinate=N.prototype.ik; -N.prototype.clone=N.prototype.clone;N.prototype.forEachSegment=N.prototype.yk;N.prototype.getCoordinateAtM=N.prototype.gn;N.prototype.getCoordinates=N.prototype.W;N.prototype.getCoordinateAt=N.prototype.ph;N.prototype.getLength=N.prototype.hn;N.prototype.getType=N.prototype.S;N.prototype.intersectsExtent=N.prototype.Ya;N.prototype.setCoordinates=N.prototype.pa;t("ol.geom.MultiLineString",O);O.prototype.appendLineString=O.prototype.jk;O.prototype.clone=O.prototype.clone; -O.prototype.getCoordinateAtM=O.prototype.kn;O.prototype.getCoordinates=O.prototype.W;O.prototype.getLineString=O.prototype.Tk;O.prototype.getLineStrings=O.prototype.Nc;O.prototype.getType=O.prototype.S;O.prototype.intersectsExtent=O.prototype.Ya;O.prototype.setCoordinates=O.prototype.pa;t("ol.geom.MultiPoint",P);P.prototype.appendPoint=P.prototype.lk;P.prototype.clone=P.prototype.clone;P.prototype.getCoordinates=P.prototype.W;P.prototype.getPoint=P.prototype.dl;P.prototype.getPoints=P.prototype.Zd; -P.prototype.getType=P.prototype.S;P.prototype.intersectsExtent=P.prototype.Ya;P.prototype.setCoordinates=P.prototype.pa;t("ol.geom.MultiPolygon",Q);Q.prototype.appendPolygon=Q.prototype.mk;Q.prototype.clone=Q.prototype.clone;Q.prototype.getArea=Q.prototype.ln;Q.prototype.getCoordinates=Q.prototype.W;Q.prototype.getInteriorPoints=Q.prototype.Pk;Q.prototype.getPolygon=Q.prototype.el;Q.prototype.getPolygons=Q.prototype.md;Q.prototype.getType=Q.prototype.S;Q.prototype.intersectsExtent=Q.prototype.Ya; -Q.prototype.setCoordinates=Q.prototype.pa;t("ol.geom.Point",E);E.prototype.clone=E.prototype.clone;E.prototype.getCoordinates=E.prototype.W;E.prototype.getType=E.prototype.S;E.prototype.intersectsExtent=E.prototype.Ya;E.prototype.setCoordinates=E.prototype.pa;t("ol.geom.Polygon",F);F.prototype.appendLinearRing=F.prototype.kk;F.prototype.clone=F.prototype.clone;F.prototype.getArea=F.prototype.mn;F.prototype.getCoordinates=F.prototype.W;F.prototype.getInteriorPoint=F.prototype.Ok; -F.prototype.getLinearRingCount=F.prototype.Uk;F.prototype.getLinearRing=F.prototype.vh;F.prototype.getLinearRings=F.prototype.Oc;F.prototype.getType=F.prototype.S;F.prototype.intersectsExtent=F.prototype.Ya;F.prototype.setCoordinates=F.prototype.pa;t("ol.geom.Polygon.circular",Uf);t("ol.geom.Polygon.fromExtent",Vf);t("ol.geom.Polygon.fromCircle",Wf);t("ol.geom.SimpleGeometry",of);of.prototype.getFirstCoordinate=of.prototype.cc;of.prototype.getLastCoordinate=of.prototype.dc; -of.prototype.getLayout=of.prototype.ec;of.prototype.applyTransform=of.prototype.Fc;of.prototype.translate=of.prototype.translate;t("ol.format.EsriJSON",Ql);Ql.prototype.readFeature=Ql.prototype.Vb;Ql.prototype.readFeatures=Ql.prototype.Pa;Ql.prototype.readGeometry=Ql.prototype.Xc;Ql.prototype.readProjection=Ql.prototype.jb;Ql.prototype.writeGeometry=Ql.prototype.ed;Ql.prototype.writeGeometryObject=Ql.prototype.ie;Ql.prototype.writeFeature=Ql.prototype.Dd;Ql.prototype.writeFeatureObject=Ql.prototype.dd; -Ql.prototype.writeFeatures=Ql.prototype.Yb;Ql.prototype.writeFeaturesObject=Ql.prototype.ge;t("ol.format.Feature",El);t("ol.format.filter.and",qm);t("ol.format.filter.or",function(a){var b=[null].concat(Array.prototype.slice.call(arguments));return new (Function.prototype.bind.apply(om,b))});t("ol.format.filter.not",function(a){return new mm(a)});t("ol.format.filter.bbox",rm);t("ol.format.filter.intersects",function(a,b,c){return new gm(a,b,c)}); -t("ol.format.filter.within",function(a,b,c){return new pm(a,b,c)});t("ol.format.filter.equalTo",function(a,b,c){return new cm(a,b,c)});t("ol.format.filter.notEqualTo",function(a,b,c){return new nm(a,b,c)});t("ol.format.filter.lessThan",function(a,b){return new km(a,b)});t("ol.format.filter.lessThanOrEqualTo",function(a,b){return new lm(a,b)});t("ol.format.filter.greaterThan",function(a,b){return new dm(a,b)});t("ol.format.filter.greaterThanOrEqualTo",function(a,b){return new em(a,b)}); -t("ol.format.filter.isNull",function(a){return new jm(a)});t("ol.format.filter.between",function(a,b,c){return new hm(a,b,c)});t("ol.format.filter.like",function(a,b,c,d,e,f){return new im(a,b,c,d,e,f)});t("ol.format.GeoJSON",wm);wm.prototype.readFeature=wm.prototype.Vb;wm.prototype.readFeatures=wm.prototype.Pa;wm.prototype.readGeometry=wm.prototype.Xc;wm.prototype.readProjection=wm.prototype.jb;wm.prototype.writeFeature=wm.prototype.Dd;wm.prototype.writeFeatureObject=wm.prototype.dd; -wm.prototype.writeFeatures=wm.prototype.Yb;wm.prototype.writeFeaturesObject=wm.prototype.ge;wm.prototype.writeGeometry=wm.prototype.ed;wm.prototype.writeGeometryObject=wm.prototype.ie;t("ol.format.GML",Rm);Rm.prototype.writeFeatures=Rm.prototype.Yb;Rm.prototype.writeFeaturesNode=Rm.prototype.Zb;t("ol.format.GML2",$m);t("ol.format.GML3",Rm);Rm.prototype.writeGeometryNode=Rm.prototype.he;Rm.prototype.writeFeatures=Rm.prototype.Yb;Rm.prototype.writeFeaturesNode=Rm.prototype.Zb; -Em.prototype.readFeatures=Em.prototype.Pa;t("ol.format.GPX",ln);ln.prototype.readFeature=ln.prototype.Vb;ln.prototype.readFeatures=ln.prototype.Pa;ln.prototype.readProjection=ln.prototype.jb;ln.prototype.writeFeatures=ln.prototype.Yb;ln.prototype.writeFeaturesNode=ln.prototype.Zb;t("ol.format.IGC",Wn);Wn.prototype.readFeature=Wn.prototype.Vb;Wn.prototype.readFeatures=Wn.prototype.Pa;Wn.prototype.readProjection=Wn.prototype.jb;t("ol.format.KML",fo);fo.prototype.readFeature=fo.prototype.Vb; -fo.prototype.readFeatures=fo.prototype.Pa;fo.prototype.readName=fo.prototype.sp;fo.prototype.readNetworkLinks=fo.prototype.tp;fo.prototype.readRegion=fo.prototype.wp;fo.prototype.readRegionFromNode=fo.prototype.jf;fo.prototype.readProjection=fo.prototype.jb;fo.prototype.writeFeatures=fo.prototype.Yb;fo.prototype.writeFeaturesNode=fo.prototype.Zb;t("ol.format.MVT",kq);kq.prototype.readFeatures=kq.prototype.Pa;kq.prototype.readProjection=kq.prototype.jb;kq.prototype.setLayers=kq.prototype.fn; -t("ol.format.OSMXML",mq);mq.prototype.readFeatures=mq.prototype.Pa;mq.prototype.readProjection=mq.prototype.jb;t("ol.format.Polyline",Mq);t("ol.format.Polyline.encodeDeltas",Nq);t("ol.format.Polyline.decodeDeltas",Pq);t("ol.format.Polyline.encodeFloats",Oq);t("ol.format.Polyline.decodeFloats",Qq);Mq.prototype.readFeature=Mq.prototype.Vb;Mq.prototype.readFeatures=Mq.prototype.Pa;Mq.prototype.readGeometry=Mq.prototype.Xc;Mq.prototype.readProjection=Mq.prototype.jb;Mq.prototype.writeGeometry=Mq.prototype.ed; -t("ol.format.TopoJSON",Rq);Rq.prototype.readFeatures=Rq.prototype.Pa;Rq.prototype.readProjection=Rq.prototype.jb;t("ol.format.WFS",Xq);Xq.prototype.readFeatures=Xq.prototype.Pa;Xq.prototype.readTransactionResponse=Xq.prototype.j;Xq.prototype.readFeatureCollectionMetadata=Xq.prototype.f;t("ol.format.WFS.writeFilter",function(a){var b=kl("http://www.opengis.net/ogc","Filter");Bl({node:b},kr,wl(a.mc),[a],[]);return b});Xq.prototype.writeGetFeature=Xq.prototype.o;Xq.prototype.writeTransaction=Xq.prototype.u; -Xq.prototype.readProjection=Xq.prototype.jb;t("ol.format.WKT",pr);pr.prototype.readFeature=pr.prototype.Vb;pr.prototype.readFeatures=pr.prototype.Pa;pr.prototype.readGeometry=pr.prototype.Xc;pr.prototype.writeFeature=pr.prototype.Dd;pr.prototype.writeFeatures=pr.prototype.Yb;pr.prototype.writeGeometry=pr.prototype.ed;t("ol.format.WMSCapabilities",Ir);Ir.prototype.read=Ir.prototype.read;t("ol.format.WMSGetFeatureInfo",es);es.prototype.readFeatures=es.prototype.Pa;t("ol.format.WMTSCapabilities",fs); -fs.prototype.read=fs.prototype.read;t("ol.format.filter.And",Zl);t("ol.format.filter.Bbox",$l);t("ol.format.filter.Comparison",am);t("ol.format.filter.ComparisonBinary",bm);t("ol.format.filter.EqualTo",cm);t("ol.format.filter.Filter",Xl);t("ol.format.filter.GreaterThan",dm);t("ol.format.filter.GreaterThanOrEqualTo",em);t("ol.format.filter.Intersects",gm);t("ol.format.filter.IsBetween",hm);t("ol.format.filter.IsLike",im);t("ol.format.filter.IsNull",jm);t("ol.format.filter.LessThan",km); -t("ol.format.filter.LessThanOrEqualTo",lm);t("ol.format.filter.Not",mm);t("ol.format.filter.NotEqualTo",nm);t("ol.format.filter.Or",om);t("ol.format.filter.Spatial",fm);t("ol.format.filter.Within",pm);t("ol.events.condition.altKeyOnly",function(a){a=a.originalEvent;return a.altKey&&!(a.metaKey||a.ctrlKey)&&!a.shiftKey});t("ol.events.condition.altShiftKeysOnly",qg);t("ol.events.condition.always",jf);t("ol.events.condition.click",function(a){return"click"==a.type});t("ol.events.condition.never",kf); -t("ol.events.condition.pointerMove",sg);t("ol.events.condition.singleClick",tg);t("ol.events.condition.doubleClick",function(a){return"dblclick"==a.type});t("ol.events.condition.noModifierKeys",vg);t("ol.events.condition.platformModifierKeyOnly",function(a){a=a.originalEvent;return!a.altKey&&(Sd?a.metaKey:a.ctrlKey)&&!a.shiftKey});t("ol.events.condition.shiftKeyOnly",wg);t("ol.events.condition.targetNotEditable",xg);t("ol.events.condition.mouseOnly",yg);t("ol.events.condition.primaryAction",zg); -Lc.prototype.type=Lc.prototype.type;Lc.prototype.target=Lc.prototype.target;Lc.prototype.preventDefault=Lc.prototype.preventDefault;Lc.prototype.stopPropagation=Lc.prototype.stopPropagation;t("ol.control.Attribution",ld);t("ol.control.Attribution.render",md);ld.prototype.getCollapsible=ld.prototype.Om;ld.prototype.setCollapsible=ld.prototype.Rm;ld.prototype.setCollapsed=ld.prototype.Qm;ld.prototype.getCollapsed=ld.prototype.Nm;t("ol.control.Control",kd);kd.prototype.getMap=kd.prototype.f; -kd.prototype.setMap=kd.prototype.setMap;kd.prototype.setTarget=kd.prototype.i;t("ol.control.FullScreen",wd);t("ol.control.MousePosition",Bd);t("ol.control.MousePosition.render",Cd);Bd.prototype.getCoordinateFormat=Bd.prototype.qh;Bd.prototype.getProjection=Bd.prototype.Sh;Bd.prototype.setCoordinateFormat=Bd.prototype.fj;Bd.prototype.setProjection=Bd.prototype.Th;t("ol.control.OverviewMap",Bk);t("ol.control.OverviewMap.render",Ck);Bk.prototype.getCollapsible=Bk.prototype.Um; -Bk.prototype.setCollapsible=Bk.prototype.Xm;Bk.prototype.setCollapsed=Bk.prototype.Wm;Bk.prototype.getCollapsed=Bk.prototype.Tm;Bk.prototype.getOverviewMap=Bk.prototype.bl;t("ol.control.Rotate",sd);t("ol.control.Rotate.render",td);t("ol.control.ScaleLine",Gk);Gk.prototype.getUnits=Gk.prototype.Kb;t("ol.control.ScaleLine.render",Hk);Gk.prototype.setUnits=Gk.prototype.G;t("ol.control.Zoom",ud);t("ol.control.ZoomSlider",Lk);t("ol.control.ZoomSlider.render",Nk);t("ol.control.ZoomToExtent",Qk); -Qc.prototype.changed=Qc.prototype.s;Qc.prototype.dispatchEvent=Qc.prototype.b;Qc.prototype.getRevision=Qc.prototype.L;Qc.prototype.on=Qc.prototype.J;Qc.prototype.once=Qc.prototype.once;Qc.prototype.un=Qc.prototype.K;D.prototype.get=D.prototype.get;D.prototype.getKeys=D.prototype.P;D.prototype.getProperties=D.prototype.M;D.prototype.set=D.prototype.set;D.prototype.setProperties=D.prototype.H;D.prototype.unset=D.prototype.R;D.prototype.changed=D.prototype.s;D.prototype.dispatchEvent=D.prototype.b; -D.prototype.getRevision=D.prototype.L;D.prototype.on=D.prototype.J;D.prototype.once=D.prototype.once;D.prototype.un=D.prototype.K;Yc.prototype.type=Yc.prototype.type;Yc.prototype.target=Yc.prototype.target;Yc.prototype.preventDefault=Yc.prototype.preventDefault;Yc.prototype.stopPropagation=Yc.prototype.stopPropagation;Rk.prototype.get=Rk.prototype.get;Rk.prototype.getKeys=Rk.prototype.P;Rk.prototype.getProperties=Rk.prototype.M;Rk.prototype.set=Rk.prototype.set;Rk.prototype.setProperties=Rk.prototype.H; -Rk.prototype.unset=Rk.prototype.R;Rk.prototype.changed=Rk.prototype.s;Rk.prototype.dispatchEvent=Rk.prototype.b;Rk.prototype.getRevision=Rk.prototype.L;Rk.prototype.on=Rk.prototype.J;Rk.prototype.once=Rk.prototype.once;Rk.prototype.un=Rk.prototype.K;I.prototype.get=I.prototype.get;I.prototype.getKeys=I.prototype.P;I.prototype.getProperties=I.prototype.M;I.prototype.set=I.prototype.set;I.prototype.setProperties=I.prototype.H;I.prototype.unset=I.prototype.R;I.prototype.changed=I.prototype.s; -I.prototype.dispatchEvent=I.prototype.b;I.prototype.getRevision=I.prototype.L;I.prototype.on=I.prototype.J;I.prototype.once=I.prototype.once;I.prototype.un=I.prototype.K;us.prototype.get=us.prototype.get;us.prototype.getKeys=us.prototype.P;us.prototype.getProperties=us.prototype.M;us.prototype.set=us.prototype.set;us.prototype.setProperties=us.prototype.H;us.prototype.unset=us.prototype.R;us.prototype.changed=us.prototype.s;us.prototype.dispatchEvent=us.prototype.b;us.prototype.getRevision=us.prototype.L; -us.prototype.on=us.prototype.J;us.prototype.once=us.prototype.once;us.prototype.un=us.prototype.K;Ks.prototype.getTileCoord=Ks.prototype.i;Ks.prototype.load=Ks.prototype.load;H.prototype.get=H.prototype.get;H.prototype.getKeys=H.prototype.P;H.prototype.getProperties=H.prototype.M;H.prototype.set=H.prototype.set;H.prototype.setProperties=H.prototype.H;H.prototype.unset=H.prototype.R;H.prototype.changed=H.prototype.s;H.prototype.dispatchEvent=H.prototype.b;H.prototype.getRevision=H.prototype.L; -H.prototype.on=H.prototype.J;H.prototype.once=H.prototype.once;H.prototype.un=H.prototype.K;Gd.prototype.type=Gd.prototype.type;Gd.prototype.target=Gd.prototype.target;Gd.prototype.preventDefault=Gd.prototype.preventDefault;Gd.prototype.stopPropagation=Gd.prototype.stopPropagation;Hd.prototype.map=Hd.prototype.map;Hd.prototype.frameState=Hd.prototype.frameState;Hd.prototype.type=Hd.prototype.type;Hd.prototype.target=Hd.prototype.target;Hd.prototype.preventDefault=Hd.prototype.preventDefault; -Hd.prototype.stopPropagation=Hd.prototype.stopPropagation;Kd.prototype.originalEvent=Kd.prototype.originalEvent;Kd.prototype.pixel=Kd.prototype.pixel;Kd.prototype.coordinate=Kd.prototype.coordinate;Kd.prototype.dragging=Kd.prototype.dragging;Kd.prototype.preventDefault=Kd.prototype.preventDefault;Kd.prototype.stopPropagation=Kd.prototype.stopPropagation;Kd.prototype.map=Kd.prototype.map;Kd.prototype.frameState=Kd.prototype.frameState;Kd.prototype.type=Kd.prototype.type;Kd.prototype.target=Kd.prototype.target; -Uc.prototype.type=Uc.prototype.type;Uc.prototype.target=Uc.prototype.target;Uc.prototype.preventDefault=Uc.prototype.preventDefault;Uc.prototype.stopPropagation=Uc.prototype.stopPropagation;sk.prototype.get=sk.prototype.get;sk.prototype.getKeys=sk.prototype.P;sk.prototype.getProperties=sk.prototype.M;sk.prototype.set=sk.prototype.set;sk.prototype.setProperties=sk.prototype.H;sk.prototype.unset=sk.prototype.R;sk.prototype.changed=sk.prototype.s;sk.prototype.dispatchEvent=sk.prototype.b; -sk.prototype.getRevision=sk.prototype.L;sk.prototype.on=sk.prototype.J;sk.prototype.once=sk.prototype.once;sk.prototype.un=sk.prototype.K;gx.prototype.getTileCoord=gx.prototype.i;gx.prototype.load=gx.prototype.load;G.prototype.get=G.prototype.get;G.prototype.getKeys=G.prototype.P;G.prototype.getProperties=G.prototype.M;G.prototype.set=G.prototype.set;G.prototype.setProperties=G.prototype.H;G.prototype.unset=G.prototype.R;G.prototype.changed=G.prototype.s;G.prototype.dispatchEvent=G.prototype.b; -G.prototype.getRevision=G.prototype.L;G.prototype.on=G.prototype.J;G.prototype.once=G.prototype.once;G.prototype.un=G.prototype.K;jx.prototype.forEachTileCoord=jx.prototype.mh;jx.prototype.getMaxZoom=jx.prototype.Ni;jx.prototype.getMinZoom=jx.prototype.Oi;jx.prototype.getOrigin=jx.prototype.Uc;jx.prototype.getResolution=jx.prototype.La;jx.prototype.getResolutions=jx.prototype.Pi;jx.prototype.getTileCoordExtent=jx.prototype.Ua;jx.prototype.getTileCoordForCoordAndResolution=jx.prototype.Ae; -jx.prototype.getTileCoordForCoordAndZ=jx.prototype.Xf;jx.prototype.getTileSize=jx.prototype.eb;jx.prototype.getZForResolution=jx.prototype.Qc;Yk.prototype.getOpacity=Yk.prototype.Ye;Yk.prototype.getRotateWithView=Yk.prototype.Ze;Yk.prototype.getRotation=Yk.prototype.$e;Yk.prototype.getScale=Yk.prototype.af;Yk.prototype.getSnapToPixel=Yk.prototype.ze;Yk.prototype.setOpacity=Yk.prototype.vd;Yk.prototype.setRotation=Yk.prototype.bf;Yk.prototype.setScale=Yk.prototype.wd;$k.prototype.clone=$k.prototype.clone; -$k.prototype.getAngle=$k.prototype.Ji;$k.prototype.getFill=$k.prototype.Ca;$k.prototype.getPoints=$k.prototype.Ki;$k.prototype.getRadius=$k.prototype.Li;$k.prototype.getRadius2=$k.prototype.yh;$k.prototype.getStroke=$k.prototype.Da;$k.prototype.getOpacity=$k.prototype.Ye;$k.prototype.getRotateWithView=$k.prototype.Ze;$k.prototype.getRotation=$k.prototype.$e;$k.prototype.getScale=$k.prototype.af;$k.prototype.getSnapToPixel=$k.prototype.ze;$k.prototype.setOpacity=$k.prototype.vd; -$k.prototype.setRotation=$k.prototype.bf;$k.prototype.setScale=$k.prototype.wd;co.prototype.getOpacity=co.prototype.Ye;co.prototype.getRotateWithView=co.prototype.Ze;co.prototype.getRotation=co.prototype.$e;co.prototype.getScale=co.prototype.af;co.prototype.getSnapToPixel=co.prototype.ze;co.prototype.setOpacity=co.prototype.vd;co.prototype.setRotation=co.prototype.bf;co.prototype.setScale=co.prototype.wd;Tt.prototype.get=Tt.prototype.get;Tt.prototype.getKeys=Tt.prototype.P; -Tt.prototype.getProperties=Tt.prototype.M;Tt.prototype.set=Tt.prototype.set;Tt.prototype.setProperties=Tt.prototype.H;Tt.prototype.unset=Tt.prototype.R;Tt.prototype.changed=Tt.prototype.s;Tt.prototype.dispatchEvent=Tt.prototype.b;Tt.prototype.getRevision=Tt.prototype.L;Tt.prototype.on=Tt.prototype.J;Tt.prototype.once=Tt.prototype.once;Tt.prototype.un=Tt.prototype.K;iw.prototype.getAttributions=iw.prototype.xa;iw.prototype.getLogo=iw.prototype.wa;iw.prototype.getProjection=iw.prototype.ya; -iw.prototype.getState=iw.prototype.V;iw.prototype.refresh=iw.prototype.va;iw.prototype.setAttributions=iw.prototype.ua;iw.prototype.get=iw.prototype.get;iw.prototype.getKeys=iw.prototype.P;iw.prototype.getProperties=iw.prototype.M;iw.prototype.set=iw.prototype.set;iw.prototype.setProperties=iw.prototype.H;iw.prototype.unset=iw.prototype.R;iw.prototype.changed=iw.prototype.s;iw.prototype.dispatchEvent=iw.prototype.b;iw.prototype.getRevision=iw.prototype.L;iw.prototype.on=iw.prototype.J; -iw.prototype.once=iw.prototype.once;iw.prototype.un=iw.prototype.K;mw.prototype.getTileGrid=mw.prototype.ab;mw.prototype.refresh=mw.prototype.va;mw.prototype.getAttributions=mw.prototype.xa;mw.prototype.getLogo=mw.prototype.wa;mw.prototype.getProjection=mw.prototype.ya;mw.prototype.getState=mw.prototype.V;mw.prototype.setAttributions=mw.prototype.ua;mw.prototype.get=mw.prototype.get;mw.prototype.getKeys=mw.prototype.P;mw.prototype.getProperties=mw.prototype.M;mw.prototype.set=mw.prototype.set; -mw.prototype.setProperties=mw.prototype.H;mw.prototype.unset=mw.prototype.R;mw.prototype.changed=mw.prototype.s;mw.prototype.dispatchEvent=mw.prototype.b;mw.prototype.getRevision=mw.prototype.L;mw.prototype.on=mw.prototype.J;mw.prototype.once=mw.prototype.once;mw.prototype.un=mw.prototype.K;W.prototype.getTileLoadFunction=W.prototype.ob;W.prototype.getTileUrlFunction=W.prototype.qb;W.prototype.getUrls=W.prototype.rb;W.prototype.setTileLoadFunction=W.prototype.wb;W.prototype.setTileUrlFunction=W.prototype.bb; -W.prototype.setUrl=W.prototype.ib;W.prototype.setUrls=W.prototype.cb;W.prototype.getTileGrid=W.prototype.ab;W.prototype.refresh=W.prototype.va;W.prototype.getAttributions=W.prototype.xa;W.prototype.getLogo=W.prototype.wa;W.prototype.getProjection=W.prototype.ya;W.prototype.getState=W.prototype.V;W.prototype.setAttributions=W.prototype.ua;W.prototype.get=W.prototype.get;W.prototype.getKeys=W.prototype.P;W.prototype.getProperties=W.prototype.M;W.prototype.set=W.prototype.set; -W.prototype.setProperties=W.prototype.H;W.prototype.unset=W.prototype.R;W.prototype.changed=W.prototype.s;W.prototype.dispatchEvent=W.prototype.b;W.prototype.getRevision=W.prototype.L;W.prototype.on=W.prototype.J;W.prototype.once=W.prototype.once;W.prototype.un=W.prototype.K;qw.prototype.setRenderReprojectionEdges=qw.prototype.Ob;qw.prototype.setTileGridForProjection=qw.prototype.Pb;qw.prototype.getTileLoadFunction=qw.prototype.ob;qw.prototype.getTileUrlFunction=qw.prototype.qb; -qw.prototype.getUrls=qw.prototype.rb;qw.prototype.setTileLoadFunction=qw.prototype.wb;qw.prototype.setTileUrlFunction=qw.prototype.bb;qw.prototype.setUrl=qw.prototype.ib;qw.prototype.setUrls=qw.prototype.cb;qw.prototype.getTileGrid=qw.prototype.ab;qw.prototype.refresh=qw.prototype.va;qw.prototype.getAttributions=qw.prototype.xa;qw.prototype.getLogo=qw.prototype.wa;qw.prototype.getProjection=qw.prototype.ya;qw.prototype.getState=qw.prototype.V;qw.prototype.setAttributions=qw.prototype.ua; -qw.prototype.get=qw.prototype.get;qw.prototype.getKeys=qw.prototype.P;qw.prototype.getProperties=qw.prototype.M;qw.prototype.set=qw.prototype.set;qw.prototype.setProperties=qw.prototype.H;qw.prototype.unset=qw.prototype.R;qw.prototype.changed=qw.prototype.s;qw.prototype.dispatchEvent=qw.prototype.b;qw.prototype.getRevision=qw.prototype.L;qw.prototype.on=qw.prototype.J;qw.prototype.once=qw.prototype.once;qw.prototype.un=qw.prototype.K;sw.prototype.setRenderReprojectionEdges=sw.prototype.Ob; -sw.prototype.setTileGridForProjection=sw.prototype.Pb;sw.prototype.getTileLoadFunction=sw.prototype.ob;sw.prototype.getTileUrlFunction=sw.prototype.qb;sw.prototype.getUrls=sw.prototype.rb;sw.prototype.setTileLoadFunction=sw.prototype.wb;sw.prototype.setTileUrlFunction=sw.prototype.bb;sw.prototype.setUrl=sw.prototype.ib;sw.prototype.setUrls=sw.prototype.cb;sw.prototype.getTileGrid=sw.prototype.ab;sw.prototype.refresh=sw.prototype.va;sw.prototype.getAttributions=sw.prototype.xa; -sw.prototype.getLogo=sw.prototype.wa;sw.prototype.getProjection=sw.prototype.ya;sw.prototype.getState=sw.prototype.V;sw.prototype.setAttributions=sw.prototype.ua;sw.prototype.get=sw.prototype.get;sw.prototype.getKeys=sw.prototype.P;sw.prototype.getProperties=sw.prototype.M;sw.prototype.set=sw.prototype.set;sw.prototype.setProperties=sw.prototype.H;sw.prototype.unset=sw.prototype.R;sw.prototype.changed=sw.prototype.s;sw.prototype.dispatchEvent=sw.prototype.b;sw.prototype.getRevision=sw.prototype.L; -sw.prototype.on=sw.prototype.J;sw.prototype.once=sw.prototype.once;sw.prototype.un=sw.prototype.K;tw.prototype.setRenderReprojectionEdges=tw.prototype.Ob;tw.prototype.setTileGridForProjection=tw.prototype.Pb;tw.prototype.getTileLoadFunction=tw.prototype.ob;tw.prototype.getTileUrlFunction=tw.prototype.qb;tw.prototype.getUrls=tw.prototype.rb;tw.prototype.setTileLoadFunction=tw.prototype.wb;tw.prototype.setTileUrlFunction=tw.prototype.bb;tw.prototype.setUrl=tw.prototype.ib;tw.prototype.setUrls=tw.prototype.cb; -tw.prototype.getTileGrid=tw.prototype.ab;tw.prototype.refresh=tw.prototype.va;tw.prototype.getAttributions=tw.prototype.xa;tw.prototype.getLogo=tw.prototype.wa;tw.prototype.getProjection=tw.prototype.ya;tw.prototype.getState=tw.prototype.V;tw.prototype.setAttributions=tw.prototype.ua;tw.prototype.get=tw.prototype.get;tw.prototype.getKeys=tw.prototype.P;tw.prototype.getProperties=tw.prototype.M;tw.prototype.set=tw.prototype.set;tw.prototype.setProperties=tw.prototype.H;tw.prototype.unset=tw.prototype.R; -tw.prototype.changed=tw.prototype.s;tw.prototype.dispatchEvent=tw.prototype.b;tw.prototype.getRevision=tw.prototype.L;tw.prototype.on=tw.prototype.J;tw.prototype.once=tw.prototype.once;tw.prototype.un=tw.prototype.K;T.prototype.getAttributions=T.prototype.xa;T.prototype.getLogo=T.prototype.wa;T.prototype.getProjection=T.prototype.ya;T.prototype.getState=T.prototype.V;T.prototype.refresh=T.prototype.va;T.prototype.setAttributions=T.prototype.ua;T.prototype.get=T.prototype.get;T.prototype.getKeys=T.prototype.P; -T.prototype.getProperties=T.prototype.M;T.prototype.set=T.prototype.set;T.prototype.setProperties=T.prototype.H;T.prototype.unset=T.prototype.R;T.prototype.changed=T.prototype.s;T.prototype.dispatchEvent=T.prototype.b;T.prototype.getRevision=T.prototype.L;T.prototype.on=T.prototype.J;T.prototype.once=T.prototype.once;T.prototype.un=T.prototype.K;X.prototype.addFeature=X.prototype.zb;X.prototype.addFeatures=X.prototype.gd;X.prototype.clear=X.prototype.clear;X.prototype.forEachFeature=X.prototype.kh; -X.prototype.forEachFeatureInExtent=X.prototype.bc;X.prototype.forEachFeatureIntersectingExtent=X.prototype.lh;X.prototype.getFeaturesCollection=X.prototype.th;X.prototype.getFeatures=X.prototype.We;X.prototype.getFeaturesAtCoordinate=X.prototype.sh;X.prototype.getFeaturesInExtent=X.prototype.Pf;X.prototype.getClosestFeatureToCoordinate=X.prototype.oh;X.prototype.getExtent=X.prototype.D;X.prototype.getFeatureById=X.prototype.rh;X.prototype.getFormat=X.prototype.Gi;X.prototype.getUrl=X.prototype.Hi; -X.prototype.removeFeature=X.prototype.Db;X.prototype.getAttributions=X.prototype.xa;X.prototype.getLogo=X.prototype.wa;X.prototype.getProjection=X.prototype.ya;X.prototype.getState=X.prototype.V;X.prototype.refresh=X.prototype.va;X.prototype.setAttributions=X.prototype.ua;X.prototype.get=X.prototype.get;X.prototype.getKeys=X.prototype.P;X.prototype.getProperties=X.prototype.M;X.prototype.set=X.prototype.set;X.prototype.setProperties=X.prototype.H;X.prototype.unset=X.prototype.R; -X.prototype.changed=X.prototype.s;X.prototype.dispatchEvent=X.prototype.b;X.prototype.getRevision=X.prototype.L;X.prototype.on=X.prototype.J;X.prototype.once=X.prototype.once;X.prototype.un=X.prototype.K;zv.prototype.getAttributions=zv.prototype.xa;zv.prototype.getLogo=zv.prototype.wa;zv.prototype.getProjection=zv.prototype.ya;zv.prototype.getState=zv.prototype.V;zv.prototype.refresh=zv.prototype.va;zv.prototype.setAttributions=zv.prototype.ua;zv.prototype.get=zv.prototype.get; -zv.prototype.getKeys=zv.prototype.P;zv.prototype.getProperties=zv.prototype.M;zv.prototype.set=zv.prototype.set;zv.prototype.setProperties=zv.prototype.H;zv.prototype.unset=zv.prototype.R;zv.prototype.changed=zv.prototype.s;zv.prototype.dispatchEvent=zv.prototype.b;zv.prototype.getRevision=zv.prototype.L;zv.prototype.on=zv.prototype.J;zv.prototype.once=zv.prototype.once;zv.prototype.un=zv.prototype.K;Bv.prototype.type=Bv.prototype.type;Bv.prototype.target=Bv.prototype.target; -Bv.prototype.preventDefault=Bv.prototype.preventDefault;Bv.prototype.stopPropagation=Bv.prototype.stopPropagation;zw.prototype.getAttributions=zw.prototype.xa;zw.prototype.getLogo=zw.prototype.wa;zw.prototype.getProjection=zw.prototype.ya;zw.prototype.getState=zw.prototype.V;zw.prototype.refresh=zw.prototype.va;zw.prototype.setAttributions=zw.prototype.ua;zw.prototype.get=zw.prototype.get;zw.prototype.getKeys=zw.prototype.P;zw.prototype.getProperties=zw.prototype.M;zw.prototype.set=zw.prototype.set; -zw.prototype.setProperties=zw.prototype.H;zw.prototype.unset=zw.prototype.R;zw.prototype.changed=zw.prototype.s;zw.prototype.dispatchEvent=zw.prototype.b;zw.prototype.getRevision=zw.prototype.L;zw.prototype.on=zw.prototype.J;zw.prototype.once=zw.prototype.once;zw.prototype.un=zw.prototype.K;Gv.prototype.getAttributions=Gv.prototype.xa;Gv.prototype.getLogo=Gv.prototype.wa;Gv.prototype.getProjection=Gv.prototype.ya;Gv.prototype.getState=Gv.prototype.V;Gv.prototype.refresh=Gv.prototype.va; -Gv.prototype.setAttributions=Gv.prototype.ua;Gv.prototype.get=Gv.prototype.get;Gv.prototype.getKeys=Gv.prototype.P;Gv.prototype.getProperties=Gv.prototype.M;Gv.prototype.set=Gv.prototype.set;Gv.prototype.setProperties=Gv.prototype.H;Gv.prototype.unset=Gv.prototype.R;Gv.prototype.changed=Gv.prototype.s;Gv.prototype.dispatchEvent=Gv.prototype.b;Gv.prototype.getRevision=Gv.prototype.L;Gv.prototype.on=Gv.prototype.J;Gv.prototype.once=Gv.prototype.once;Gv.prototype.un=Gv.prototype.K; -Aw.prototype.getAttributions=Aw.prototype.xa;Aw.prototype.getLogo=Aw.prototype.wa;Aw.prototype.getProjection=Aw.prototype.ya;Aw.prototype.getState=Aw.prototype.V;Aw.prototype.refresh=Aw.prototype.va;Aw.prototype.setAttributions=Aw.prototype.ua;Aw.prototype.get=Aw.prototype.get;Aw.prototype.getKeys=Aw.prototype.P;Aw.prototype.getProperties=Aw.prototype.M;Aw.prototype.set=Aw.prototype.set;Aw.prototype.setProperties=Aw.prototype.H;Aw.prototype.unset=Aw.prototype.R;Aw.prototype.changed=Aw.prototype.s; -Aw.prototype.dispatchEvent=Aw.prototype.b;Aw.prototype.getRevision=Aw.prototype.L;Aw.prototype.on=Aw.prototype.J;Aw.prototype.once=Aw.prototype.once;Aw.prototype.un=Aw.prototype.K;Bw.prototype.getAttributions=Bw.prototype.xa;Bw.prototype.getLogo=Bw.prototype.wa;Bw.prototype.getProjection=Bw.prototype.ya;Bw.prototype.getState=Bw.prototype.V;Bw.prototype.refresh=Bw.prototype.va;Bw.prototype.setAttributions=Bw.prototype.ua;Bw.prototype.get=Bw.prototype.get;Bw.prototype.getKeys=Bw.prototype.P; -Bw.prototype.getProperties=Bw.prototype.M;Bw.prototype.set=Bw.prototype.set;Bw.prototype.setProperties=Bw.prototype.H;Bw.prototype.unset=Bw.prototype.R;Bw.prototype.changed=Bw.prototype.s;Bw.prototype.dispatchEvent=Bw.prototype.b;Bw.prototype.getRevision=Bw.prototype.L;Bw.prototype.on=Bw.prototype.J;Bw.prototype.once=Bw.prototype.once;Bw.prototype.un=Bw.prototype.K;Hv.prototype.getAttributions=Hv.prototype.xa;Hv.prototype.getLogo=Hv.prototype.wa;Hv.prototype.getProjection=Hv.prototype.ya; -Hv.prototype.getState=Hv.prototype.V;Hv.prototype.refresh=Hv.prototype.va;Hv.prototype.setAttributions=Hv.prototype.ua;Hv.prototype.get=Hv.prototype.get;Hv.prototype.getKeys=Hv.prototype.P;Hv.prototype.getProperties=Hv.prototype.M;Hv.prototype.set=Hv.prototype.set;Hv.prototype.setProperties=Hv.prototype.H;Hv.prototype.unset=Hv.prototype.R;Hv.prototype.changed=Hv.prototype.s;Hv.prototype.dispatchEvent=Hv.prototype.b;Hv.prototype.getRevision=Hv.prototype.L;Hv.prototype.on=Hv.prototype.J; -Hv.prototype.once=Hv.prototype.once;Hv.prototype.un=Hv.prototype.K;Cw.prototype.getAttributions=Cw.prototype.xa;Cw.prototype.getLogo=Cw.prototype.wa;Cw.prototype.getProjection=Cw.prototype.ya;Cw.prototype.getState=Cw.prototype.V;Cw.prototype.refresh=Cw.prototype.va;Cw.prototype.setAttributions=Cw.prototype.ua;Cw.prototype.get=Cw.prototype.get;Cw.prototype.getKeys=Cw.prototype.P;Cw.prototype.getProperties=Cw.prototype.M;Cw.prototype.set=Cw.prototype.set;Cw.prototype.setProperties=Cw.prototype.H; -Cw.prototype.unset=Cw.prototype.R;Cw.prototype.changed=Cw.prototype.s;Cw.prototype.dispatchEvent=Cw.prototype.b;Cw.prototype.getRevision=Cw.prototype.L;Cw.prototype.on=Cw.prototype.J;Cw.prototype.once=Cw.prototype.once;Cw.prototype.un=Cw.prototype.K;Gw.prototype.setRenderReprojectionEdges=Gw.prototype.Ob;Gw.prototype.setTileGridForProjection=Gw.prototype.Pb;Gw.prototype.getTileLoadFunction=Gw.prototype.ob;Gw.prototype.getTileUrlFunction=Gw.prototype.qb;Gw.prototype.getUrls=Gw.prototype.rb; -Gw.prototype.setTileLoadFunction=Gw.prototype.wb;Gw.prototype.setTileUrlFunction=Gw.prototype.bb;Gw.prototype.setUrl=Gw.prototype.ib;Gw.prototype.setUrls=Gw.prototype.cb;Gw.prototype.getTileGrid=Gw.prototype.ab;Gw.prototype.refresh=Gw.prototype.va;Gw.prototype.getAttributions=Gw.prototype.xa;Gw.prototype.getLogo=Gw.prototype.wa;Gw.prototype.getProjection=Gw.prototype.ya;Gw.prototype.getState=Gw.prototype.V;Gw.prototype.setAttributions=Gw.prototype.ua;Gw.prototype.get=Gw.prototype.get; -Gw.prototype.getKeys=Gw.prototype.P;Gw.prototype.getProperties=Gw.prototype.M;Gw.prototype.set=Gw.prototype.set;Gw.prototype.setProperties=Gw.prototype.H;Gw.prototype.unset=Gw.prototype.R;Gw.prototype.changed=Gw.prototype.s;Gw.prototype.dispatchEvent=Gw.prototype.b;Gw.prototype.getRevision=Gw.prototype.L;Gw.prototype.on=Gw.prototype.J;Gw.prototype.once=Gw.prototype.once;Gw.prototype.un=Gw.prototype.K;Iw.prototype.getAttributions=Iw.prototype.xa;Iw.prototype.getLogo=Iw.prototype.wa; -Iw.prototype.getProjection=Iw.prototype.ya;Iw.prototype.getState=Iw.prototype.V;Iw.prototype.refresh=Iw.prototype.va;Iw.prototype.setAttributions=Iw.prototype.ua;Iw.prototype.get=Iw.prototype.get;Iw.prototype.getKeys=Iw.prototype.P;Iw.prototype.getProperties=Iw.prototype.M;Iw.prototype.set=Iw.prototype.set;Iw.prototype.setProperties=Iw.prototype.H;Iw.prototype.unset=Iw.prototype.R;Iw.prototype.changed=Iw.prototype.s;Iw.prototype.dispatchEvent=Iw.prototype.b;Iw.prototype.getRevision=Iw.prototype.L; -Iw.prototype.on=Iw.prototype.J;Iw.prototype.once=Iw.prototype.once;Iw.prototype.un=Iw.prototype.K;Mw.prototype.type=Mw.prototype.type;Mw.prototype.target=Mw.prototype.target;Mw.prototype.preventDefault=Mw.prototype.preventDefault;Mw.prototype.stopPropagation=Mw.prototype.stopPropagation;Pw.prototype.setRenderReprojectionEdges=Pw.prototype.Ob;Pw.prototype.setTileGridForProjection=Pw.prototype.Pb;Pw.prototype.getTileLoadFunction=Pw.prototype.ob;Pw.prototype.getTileUrlFunction=Pw.prototype.qb; -Pw.prototype.getUrls=Pw.prototype.rb;Pw.prototype.setTileLoadFunction=Pw.prototype.wb;Pw.prototype.setTileUrlFunction=Pw.prototype.bb;Pw.prototype.setUrl=Pw.prototype.ib;Pw.prototype.setUrls=Pw.prototype.cb;Pw.prototype.getTileGrid=Pw.prototype.ab;Pw.prototype.refresh=Pw.prototype.va;Pw.prototype.getAttributions=Pw.prototype.xa;Pw.prototype.getLogo=Pw.prototype.wa;Pw.prototype.getProjection=Pw.prototype.ya;Pw.prototype.getState=Pw.prototype.V;Pw.prototype.setAttributions=Pw.prototype.ua; -Pw.prototype.get=Pw.prototype.get;Pw.prototype.getKeys=Pw.prototype.P;Pw.prototype.getProperties=Pw.prototype.M;Pw.prototype.set=Pw.prototype.set;Pw.prototype.setProperties=Pw.prototype.H;Pw.prototype.unset=Pw.prototype.R;Pw.prototype.changed=Pw.prototype.s;Pw.prototype.dispatchEvent=Pw.prototype.b;Pw.prototype.getRevision=Pw.prototype.L;Pw.prototype.on=Pw.prototype.J;Pw.prototype.once=Pw.prototype.once;Pw.prototype.un=Pw.prototype.K;lw.prototype.type=lw.prototype.type;lw.prototype.target=lw.prototype.target; -lw.prototype.preventDefault=lw.prototype.preventDefault;lw.prototype.stopPropagation=lw.prototype.stopPropagation;Tw.prototype.setRenderReprojectionEdges=Tw.prototype.Ob;Tw.prototype.setTileGridForProjection=Tw.prototype.Pb;Tw.prototype.getTileLoadFunction=Tw.prototype.ob;Tw.prototype.getTileUrlFunction=Tw.prototype.qb;Tw.prototype.getUrls=Tw.prototype.rb;Tw.prototype.setTileLoadFunction=Tw.prototype.wb;Tw.prototype.setTileUrlFunction=Tw.prototype.bb;Tw.prototype.setUrl=Tw.prototype.ib; -Tw.prototype.setUrls=Tw.prototype.cb;Tw.prototype.getTileGrid=Tw.prototype.ab;Tw.prototype.refresh=Tw.prototype.va;Tw.prototype.getAttributions=Tw.prototype.xa;Tw.prototype.getLogo=Tw.prototype.wa;Tw.prototype.getProjection=Tw.prototype.ya;Tw.prototype.getState=Tw.prototype.V;Tw.prototype.setAttributions=Tw.prototype.ua;Tw.prototype.get=Tw.prototype.get;Tw.prototype.getKeys=Tw.prototype.P;Tw.prototype.getProperties=Tw.prototype.M;Tw.prototype.set=Tw.prototype.set;Tw.prototype.setProperties=Tw.prototype.H; -Tw.prototype.unset=Tw.prototype.R;Tw.prototype.changed=Tw.prototype.s;Tw.prototype.dispatchEvent=Tw.prototype.b;Tw.prototype.getRevision=Tw.prototype.L;Tw.prototype.on=Tw.prototype.J;Tw.prototype.once=Tw.prototype.once;Tw.prototype.un=Tw.prototype.K;Vw.prototype.getTileGrid=Vw.prototype.ab;Vw.prototype.refresh=Vw.prototype.va;Vw.prototype.getAttributions=Vw.prototype.xa;Vw.prototype.getLogo=Vw.prototype.wa;Vw.prototype.getProjection=Vw.prototype.ya;Vw.prototype.getState=Vw.prototype.V; -Vw.prototype.setAttributions=Vw.prototype.ua;Vw.prototype.get=Vw.prototype.get;Vw.prototype.getKeys=Vw.prototype.P;Vw.prototype.getProperties=Vw.prototype.M;Vw.prototype.set=Vw.prototype.set;Vw.prototype.setProperties=Vw.prototype.H;Vw.prototype.unset=Vw.prototype.R;Vw.prototype.changed=Vw.prototype.s;Vw.prototype.dispatchEvent=Vw.prototype.b;Vw.prototype.getRevision=Vw.prototype.L;Vw.prototype.on=Vw.prototype.J;Vw.prototype.once=Vw.prototype.once;Vw.prototype.un=Vw.prototype.K; -Xw.prototype.setRenderReprojectionEdges=Xw.prototype.Ob;Xw.prototype.setTileGridForProjection=Xw.prototype.Pb;Xw.prototype.getTileLoadFunction=Xw.prototype.ob;Xw.prototype.getTileUrlFunction=Xw.prototype.qb;Xw.prototype.getUrls=Xw.prototype.rb;Xw.prototype.setTileLoadFunction=Xw.prototype.wb;Xw.prototype.setTileUrlFunction=Xw.prototype.bb;Xw.prototype.setUrl=Xw.prototype.ib;Xw.prototype.setUrls=Xw.prototype.cb;Xw.prototype.getTileGrid=Xw.prototype.ab;Xw.prototype.refresh=Xw.prototype.va; -Xw.prototype.getAttributions=Xw.prototype.xa;Xw.prototype.getLogo=Xw.prototype.wa;Xw.prototype.getProjection=Xw.prototype.ya;Xw.prototype.getState=Xw.prototype.V;Xw.prototype.setAttributions=Xw.prototype.ua;Xw.prototype.get=Xw.prototype.get;Xw.prototype.getKeys=Xw.prototype.P;Xw.prototype.getProperties=Xw.prototype.M;Xw.prototype.set=Xw.prototype.set;Xw.prototype.setProperties=Xw.prototype.H;Xw.prototype.unset=Xw.prototype.R;Xw.prototype.changed=Xw.prototype.s;Xw.prototype.dispatchEvent=Xw.prototype.b; -Xw.prototype.getRevision=Xw.prototype.L;Xw.prototype.on=Xw.prototype.J;Xw.prototype.once=Xw.prototype.once;Xw.prototype.un=Xw.prototype.K;Yw.prototype.getTileGrid=Yw.prototype.ab;Yw.prototype.refresh=Yw.prototype.va;Yw.prototype.getAttributions=Yw.prototype.xa;Yw.prototype.getLogo=Yw.prototype.wa;Yw.prototype.getProjection=Yw.prototype.ya;Yw.prototype.getState=Yw.prototype.V;Yw.prototype.setAttributions=Yw.prototype.ua;Yw.prototype.get=Yw.prototype.get;Yw.prototype.getKeys=Yw.prototype.P; -Yw.prototype.getProperties=Yw.prototype.M;Yw.prototype.set=Yw.prototype.set;Yw.prototype.setProperties=Yw.prototype.H;Yw.prototype.unset=Yw.prototype.R;Yw.prototype.changed=Yw.prototype.s;Yw.prototype.dispatchEvent=Yw.prototype.b;Yw.prototype.getRevision=Yw.prototype.L;Yw.prototype.on=Yw.prototype.J;Yw.prototype.once=Yw.prototype.once;Yw.prototype.un=Yw.prototype.K;bx.prototype.setRenderReprojectionEdges=bx.prototype.Ob;bx.prototype.setTileGridForProjection=bx.prototype.Pb; -bx.prototype.getTileLoadFunction=bx.prototype.ob;bx.prototype.getTileUrlFunction=bx.prototype.qb;bx.prototype.getUrls=bx.prototype.rb;bx.prototype.setTileLoadFunction=bx.prototype.wb;bx.prototype.setTileUrlFunction=bx.prototype.bb;bx.prototype.setUrl=bx.prototype.ib;bx.prototype.setUrls=bx.prototype.cb;bx.prototype.getTileGrid=bx.prototype.ab;bx.prototype.refresh=bx.prototype.va;bx.prototype.getAttributions=bx.prototype.xa;bx.prototype.getLogo=bx.prototype.wa;bx.prototype.getProjection=bx.prototype.ya; -bx.prototype.getState=bx.prototype.V;bx.prototype.setAttributions=bx.prototype.ua;bx.prototype.get=bx.prototype.get;bx.prototype.getKeys=bx.prototype.P;bx.prototype.getProperties=bx.prototype.M;bx.prototype.set=bx.prototype.set;bx.prototype.setProperties=bx.prototype.H;bx.prototype.unset=bx.prototype.R;bx.prototype.changed=bx.prototype.s;bx.prototype.dispatchEvent=bx.prototype.b;bx.prototype.getRevision=bx.prototype.L;bx.prototype.on=bx.prototype.J;bx.prototype.once=bx.prototype.once; -bx.prototype.un=bx.prototype.K;$t.prototype.type=$t.prototype.type;$t.prototype.target=$t.prototype.target;$t.prototype.preventDefault=$t.prototype.preventDefault;$t.prototype.stopPropagation=$t.prototype.stopPropagation;ix.prototype.getTileLoadFunction=ix.prototype.ob;ix.prototype.getTileUrlFunction=ix.prototype.qb;ix.prototype.getUrls=ix.prototype.rb;ix.prototype.setTileLoadFunction=ix.prototype.wb;ix.prototype.setTileUrlFunction=ix.prototype.bb;ix.prototype.setUrl=ix.prototype.ib; -ix.prototype.setUrls=ix.prototype.cb;ix.prototype.getTileGrid=ix.prototype.ab;ix.prototype.refresh=ix.prototype.va;ix.prototype.getAttributions=ix.prototype.xa;ix.prototype.getLogo=ix.prototype.wa;ix.prototype.getProjection=ix.prototype.ya;ix.prototype.getState=ix.prototype.V;ix.prototype.setAttributions=ix.prototype.ua;ix.prototype.get=ix.prototype.get;ix.prototype.getKeys=ix.prototype.P;ix.prototype.getProperties=ix.prototype.M;ix.prototype.set=ix.prototype.set;ix.prototype.setProperties=ix.prototype.H; -ix.prototype.unset=ix.prototype.R;ix.prototype.changed=ix.prototype.s;ix.prototype.dispatchEvent=ix.prototype.b;ix.prototype.getRevision=ix.prototype.L;ix.prototype.on=ix.prototype.J;ix.prototype.once=ix.prototype.once;ix.prototype.un=ix.prototype.K;Y.prototype.setRenderReprojectionEdges=Y.prototype.Ob;Y.prototype.setTileGridForProjection=Y.prototype.Pb;Y.prototype.getTileLoadFunction=Y.prototype.ob;Y.prototype.getTileUrlFunction=Y.prototype.qb;Y.prototype.getUrls=Y.prototype.rb; -Y.prototype.setTileLoadFunction=Y.prototype.wb;Y.prototype.setTileUrlFunction=Y.prototype.bb;Y.prototype.setUrl=Y.prototype.ib;Y.prototype.setUrls=Y.prototype.cb;Y.prototype.getTileGrid=Y.prototype.ab;Y.prototype.refresh=Y.prototype.va;Y.prototype.getAttributions=Y.prototype.xa;Y.prototype.getLogo=Y.prototype.wa;Y.prototype.getProjection=Y.prototype.ya;Y.prototype.getState=Y.prototype.V;Y.prototype.setAttributions=Y.prototype.ua;Y.prototype.get=Y.prototype.get;Y.prototype.getKeys=Y.prototype.P; -Y.prototype.getProperties=Y.prototype.M;Y.prototype.set=Y.prototype.set;Y.prototype.setProperties=Y.prototype.H;Y.prototype.unset=Y.prototype.R;Y.prototype.changed=Y.prototype.s;Y.prototype.dispatchEvent=Y.prototype.b;Y.prototype.getRevision=Y.prototype.L;Y.prototype.on=Y.prototype.J;Y.prototype.once=Y.prototype.once;Y.prototype.un=Y.prototype.K;mx.prototype.setRenderReprojectionEdges=mx.prototype.Ob;mx.prototype.setTileGridForProjection=mx.prototype.Pb;mx.prototype.getTileLoadFunction=mx.prototype.ob; -mx.prototype.getTileUrlFunction=mx.prototype.qb;mx.prototype.getUrls=mx.prototype.rb;mx.prototype.setTileLoadFunction=mx.prototype.wb;mx.prototype.setTileUrlFunction=mx.prototype.bb;mx.prototype.setUrl=mx.prototype.ib;mx.prototype.setUrls=mx.prototype.cb;mx.prototype.getTileGrid=mx.prototype.ab;mx.prototype.refresh=mx.prototype.va;mx.prototype.getAttributions=mx.prototype.xa;mx.prototype.getLogo=mx.prototype.wa;mx.prototype.getProjection=mx.prototype.ya;mx.prototype.getState=mx.prototype.V; -mx.prototype.setAttributions=mx.prototype.ua;mx.prototype.get=mx.prototype.get;mx.prototype.getKeys=mx.prototype.P;mx.prototype.getProperties=mx.prototype.M;mx.prototype.set=mx.prototype.set;mx.prototype.setProperties=mx.prototype.H;mx.prototype.unset=mx.prototype.R;mx.prototype.changed=mx.prototype.s;mx.prototype.dispatchEvent=mx.prototype.b;mx.prototype.getRevision=mx.prototype.L;mx.prototype.on=mx.prototype.J;mx.prototype.once=mx.prototype.once;mx.prototype.un=mx.prototype.K; -aw.prototype.getTileCoord=aw.prototype.i;aw.prototype.load=aw.prototype.load;qt.prototype.changed=qt.prototype.s;qt.prototype.dispatchEvent=qt.prototype.b;qt.prototype.getRevision=qt.prototype.L;qt.prototype.on=qt.prototype.J;qt.prototype.once=qt.prototype.once;qt.prototype.un=qt.prototype.K;Ot.prototype.changed=Ot.prototype.s;Ot.prototype.dispatchEvent=Ot.prototype.b;Ot.prototype.getRevision=Ot.prototype.L;Ot.prototype.on=Ot.prototype.J;Ot.prototype.once=Ot.prototype.once;Ot.prototype.un=Ot.prototype.K; -Jv.prototype.changed=Jv.prototype.s;Jv.prototype.dispatchEvent=Jv.prototype.b;Jv.prototype.getRevision=Jv.prototype.L;Jv.prototype.on=Jv.prototype.J;Jv.prototype.once=Jv.prototype.once;Jv.prototype.un=Jv.prototype.K;Uv.prototype.changed=Uv.prototype.s;Uv.prototype.dispatchEvent=Uv.prototype.b;Uv.prototype.getRevision=Uv.prototype.L;Uv.prototype.on=Uv.prototype.J;Uv.prototype.once=Uv.prototype.once;Uv.prototype.un=Uv.prototype.K;Rt.prototype.changed=Rt.prototype.s;Rt.prototype.dispatchEvent=Rt.prototype.b; -Rt.prototype.getRevision=Rt.prototype.L;Rt.prototype.on=Rt.prototype.J;Rt.prototype.once=Rt.prototype.once;Rt.prototype.un=Rt.prototype.K;zt.prototype.changed=zt.prototype.s;zt.prototype.dispatchEvent=zt.prototype.b;zt.prototype.getRevision=zt.prototype.L;zt.prototype.on=zt.prototype.J;zt.prototype.once=zt.prototype.once;zt.prototype.un=zt.prototype.K;qv.prototype.changed=qv.prototype.s;qv.prototype.dispatchEvent=qv.prototype.b;qv.prototype.getRevision=qv.prototype.L;qv.prototype.on=qv.prototype.J; -qv.prototype.once=qv.prototype.once;qv.prototype.un=qv.prototype.K;rv.prototype.changed=rv.prototype.s;rv.prototype.dispatchEvent=rv.prototype.b;rv.prototype.getRevision=rv.prototype.L;rv.prototype.on=rv.prototype.J;rv.prototype.once=rv.prototype.once;rv.prototype.un=rv.prototype.K;Nv.prototype.changed=Nv.prototype.s;Nv.prototype.dispatchEvent=Nv.prototype.b;Nv.prototype.getRevision=Nv.prototype.L;Nv.prototype.on=Nv.prototype.J;Nv.prototype.once=Nv.prototype.once;Nv.prototype.un=Nv.prototype.K; -Ht.prototype.changed=Ht.prototype.s;Ht.prototype.dispatchEvent=Ht.prototype.b;Ht.prototype.getRevision=Ht.prototype.L;Ht.prototype.on=Ht.prototype.J;Ht.prototype.once=Ht.prototype.once;Ht.prototype.un=Ht.prototype.K;Wv.prototype.changed=Wv.prototype.s;Wv.prototype.dispatchEvent=Wv.prototype.b;Wv.prototype.getRevision=Wv.prototype.L;Wv.prototype.on=Wv.prototype.J;Wv.prototype.once=Wv.prototype.once;Wv.prototype.un=Wv.prototype.K;Oh.prototype.type=Oh.prototype.type;Oh.prototype.target=Oh.prototype.target; -Oh.prototype.preventDefault=Oh.prototype.preventDefault;Oh.prototype.stopPropagation=Oh.prototype.stopPropagation;oe.prototype.type=oe.prototype.type;oe.prototype.target=oe.prototype.target;oe.prototype.preventDefault=oe.prototype.preventDefault;oe.prototype.stopPropagation=oe.prototype.stopPropagation;ph.prototype.get=ph.prototype.get;ph.prototype.getKeys=ph.prototype.P;ph.prototype.getProperties=ph.prototype.M;ph.prototype.set=ph.prototype.set;ph.prototype.setProperties=ph.prototype.H; -ph.prototype.unset=ph.prototype.R;ph.prototype.changed=ph.prototype.s;ph.prototype.dispatchEvent=ph.prototype.b;ph.prototype.getRevision=ph.prototype.L;ph.prototype.on=ph.prototype.J;ph.prototype.once=ph.prototype.once;ph.prototype.un=ph.prototype.K;rh.prototype.getExtent=rh.prototype.D;rh.prototype.getMaxResolution=rh.prototype.hc;rh.prototype.getMinResolution=rh.prototype.ic;rh.prototype.getOpacity=rh.prototype.jc;rh.prototype.getVisible=rh.prototype.Lb;rh.prototype.getZIndex=rh.prototype.Aa; -rh.prototype.setExtent=rh.prototype.xc;rh.prototype.setMaxResolution=rh.prototype.Cc;rh.prototype.setMinResolution=rh.prototype.Dc;rh.prototype.setOpacity=rh.prototype.yc;rh.prototype.setVisible=rh.prototype.zc;rh.prototype.setZIndex=rh.prototype.Xb;rh.prototype.get=rh.prototype.get;rh.prototype.getKeys=rh.prototype.P;rh.prototype.getProperties=rh.prototype.M;rh.prototype.set=rh.prototype.set;rh.prototype.setProperties=rh.prototype.H;rh.prototype.unset=rh.prototype.R;rh.prototype.changed=rh.prototype.s; -rh.prototype.dispatchEvent=rh.prototype.b;rh.prototype.getRevision=rh.prototype.L;rh.prototype.on=rh.prototype.J;rh.prototype.once=rh.prototype.once;rh.prototype.un=rh.prototype.K;th.prototype.getExtent=th.prototype.D;th.prototype.getMaxResolution=th.prototype.hc;th.prototype.getMinResolution=th.prototype.ic;th.prototype.getOpacity=th.prototype.jc;th.prototype.getVisible=th.prototype.Lb;th.prototype.getZIndex=th.prototype.Aa;th.prototype.setExtent=th.prototype.xc;th.prototype.setMaxResolution=th.prototype.Cc; -th.prototype.setMinResolution=th.prototype.Dc;th.prototype.setOpacity=th.prototype.yc;th.prototype.setVisible=th.prototype.zc;th.prototype.setZIndex=th.prototype.Xb;th.prototype.get=th.prototype.get;th.prototype.getKeys=th.prototype.P;th.prototype.getProperties=th.prototype.M;th.prototype.set=th.prototype.set;th.prototype.setProperties=th.prototype.H;th.prototype.unset=th.prototype.R;th.prototype.changed=th.prototype.s;th.prototype.dispatchEvent=th.prototype.b;th.prototype.getRevision=th.prototype.L; -th.prototype.on=th.prototype.J;th.prototype.once=th.prototype.once;th.prototype.un=th.prototype.K;S.prototype.setMap=S.prototype.setMap;S.prototype.setSource=S.prototype.ad;S.prototype.getExtent=S.prototype.D;S.prototype.getMaxResolution=S.prototype.hc;S.prototype.getMinResolution=S.prototype.ic;S.prototype.getOpacity=S.prototype.jc;S.prototype.getVisible=S.prototype.Lb;S.prototype.getZIndex=S.prototype.Aa;S.prototype.setExtent=S.prototype.xc;S.prototype.setMaxResolution=S.prototype.Cc; -S.prototype.setMinResolution=S.prototype.Dc;S.prototype.setOpacity=S.prototype.yc;S.prototype.setVisible=S.prototype.zc;S.prototype.setZIndex=S.prototype.Xb;S.prototype.get=S.prototype.get;S.prototype.getKeys=S.prototype.P;S.prototype.getProperties=S.prototype.M;S.prototype.set=S.prototype.set;S.prototype.setProperties=S.prototype.H;S.prototype.unset=S.prototype.R;S.prototype.changed=S.prototype.s;S.prototype.dispatchEvent=S.prototype.b;S.prototype.getRevision=S.prototype.L;S.prototype.on=S.prototype.J; -S.prototype.once=S.prototype.once;S.prototype.un=S.prototype.K;U.prototype.getSource=U.prototype.ka;U.prototype.getStyle=U.prototype.C;U.prototype.getStyleFunction=U.prototype.G;U.prototype.setStyle=U.prototype.f;U.prototype.setMap=U.prototype.setMap;U.prototype.setSource=U.prototype.ad;U.prototype.getExtent=U.prototype.D;U.prototype.getMaxResolution=U.prototype.hc;U.prototype.getMinResolution=U.prototype.ic;U.prototype.getOpacity=U.prototype.jc;U.prototype.getVisible=U.prototype.Lb; -U.prototype.getZIndex=U.prototype.Aa;U.prototype.setExtent=U.prototype.xc;U.prototype.setMaxResolution=U.prototype.Cc;U.prototype.setMinResolution=U.prototype.Dc;U.prototype.setOpacity=U.prototype.yc;U.prototype.setVisible=U.prototype.zc;U.prototype.setZIndex=U.prototype.Xb;U.prototype.get=U.prototype.get;U.prototype.getKeys=U.prototype.P;U.prototype.getProperties=U.prototype.M;U.prototype.set=U.prototype.set;U.prototype.setProperties=U.prototype.H;U.prototype.unset=U.prototype.R; -U.prototype.changed=U.prototype.s;U.prototype.dispatchEvent=U.prototype.b;U.prototype.getRevision=U.prototype.L;U.prototype.on=U.prototype.J;U.prototype.once=U.prototype.once;U.prototype.un=U.prototype.K;Mv.prototype.setMap=Mv.prototype.setMap;Mv.prototype.setSource=Mv.prototype.ad;Mv.prototype.getExtent=Mv.prototype.D;Mv.prototype.getMaxResolution=Mv.prototype.hc;Mv.prototype.getMinResolution=Mv.prototype.ic;Mv.prototype.getOpacity=Mv.prototype.jc;Mv.prototype.getVisible=Mv.prototype.Lb; -Mv.prototype.getZIndex=Mv.prototype.Aa;Mv.prototype.setExtent=Mv.prototype.xc;Mv.prototype.setMaxResolution=Mv.prototype.Cc;Mv.prototype.setMinResolution=Mv.prototype.Dc;Mv.prototype.setOpacity=Mv.prototype.yc;Mv.prototype.setVisible=Mv.prototype.zc;Mv.prototype.setZIndex=Mv.prototype.Xb;Mv.prototype.get=Mv.prototype.get;Mv.prototype.getKeys=Mv.prototype.P;Mv.prototype.getProperties=Mv.prototype.M;Mv.prototype.set=Mv.prototype.set;Mv.prototype.setProperties=Mv.prototype.H;Mv.prototype.unset=Mv.prototype.R; -Mv.prototype.changed=Mv.prototype.s;Mv.prototype.dispatchEvent=Mv.prototype.b;Mv.prototype.getRevision=Mv.prototype.L;Mv.prototype.on=Mv.prototype.J;Mv.prototype.once=Mv.prototype.once;Mv.prototype.un=Mv.prototype.K;Vv.prototype.setMap=Vv.prototype.setMap;Vv.prototype.setSource=Vv.prototype.ad;Vv.prototype.getExtent=Vv.prototype.D;Vv.prototype.getMaxResolution=Vv.prototype.hc;Vv.prototype.getMinResolution=Vv.prototype.ic;Vv.prototype.getOpacity=Vv.prototype.jc;Vv.prototype.getVisible=Vv.prototype.Lb; -Vv.prototype.getZIndex=Vv.prototype.Aa;Vv.prototype.setExtent=Vv.prototype.xc;Vv.prototype.setMaxResolution=Vv.prototype.Cc;Vv.prototype.setMinResolution=Vv.prototype.Dc;Vv.prototype.setOpacity=Vv.prototype.yc;Vv.prototype.setVisible=Vv.prototype.zc;Vv.prototype.setZIndex=Vv.prototype.Xb;Vv.prototype.get=Vv.prototype.get;Vv.prototype.getKeys=Vv.prototype.P;Vv.prototype.getProperties=Vv.prototype.M;Vv.prototype.set=Vv.prototype.set;Vv.prototype.setProperties=Vv.prototype.H;Vv.prototype.unset=Vv.prototype.R; -Vv.prototype.changed=Vv.prototype.s;Vv.prototype.dispatchEvent=Vv.prototype.b;Vv.prototype.getRevision=Vv.prototype.L;Vv.prototype.on=Vv.prototype.J;Vv.prototype.once=Vv.prototype.once;Vv.prototype.un=Vv.prototype.K;V.prototype.getSource=V.prototype.ka;V.prototype.getStyle=V.prototype.C;V.prototype.getStyleFunction=V.prototype.G;V.prototype.setStyle=V.prototype.f;V.prototype.setMap=V.prototype.setMap;V.prototype.setSource=V.prototype.ad;V.prototype.getExtent=V.prototype.D; -V.prototype.getMaxResolution=V.prototype.hc;V.prototype.getMinResolution=V.prototype.ic;V.prototype.getOpacity=V.prototype.jc;V.prototype.getVisible=V.prototype.Lb;V.prototype.getZIndex=V.prototype.Aa;V.prototype.setExtent=V.prototype.xc;V.prototype.setMaxResolution=V.prototype.Cc;V.prototype.setMinResolution=V.prototype.Dc;V.prototype.setOpacity=V.prototype.yc;V.prototype.setVisible=V.prototype.zc;V.prototype.setZIndex=V.prototype.Xb;V.prototype.get=V.prototype.get;V.prototype.getKeys=V.prototype.P; -V.prototype.getProperties=V.prototype.M;V.prototype.set=V.prototype.set;V.prototype.setProperties=V.prototype.H;V.prototype.unset=V.prototype.R;V.prototype.changed=V.prototype.s;V.prototype.dispatchEvent=V.prototype.b;V.prototype.getRevision=V.prototype.L;V.prototype.on=V.prototype.J;V.prototype.once=V.prototype.once;V.prototype.un=V.prototype.K;kg.prototype.get=kg.prototype.get;kg.prototype.getKeys=kg.prototype.P;kg.prototype.getProperties=kg.prototype.M;kg.prototype.set=kg.prototype.set; -kg.prototype.setProperties=kg.prototype.H;kg.prototype.unset=kg.prototype.R;kg.prototype.changed=kg.prototype.s;kg.prototype.dispatchEvent=kg.prototype.b;kg.prototype.getRevision=kg.prototype.L;kg.prototype.on=kg.prototype.J;kg.prototype.once=kg.prototype.once;kg.prototype.un=kg.prototype.K;og.prototype.getActive=og.prototype.c;og.prototype.getMap=og.prototype.i;og.prototype.setActive=og.prototype.Ia;og.prototype.get=og.prototype.get;og.prototype.getKeys=og.prototype.P; -og.prototype.getProperties=og.prototype.M;og.prototype.set=og.prototype.set;og.prototype.setProperties=og.prototype.H;og.prototype.unset=og.prototype.R;og.prototype.changed=og.prototype.s;og.prototype.dispatchEvent=og.prototype.b;og.prototype.getRevision=og.prototype.L;og.prototype.on=og.prototype.J;og.prototype.once=og.prototype.once;og.prototype.un=og.prototype.K;Ms.prototype.getActive=Ms.prototype.c;Ms.prototype.getMap=Ms.prototype.i;Ms.prototype.setActive=Ms.prototype.Ia;Ms.prototype.get=Ms.prototype.get; -Ms.prototype.getKeys=Ms.prototype.P;Ms.prototype.getProperties=Ms.prototype.M;Ms.prototype.set=Ms.prototype.set;Ms.prototype.setProperties=Ms.prototype.H;Ms.prototype.unset=Ms.prototype.R;Ms.prototype.changed=Ms.prototype.s;Ms.prototype.dispatchEvent=Ms.prototype.b;Ms.prototype.getRevision=Ms.prototype.L;Ms.prototype.on=Ms.prototype.J;Ms.prototype.once=Ms.prototype.once;Ms.prototype.un=Ms.prototype.K;Ps.prototype.type=Ps.prototype.type;Ps.prototype.target=Ps.prototype.target; -Ps.prototype.preventDefault=Ps.prototype.preventDefault;Ps.prototype.stopPropagation=Ps.prototype.stopPropagation;Ag.prototype.getActive=Ag.prototype.c;Ag.prototype.getMap=Ag.prototype.i;Ag.prototype.setActive=Ag.prototype.Ia;Ag.prototype.get=Ag.prototype.get;Ag.prototype.getKeys=Ag.prototype.P;Ag.prototype.getProperties=Ag.prototype.M;Ag.prototype.set=Ag.prototype.set;Ag.prototype.setProperties=Ag.prototype.H;Ag.prototype.unset=Ag.prototype.R;Ag.prototype.changed=Ag.prototype.s; -Ag.prototype.dispatchEvent=Ag.prototype.b;Ag.prototype.getRevision=Ag.prototype.L;Ag.prototype.on=Ag.prototype.J;Ag.prototype.once=Ag.prototype.once;Ag.prototype.un=Ag.prototype.K;Og.prototype.getActive=Og.prototype.c;Og.prototype.getMap=Og.prototype.i;Og.prototype.setActive=Og.prototype.Ia;Og.prototype.get=Og.prototype.get;Og.prototype.getKeys=Og.prototype.P;Og.prototype.getProperties=Og.prototype.M;Og.prototype.set=Og.prototype.set;Og.prototype.setProperties=Og.prototype.H;Og.prototype.unset=Og.prototype.R; -Og.prototype.changed=Og.prototype.s;Og.prototype.dispatchEvent=Og.prototype.b;Og.prototype.getRevision=Og.prototype.L;Og.prototype.on=Og.prototype.J;Og.prototype.once=Og.prototype.once;Og.prototype.un=Og.prototype.K;Tg.prototype.type=Tg.prototype.type;Tg.prototype.target=Tg.prototype.target;Tg.prototype.preventDefault=Tg.prototype.preventDefault;Tg.prototype.stopPropagation=Tg.prototype.stopPropagation;Dg.prototype.getActive=Dg.prototype.c;Dg.prototype.getMap=Dg.prototype.i; -Dg.prototype.setActive=Dg.prototype.Ia;Dg.prototype.get=Dg.prototype.get;Dg.prototype.getKeys=Dg.prototype.P;Dg.prototype.getProperties=Dg.prototype.M;Dg.prototype.set=Dg.prototype.set;Dg.prototype.setProperties=Dg.prototype.H;Dg.prototype.unset=Dg.prototype.R;Dg.prototype.changed=Dg.prototype.s;Dg.prototype.dispatchEvent=Dg.prototype.b;Dg.prototype.getRevision=Dg.prototype.L;Dg.prototype.on=Dg.prototype.J;Dg.prototype.once=Dg.prototype.once;Dg.prototype.un=Dg.prototype.K;Hg.prototype.getActive=Hg.prototype.c; -Hg.prototype.getMap=Hg.prototype.i;Hg.prototype.setActive=Hg.prototype.Ia;Hg.prototype.get=Hg.prototype.get;Hg.prototype.getKeys=Hg.prototype.P;Hg.prototype.getProperties=Hg.prototype.M;Hg.prototype.set=Hg.prototype.set;Hg.prototype.setProperties=Hg.prototype.H;Hg.prototype.unset=Hg.prototype.R;Hg.prototype.changed=Hg.prototype.s;Hg.prototype.dispatchEvent=Hg.prototype.b;Hg.prototype.getRevision=Hg.prototype.L;Hg.prototype.on=Hg.prototype.J;Hg.prototype.once=Hg.prototype.once;Hg.prototype.un=Hg.prototype.K; -Rs.prototype.getActive=Rs.prototype.c;Rs.prototype.getMap=Rs.prototype.i;Rs.prototype.setActive=Rs.prototype.Ia;Rs.prototype.get=Rs.prototype.get;Rs.prototype.getKeys=Rs.prototype.P;Rs.prototype.getProperties=Rs.prototype.M;Rs.prototype.set=Rs.prototype.set;Rs.prototype.setProperties=Rs.prototype.H;Rs.prototype.unset=Rs.prototype.R;Rs.prototype.changed=Rs.prototype.s;Rs.prototype.dispatchEvent=Rs.prototype.b;Rs.prototype.getRevision=Rs.prototype.L;Rs.prototype.on=Rs.prototype.J; -Rs.prototype.once=Rs.prototype.once;Rs.prototype.un=Rs.prototype.K;Xg.prototype.getGeometry=Xg.prototype.U;Xg.prototype.getActive=Xg.prototype.c;Xg.prototype.getMap=Xg.prototype.i;Xg.prototype.setActive=Xg.prototype.Ia;Xg.prototype.get=Xg.prototype.get;Xg.prototype.getKeys=Xg.prototype.P;Xg.prototype.getProperties=Xg.prototype.M;Xg.prototype.set=Xg.prototype.set;Xg.prototype.setProperties=Xg.prototype.H;Xg.prototype.unset=Xg.prototype.R;Xg.prototype.changed=Xg.prototype.s; -Xg.prototype.dispatchEvent=Xg.prototype.b;Xg.prototype.getRevision=Xg.prototype.L;Xg.prototype.on=Xg.prototype.J;Xg.prototype.once=Xg.prototype.once;Xg.prototype.un=Xg.prototype.K;cu.prototype.getActive=cu.prototype.c;cu.prototype.getMap=cu.prototype.i;cu.prototype.setActive=cu.prototype.Ia;cu.prototype.get=cu.prototype.get;cu.prototype.getKeys=cu.prototype.P;cu.prototype.getProperties=cu.prototype.M;cu.prototype.set=cu.prototype.set;cu.prototype.setProperties=cu.prototype.H;cu.prototype.unset=cu.prototype.R; -cu.prototype.changed=cu.prototype.s;cu.prototype.dispatchEvent=cu.prototype.b;cu.prototype.getRevision=cu.prototype.L;cu.prototype.on=cu.prototype.J;cu.prototype.once=cu.prototype.once;cu.prototype.un=cu.prototype.K;su.prototype.type=su.prototype.type;su.prototype.target=su.prototype.target;su.prototype.preventDefault=su.prototype.preventDefault;su.prototype.stopPropagation=su.prototype.stopPropagation;tu.prototype.getActive=tu.prototype.c;tu.prototype.getMap=tu.prototype.i; -tu.prototype.setActive=tu.prototype.Ia;tu.prototype.get=tu.prototype.get;tu.prototype.getKeys=tu.prototype.P;tu.prototype.getProperties=tu.prototype.M;tu.prototype.set=tu.prototype.set;tu.prototype.setProperties=tu.prototype.H;tu.prototype.unset=tu.prototype.R;tu.prototype.changed=tu.prototype.s;tu.prototype.dispatchEvent=tu.prototype.b;tu.prototype.getRevision=tu.prototype.L;tu.prototype.on=tu.prototype.J;tu.prototype.once=tu.prototype.once;tu.prototype.un=tu.prototype.K;Eu.prototype.type=Eu.prototype.type; -Eu.prototype.target=Eu.prototype.target;Eu.prototype.preventDefault=Eu.prototype.preventDefault;Eu.prototype.stopPropagation=Eu.prototype.stopPropagation;Yg.prototype.getActive=Yg.prototype.c;Yg.prototype.getMap=Yg.prototype.i;Yg.prototype.setActive=Yg.prototype.Ia;Yg.prototype.get=Yg.prototype.get;Yg.prototype.getKeys=Yg.prototype.P;Yg.prototype.getProperties=Yg.prototype.M;Yg.prototype.set=Yg.prototype.set;Yg.prototype.setProperties=Yg.prototype.H;Yg.prototype.unset=Yg.prototype.R; -Yg.prototype.changed=Yg.prototype.s;Yg.prototype.dispatchEvent=Yg.prototype.b;Yg.prototype.getRevision=Yg.prototype.L;Yg.prototype.on=Yg.prototype.J;Yg.prototype.once=Yg.prototype.once;Yg.prototype.un=Yg.prototype.K;$g.prototype.getActive=$g.prototype.c;$g.prototype.getMap=$g.prototype.i;$g.prototype.setActive=$g.prototype.Ia;$g.prototype.get=$g.prototype.get;$g.prototype.getKeys=$g.prototype.P;$g.prototype.getProperties=$g.prototype.M;$g.prototype.set=$g.prototype.set; -$g.prototype.setProperties=$g.prototype.H;$g.prototype.unset=$g.prototype.R;$g.prototype.changed=$g.prototype.s;$g.prototype.dispatchEvent=$g.prototype.b;$g.prototype.getRevision=$g.prototype.L;$g.prototype.on=$g.prototype.J;$g.prototype.once=$g.prototype.once;$g.prototype.un=$g.prototype.K;Gu.prototype.getActive=Gu.prototype.c;Gu.prototype.getMap=Gu.prototype.i;Gu.prototype.setActive=Gu.prototype.Ia;Gu.prototype.get=Gu.prototype.get;Gu.prototype.getKeys=Gu.prototype.P; -Gu.prototype.getProperties=Gu.prototype.M;Gu.prototype.set=Gu.prototype.set;Gu.prototype.setProperties=Gu.prototype.H;Gu.prototype.unset=Gu.prototype.R;Gu.prototype.changed=Gu.prototype.s;Gu.prototype.dispatchEvent=Gu.prototype.b;Gu.prototype.getRevision=Gu.prototype.L;Gu.prototype.on=Gu.prototype.J;Gu.prototype.once=Gu.prototype.once;Gu.prototype.un=Gu.prototype.K;Ou.prototype.type=Ou.prototype.type;Ou.prototype.target=Ou.prototype.target;Ou.prototype.preventDefault=Ou.prototype.preventDefault; -Ou.prototype.stopPropagation=Ou.prototype.stopPropagation;bh.prototype.getActive=bh.prototype.c;bh.prototype.getMap=bh.prototype.i;bh.prototype.setActive=bh.prototype.Ia;bh.prototype.get=bh.prototype.get;bh.prototype.getKeys=bh.prototype.P;bh.prototype.getProperties=bh.prototype.M;bh.prototype.set=bh.prototype.set;bh.prototype.setProperties=bh.prototype.H;bh.prototype.unset=bh.prototype.R;bh.prototype.changed=bh.prototype.s;bh.prototype.dispatchEvent=bh.prototype.b;bh.prototype.getRevision=bh.prototype.L; -bh.prototype.on=bh.prototype.J;bh.prototype.once=bh.prototype.once;bh.prototype.un=bh.prototype.K;fh.prototype.getActive=fh.prototype.c;fh.prototype.getMap=fh.prototype.i;fh.prototype.setActive=fh.prototype.Ia;fh.prototype.get=fh.prototype.get;fh.prototype.getKeys=fh.prototype.P;fh.prototype.getProperties=fh.prototype.M;fh.prototype.set=fh.prototype.set;fh.prototype.setProperties=fh.prototype.H;fh.prototype.unset=fh.prototype.R;fh.prototype.changed=fh.prototype.s;fh.prototype.dispatchEvent=fh.prototype.b; -fh.prototype.getRevision=fh.prototype.L;fh.prototype.on=fh.prototype.J;fh.prototype.once=fh.prototype.once;fh.prototype.un=fh.prototype.K;jh.prototype.getActive=jh.prototype.c;jh.prototype.getMap=jh.prototype.i;jh.prototype.setActive=jh.prototype.Ia;jh.prototype.get=jh.prototype.get;jh.prototype.getKeys=jh.prototype.P;jh.prototype.getProperties=jh.prototype.M;jh.prototype.set=jh.prototype.set;jh.prototype.setProperties=jh.prototype.H;jh.prototype.unset=jh.prototype.R;jh.prototype.changed=jh.prototype.s; -jh.prototype.dispatchEvent=jh.prototype.b;jh.prototype.getRevision=jh.prototype.L;jh.prototype.on=jh.prototype.J;jh.prototype.once=jh.prototype.once;jh.prototype.un=jh.prototype.K;Wu.prototype.getActive=Wu.prototype.c;Wu.prototype.getMap=Wu.prototype.i;Wu.prototype.setActive=Wu.prototype.Ia;Wu.prototype.get=Wu.prototype.get;Wu.prototype.getKeys=Wu.prototype.P;Wu.prototype.getProperties=Wu.prototype.M;Wu.prototype.set=Wu.prototype.set;Wu.prototype.setProperties=Wu.prototype.H;Wu.prototype.unset=Wu.prototype.R; -Wu.prototype.changed=Wu.prototype.s;Wu.prototype.dispatchEvent=Wu.prototype.b;Wu.prototype.getRevision=Wu.prototype.L;Wu.prototype.on=Wu.prototype.J;Wu.prototype.once=Wu.prototype.once;Wu.prototype.un=Wu.prototype.K;Zu.prototype.type=Zu.prototype.type;Zu.prototype.target=Zu.prototype.target;Zu.prototype.preventDefault=Zu.prototype.preventDefault;Zu.prototype.stopPropagation=Zu.prototype.stopPropagation;av.prototype.getActive=av.prototype.c;av.prototype.getMap=av.prototype.i; -av.prototype.setActive=av.prototype.Ia;av.prototype.get=av.prototype.get;av.prototype.getKeys=av.prototype.P;av.prototype.getProperties=av.prototype.M;av.prototype.set=av.prototype.set;av.prototype.setProperties=av.prototype.H;av.prototype.unset=av.prototype.R;av.prototype.changed=av.prototype.s;av.prototype.dispatchEvent=av.prototype.b;av.prototype.getRevision=av.prototype.L;av.prototype.on=av.prototype.J;av.prototype.once=av.prototype.once;av.prototype.un=av.prototype.K;ev.prototype.getActive=ev.prototype.c; -ev.prototype.getMap=ev.prototype.i;ev.prototype.setActive=ev.prototype.Ia;ev.prototype.get=ev.prototype.get;ev.prototype.getKeys=ev.prototype.P;ev.prototype.getProperties=ev.prototype.M;ev.prototype.set=ev.prototype.set;ev.prototype.setProperties=ev.prototype.H;ev.prototype.unset=ev.prototype.R;ev.prototype.changed=ev.prototype.s;ev.prototype.dispatchEvent=ev.prototype.b;ev.prototype.getRevision=ev.prototype.L;ev.prototype.on=ev.prototype.J;ev.prototype.once=ev.prototype.once;ev.prototype.un=ev.prototype.K; -kv.prototype.type=kv.prototype.type;kv.prototype.target=kv.prototype.target;kv.prototype.preventDefault=kv.prototype.preventDefault;kv.prototype.stopPropagation=kv.prototype.stopPropagation;lf.prototype.get=lf.prototype.get;lf.prototype.getKeys=lf.prototype.P;lf.prototype.getProperties=lf.prototype.M;lf.prototype.set=lf.prototype.set;lf.prototype.setProperties=lf.prototype.H;lf.prototype.unset=lf.prototype.R;lf.prototype.changed=lf.prototype.s;lf.prototype.dispatchEvent=lf.prototype.b; -lf.prototype.getRevision=lf.prototype.L;lf.prototype.on=lf.prototype.J;lf.prototype.once=lf.prototype.once;lf.prototype.un=lf.prototype.K;of.prototype.getClosestPoint=of.prototype.Ab;of.prototype.intersectsCoordinate=of.prototype.sb;of.prototype.getExtent=of.prototype.D;of.prototype.rotate=of.prototype.rotate;of.prototype.scale=of.prototype.scale;of.prototype.simplify=of.prototype.Qb;of.prototype.transform=of.prototype.tb;of.prototype.get=of.prototype.get;of.prototype.getKeys=of.prototype.P; -of.prototype.getProperties=of.prototype.M;of.prototype.set=of.prototype.set;of.prototype.setProperties=of.prototype.H;of.prototype.unset=of.prototype.R;of.prototype.changed=of.prototype.s;of.prototype.dispatchEvent=of.prototype.b;of.prototype.getRevision=of.prototype.L;of.prototype.on=of.prototype.J;of.prototype.once=of.prototype.once;of.prototype.un=of.prototype.K;vs.prototype.getFirstCoordinate=vs.prototype.cc;vs.prototype.getLastCoordinate=vs.prototype.dc;vs.prototype.getLayout=vs.prototype.ec; -vs.prototype.rotate=vs.prototype.rotate;vs.prototype.scale=vs.prototype.scale;vs.prototype.getClosestPoint=vs.prototype.Ab;vs.prototype.intersectsCoordinate=vs.prototype.sb;vs.prototype.getExtent=vs.prototype.D;vs.prototype.simplify=vs.prototype.Qb;vs.prototype.get=vs.prototype.get;vs.prototype.getKeys=vs.prototype.P;vs.prototype.getProperties=vs.prototype.M;vs.prototype.set=vs.prototype.set;vs.prototype.setProperties=vs.prototype.H;vs.prototype.unset=vs.prototype.R;vs.prototype.changed=vs.prototype.s; -vs.prototype.dispatchEvent=vs.prototype.b;vs.prototype.getRevision=vs.prototype.L;vs.prototype.on=vs.prototype.J;vs.prototype.once=vs.prototype.once;vs.prototype.un=vs.prototype.K;sm.prototype.getClosestPoint=sm.prototype.Ab;sm.prototype.intersectsCoordinate=sm.prototype.sb;sm.prototype.getExtent=sm.prototype.D;sm.prototype.rotate=sm.prototype.rotate;sm.prototype.scale=sm.prototype.scale;sm.prototype.simplify=sm.prototype.Qb;sm.prototype.transform=sm.prototype.tb;sm.prototype.get=sm.prototype.get; -sm.prototype.getKeys=sm.prototype.P;sm.prototype.getProperties=sm.prototype.M;sm.prototype.set=sm.prototype.set;sm.prototype.setProperties=sm.prototype.H;sm.prototype.unset=sm.prototype.R;sm.prototype.changed=sm.prototype.s;sm.prototype.dispatchEvent=sm.prototype.b;sm.prototype.getRevision=sm.prototype.L;sm.prototype.on=sm.prototype.J;sm.prototype.once=sm.prototype.once;sm.prototype.un=sm.prototype.K;Gf.prototype.getFirstCoordinate=Gf.prototype.cc;Gf.prototype.getLastCoordinate=Gf.prototype.dc; -Gf.prototype.getLayout=Gf.prototype.ec;Gf.prototype.rotate=Gf.prototype.rotate;Gf.prototype.scale=Gf.prototype.scale;Gf.prototype.getClosestPoint=Gf.prototype.Ab;Gf.prototype.intersectsCoordinate=Gf.prototype.sb;Gf.prototype.getExtent=Gf.prototype.D;Gf.prototype.simplify=Gf.prototype.Qb;Gf.prototype.transform=Gf.prototype.tb;Gf.prototype.get=Gf.prototype.get;Gf.prototype.getKeys=Gf.prototype.P;Gf.prototype.getProperties=Gf.prototype.M;Gf.prototype.set=Gf.prototype.set;Gf.prototype.setProperties=Gf.prototype.H; -Gf.prototype.unset=Gf.prototype.R;Gf.prototype.changed=Gf.prototype.s;Gf.prototype.dispatchEvent=Gf.prototype.b;Gf.prototype.getRevision=Gf.prototype.L;Gf.prototype.on=Gf.prototype.J;Gf.prototype.once=Gf.prototype.once;Gf.prototype.un=Gf.prototype.K;N.prototype.getFirstCoordinate=N.prototype.cc;N.prototype.getLastCoordinate=N.prototype.dc;N.prototype.getLayout=N.prototype.ec;N.prototype.rotate=N.prototype.rotate;N.prototype.scale=N.prototype.scale;N.prototype.getClosestPoint=N.prototype.Ab; -N.prototype.intersectsCoordinate=N.prototype.sb;N.prototype.getExtent=N.prototype.D;N.prototype.simplify=N.prototype.Qb;N.prototype.transform=N.prototype.tb;N.prototype.get=N.prototype.get;N.prototype.getKeys=N.prototype.P;N.prototype.getProperties=N.prototype.M;N.prototype.set=N.prototype.set;N.prototype.setProperties=N.prototype.H;N.prototype.unset=N.prototype.R;N.prototype.changed=N.prototype.s;N.prototype.dispatchEvent=N.prototype.b;N.prototype.getRevision=N.prototype.L;N.prototype.on=N.prototype.J; -N.prototype.once=N.prototype.once;N.prototype.un=N.prototype.K;O.prototype.getFirstCoordinate=O.prototype.cc;O.prototype.getLastCoordinate=O.prototype.dc;O.prototype.getLayout=O.prototype.ec;O.prototype.rotate=O.prototype.rotate;O.prototype.scale=O.prototype.scale;O.prototype.getClosestPoint=O.prototype.Ab;O.prototype.intersectsCoordinate=O.prototype.sb;O.prototype.getExtent=O.prototype.D;O.prototype.simplify=O.prototype.Qb;O.prototype.transform=O.prototype.tb;O.prototype.get=O.prototype.get; -O.prototype.getKeys=O.prototype.P;O.prototype.getProperties=O.prototype.M;O.prototype.set=O.prototype.set;O.prototype.setProperties=O.prototype.H;O.prototype.unset=O.prototype.R;O.prototype.changed=O.prototype.s;O.prototype.dispatchEvent=O.prototype.b;O.prototype.getRevision=O.prototype.L;O.prototype.on=O.prototype.J;O.prototype.once=O.prototype.once;O.prototype.un=O.prototype.K;P.prototype.getFirstCoordinate=P.prototype.cc;P.prototype.getLastCoordinate=P.prototype.dc;P.prototype.getLayout=P.prototype.ec; -P.prototype.rotate=P.prototype.rotate;P.prototype.scale=P.prototype.scale;P.prototype.getClosestPoint=P.prototype.Ab;P.prototype.intersectsCoordinate=P.prototype.sb;P.prototype.getExtent=P.prototype.D;P.prototype.simplify=P.prototype.Qb;P.prototype.transform=P.prototype.tb;P.prototype.get=P.prototype.get;P.prototype.getKeys=P.prototype.P;P.prototype.getProperties=P.prototype.M;P.prototype.set=P.prototype.set;P.prototype.setProperties=P.prototype.H;P.prototype.unset=P.prototype.R; -P.prototype.changed=P.prototype.s;P.prototype.dispatchEvent=P.prototype.b;P.prototype.getRevision=P.prototype.L;P.prototype.on=P.prototype.J;P.prototype.once=P.prototype.once;P.prototype.un=P.prototype.K;Q.prototype.getFirstCoordinate=Q.prototype.cc;Q.prototype.getLastCoordinate=Q.prototype.dc;Q.prototype.getLayout=Q.prototype.ec;Q.prototype.rotate=Q.prototype.rotate;Q.prototype.scale=Q.prototype.scale;Q.prototype.getClosestPoint=Q.prototype.Ab;Q.prototype.intersectsCoordinate=Q.prototype.sb; -Q.prototype.getExtent=Q.prototype.D;Q.prototype.simplify=Q.prototype.Qb;Q.prototype.transform=Q.prototype.tb;Q.prototype.get=Q.prototype.get;Q.prototype.getKeys=Q.prototype.P;Q.prototype.getProperties=Q.prototype.M;Q.prototype.set=Q.prototype.set;Q.prototype.setProperties=Q.prototype.H;Q.prototype.unset=Q.prototype.R;Q.prototype.changed=Q.prototype.s;Q.prototype.dispatchEvent=Q.prototype.b;Q.prototype.getRevision=Q.prototype.L;Q.prototype.on=Q.prototype.J;Q.prototype.once=Q.prototype.once; -Q.prototype.un=Q.prototype.K;E.prototype.getFirstCoordinate=E.prototype.cc;E.prototype.getLastCoordinate=E.prototype.dc;E.prototype.getLayout=E.prototype.ec;E.prototype.rotate=E.prototype.rotate;E.prototype.scale=E.prototype.scale;E.prototype.getClosestPoint=E.prototype.Ab;E.prototype.intersectsCoordinate=E.prototype.sb;E.prototype.getExtent=E.prototype.D;E.prototype.simplify=E.prototype.Qb;E.prototype.transform=E.prototype.tb;E.prototype.get=E.prototype.get;E.prototype.getKeys=E.prototype.P; -E.prototype.getProperties=E.prototype.M;E.prototype.set=E.prototype.set;E.prototype.setProperties=E.prototype.H;E.prototype.unset=E.prototype.R;E.prototype.changed=E.prototype.s;E.prototype.dispatchEvent=E.prototype.b;E.prototype.getRevision=E.prototype.L;E.prototype.on=E.prototype.J;E.prototype.once=E.prototype.once;E.prototype.un=E.prototype.K;F.prototype.getFirstCoordinate=F.prototype.cc;F.prototype.getLastCoordinate=F.prototype.dc;F.prototype.getLayout=F.prototype.ec;F.prototype.rotate=F.prototype.rotate; -F.prototype.scale=F.prototype.scale;F.prototype.getClosestPoint=F.prototype.Ab;F.prototype.intersectsCoordinate=F.prototype.sb;F.prototype.getExtent=F.prototype.D;F.prototype.simplify=F.prototype.Qb;F.prototype.transform=F.prototype.tb;F.prototype.get=F.prototype.get;F.prototype.getKeys=F.prototype.P;F.prototype.getProperties=F.prototype.M;F.prototype.set=F.prototype.set;F.prototype.setProperties=F.prototype.H;F.prototype.unset=F.prototype.R;F.prototype.changed=F.prototype.s; -F.prototype.dispatchEvent=F.prototype.b;F.prototype.getRevision=F.prototype.L;F.prototype.on=F.prototype.J;F.prototype.once=F.prototype.once;F.prototype.un=F.prototype.K;Rm.prototype.readFeatures=Rm.prototype.Pa;$m.prototype.readFeatures=$m.prototype.Pa;Rm.prototype.readFeatures=Rm.prototype.Pa;kd.prototype.get=kd.prototype.get;kd.prototype.getKeys=kd.prototype.P;kd.prototype.getProperties=kd.prototype.M;kd.prototype.set=kd.prototype.set;kd.prototype.setProperties=kd.prototype.H; -kd.prototype.unset=kd.prototype.R;kd.prototype.changed=kd.prototype.s;kd.prototype.dispatchEvent=kd.prototype.b;kd.prototype.getRevision=kd.prototype.L;kd.prototype.on=kd.prototype.J;kd.prototype.once=kd.prototype.once;kd.prototype.un=kd.prototype.K;ld.prototype.getMap=ld.prototype.f;ld.prototype.setMap=ld.prototype.setMap;ld.prototype.setTarget=ld.prototype.i;ld.prototype.get=ld.prototype.get;ld.prototype.getKeys=ld.prototype.P;ld.prototype.getProperties=ld.prototype.M;ld.prototype.set=ld.prototype.set; -ld.prototype.setProperties=ld.prototype.H;ld.prototype.unset=ld.prototype.R;ld.prototype.changed=ld.prototype.s;ld.prototype.dispatchEvent=ld.prototype.b;ld.prototype.getRevision=ld.prototype.L;ld.prototype.on=ld.prototype.J;ld.prototype.once=ld.prototype.once;ld.prototype.un=ld.prototype.K;wd.prototype.getMap=wd.prototype.f;wd.prototype.setMap=wd.prototype.setMap;wd.prototype.setTarget=wd.prototype.i;wd.prototype.get=wd.prototype.get;wd.prototype.getKeys=wd.prototype.P; -wd.prototype.getProperties=wd.prototype.M;wd.prototype.set=wd.prototype.set;wd.prototype.setProperties=wd.prototype.H;wd.prototype.unset=wd.prototype.R;wd.prototype.changed=wd.prototype.s;wd.prototype.dispatchEvent=wd.prototype.b;wd.prototype.getRevision=wd.prototype.L;wd.prototype.on=wd.prototype.J;wd.prototype.once=wd.prototype.once;wd.prototype.un=wd.prototype.K;Bd.prototype.getMap=Bd.prototype.f;Bd.prototype.setMap=Bd.prototype.setMap;Bd.prototype.setTarget=Bd.prototype.i;Bd.prototype.get=Bd.prototype.get; -Bd.prototype.getKeys=Bd.prototype.P;Bd.prototype.getProperties=Bd.prototype.M;Bd.prototype.set=Bd.prototype.set;Bd.prototype.setProperties=Bd.prototype.H;Bd.prototype.unset=Bd.prototype.R;Bd.prototype.changed=Bd.prototype.s;Bd.prototype.dispatchEvent=Bd.prototype.b;Bd.prototype.getRevision=Bd.prototype.L;Bd.prototype.on=Bd.prototype.J;Bd.prototype.once=Bd.prototype.once;Bd.prototype.un=Bd.prototype.K;Bk.prototype.getMap=Bk.prototype.f;Bk.prototype.setMap=Bk.prototype.setMap; -Bk.prototype.setTarget=Bk.prototype.i;Bk.prototype.get=Bk.prototype.get;Bk.prototype.getKeys=Bk.prototype.P;Bk.prototype.getProperties=Bk.prototype.M;Bk.prototype.set=Bk.prototype.set;Bk.prototype.setProperties=Bk.prototype.H;Bk.prototype.unset=Bk.prototype.R;Bk.prototype.changed=Bk.prototype.s;Bk.prototype.dispatchEvent=Bk.prototype.b;Bk.prototype.getRevision=Bk.prototype.L;Bk.prototype.on=Bk.prototype.J;Bk.prototype.once=Bk.prototype.once;Bk.prototype.un=Bk.prototype.K;sd.prototype.getMap=sd.prototype.f; -sd.prototype.setMap=sd.prototype.setMap;sd.prototype.setTarget=sd.prototype.i;sd.prototype.get=sd.prototype.get;sd.prototype.getKeys=sd.prototype.P;sd.prototype.getProperties=sd.prototype.M;sd.prototype.set=sd.prototype.set;sd.prototype.setProperties=sd.prototype.H;sd.prototype.unset=sd.prototype.R;sd.prototype.changed=sd.prototype.s;sd.prototype.dispatchEvent=sd.prototype.b;sd.prototype.getRevision=sd.prototype.L;sd.prototype.on=sd.prototype.J;sd.prototype.once=sd.prototype.once; -sd.prototype.un=sd.prototype.K;Gk.prototype.getMap=Gk.prototype.f;Gk.prototype.setMap=Gk.prototype.setMap;Gk.prototype.setTarget=Gk.prototype.i;Gk.prototype.get=Gk.prototype.get;Gk.prototype.getKeys=Gk.prototype.P;Gk.prototype.getProperties=Gk.prototype.M;Gk.prototype.set=Gk.prototype.set;Gk.prototype.setProperties=Gk.prototype.H;Gk.prototype.unset=Gk.prototype.R;Gk.prototype.changed=Gk.prototype.s;Gk.prototype.dispatchEvent=Gk.prototype.b;Gk.prototype.getRevision=Gk.prototype.L;Gk.prototype.on=Gk.prototype.J; -Gk.prototype.once=Gk.prototype.once;Gk.prototype.un=Gk.prototype.K;ud.prototype.getMap=ud.prototype.f;ud.prototype.setMap=ud.prototype.setMap;ud.prototype.setTarget=ud.prototype.i;ud.prototype.get=ud.prototype.get;ud.prototype.getKeys=ud.prototype.P;ud.prototype.getProperties=ud.prototype.M;ud.prototype.set=ud.prototype.set;ud.prototype.setProperties=ud.prototype.H;ud.prototype.unset=ud.prototype.R;ud.prototype.changed=ud.prototype.s;ud.prototype.dispatchEvent=ud.prototype.b; -ud.prototype.getRevision=ud.prototype.L;ud.prototype.on=ud.prototype.J;ud.prototype.once=ud.prototype.once;ud.prototype.un=ud.prototype.K;Lk.prototype.getMap=Lk.prototype.f;Lk.prototype.setMap=Lk.prototype.setMap;Lk.prototype.setTarget=Lk.prototype.i;Lk.prototype.get=Lk.prototype.get;Lk.prototype.getKeys=Lk.prototype.P;Lk.prototype.getProperties=Lk.prototype.M;Lk.prototype.set=Lk.prototype.set;Lk.prototype.setProperties=Lk.prototype.H;Lk.prototype.unset=Lk.prototype.R;Lk.prototype.changed=Lk.prototype.s; -Lk.prototype.dispatchEvent=Lk.prototype.b;Lk.prototype.getRevision=Lk.prototype.L;Lk.prototype.on=Lk.prototype.J;Lk.prototype.once=Lk.prototype.once;Lk.prototype.un=Lk.prototype.K;Qk.prototype.getMap=Qk.prototype.f;Qk.prototype.setMap=Qk.prototype.setMap;Qk.prototype.setTarget=Qk.prototype.i;Qk.prototype.get=Qk.prototype.get;Qk.prototype.getKeys=Qk.prototype.P;Qk.prototype.getProperties=Qk.prototype.M;Qk.prototype.set=Qk.prototype.set;Qk.prototype.setProperties=Qk.prototype.H;Qk.prototype.unset=Qk.prototype.R; -Qk.prototype.changed=Qk.prototype.s;Qk.prototype.dispatchEvent=Qk.prototype.b;Qk.prototype.getRevision=Qk.prototype.L;Qk.prototype.on=Qk.prototype.J;Qk.prototype.once=Qk.prototype.once;Qk.prototype.un=Qk.prototype.K; - return OPENLAYERS.ol; -})); - diff --git a/app/resources/js/findRoute.js b/app/resources/js/findRoute.js index 0eabbb4..d98ddb5 100644 --- a/app/resources/js/findRoute.js +++ b/app/resources/js/findRoute.js @@ -312,7 +312,7 @@ function positionToAdress(pos, obj) { obj.html('Eigener Standort'); obj.attr('title', 'Eigener Standort'); } else { - var url = "https://maps.metager.de/nominatim/reverse.php?format=json&lat=" + pos[0] + "&lon=" + pos[1] + "&zoom=18"; + var url = "/search/reverse.php?format=json&lat=" + pos[0] + "&lon=" + pos[1] + "&zoom=18"; $.get(url, function(data) { if (typeof data !== "undefined" && typeof data["display_name"] !== "undefined") { obj.html(data["display_name"]); diff --git a/app/resources/js/map.js b/app/resources/js/map.js index 3679baf..37e830e 100644 --- a/app/resources/js/map.js +++ b/app/resources/js/map.js @@ -1,4 +1,3 @@ -function Map(type) {} function InteractiveMap( long = 9.841943417968748, @@ -6,7 +5,6 @@ function InteractiveMap( zoom = 8, updateMapPositionOnGps = true ) { - Map.call(this); if (isNaN(long) || isNaN(lat) || isNaN(zoom)) { this.initPos = [9.841943417968748, 52.18082778659789]; this.initZoom = 8; @@ -31,13 +29,14 @@ InteractiveMap.prototype = Object.create(Map.prototype); InteractiveMap.prototype.constructor = InteractiveMap; InteractiveMap.prototype.initMap = function() { + let tileserver_host = document.querySelector("meta[name=tileserverhost]").content; maplibregl.setRTLTextPlugin( - "https://tileserver.metager.de/maplibre-gl-rtl-text.js" + `${tileserver_host}/mapbox-gl-rtl-text.js` ); var map = new maplibregl.Map({ container: "map", style: - "https://tileserver.metager.de/styles/osm-bright/style.json?optimize=true", + `${tileserver_host}/styles/osm-bright/style.json?optimize=true`, hash: false, center: this.initPos, zoom: this.initZoom, @@ -149,5 +148,4 @@ InteractiveMap.prototype.removeDownloadedAreas = function() { }; function StaticMap() { - Map.call(this); } diff --git a/app/resources/js/ol-debug.js b/app/resources/js/ol-debug.js deleted file mode 100644 index 13eb1ba..0000000 --- a/app/resources/js/ol-debug.js +++ /dev/null @@ -1,95334 +0,0 @@ -// OpenLayers. See https://openlayers.org/ -// License: https://raw.githubusercontent.com/openlayers/openlayers/master/LICENSE.md -// Version: v4.4.2 -;(function (root, factory) { - if (typeof exports === "object") { - module.exports = factory(); - } else if (typeof define === "function" && define.amd) { - define([], factory); - } else { - root.ol = factory(); - } -}(this, function () { - var OPENLAYERS = {}; - var goog = this.goog = {}; -this.CLOSURE_NO_DEPS = true; -// Copyright 2006 The Closure Library Authors. All Rights Reserved. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS-IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - -/** - * @fileoverview Bootstrap for the Google JS Library (Closure). - * - * In uncompiled mode base.js will attempt to load Closure's deps file, unless - * the global <code>CLOSURE_NO_DEPS</code> is set to true. This allows projects - * to include their own deps file(s) from different locations. - * - * Avoid including base.js more than once. This is strictly discouraged and not - * supported. goog.require(...) won't work properly in that case. - * - * @provideGoog - */ - - -/** - * @define {boolean} Overridden to true by the compiler. - */ -var COMPILED = false; - - -/** - * Base namespace for the Closure library. Checks to see goog is already - * defined in the current scope before assigning to prevent clobbering if - * base.js is loaded more than once. - * - * @const - */ -var goog = goog || {}; - - -/** - * Reference to the global context. In most cases this will be 'window'. - */ -goog.global = this; - - -/** - * A hook for overriding the define values in uncompiled mode. - * - * In uncompiled mode, {@code CLOSURE_UNCOMPILED_DEFINES} may be defined before - * loading base.js. If a key is defined in {@code CLOSURE_UNCOMPILED_DEFINES}, - * {@code goog.define} will use the value instead of the default value. This - * allows flags to be overwritten without compilation (this is normally - * accomplished with the compiler's "define" flag). - * - * Example: - * <pre> - * var CLOSURE_UNCOMPILED_DEFINES = {'goog.DEBUG': false}; - * </pre> - * - * @type {Object<string, (string|number|boolean)>|undefined} - */ -goog.global.CLOSURE_UNCOMPILED_DEFINES; - - -/** - * A hook for overriding the define values in uncompiled or compiled mode, - * like CLOSURE_UNCOMPILED_DEFINES but effective in compiled code. In - * uncompiled code CLOSURE_UNCOMPILED_DEFINES takes precedence. - * - * Also unlike CLOSURE_UNCOMPILED_DEFINES the values must be number, boolean or - * string literals or the compiler will emit an error. - * - * While any @define value may be set, only those set with goog.define will be - * effective for uncompiled code. - * - * Example: - * <pre> - * var CLOSURE_DEFINES = {'goog.DEBUG': false} ; - * </pre> - * - * @type {Object<string, (string|number|boolean)>|undefined} - */ -goog.global.CLOSURE_DEFINES; - - -/** - * Returns true if the specified value is not undefined. - * - * @param {?} val Variable to test. - * @return {boolean} Whether variable is defined. - */ -goog.isDef = function(val) { - // void 0 always evaluates to undefined and hence we do not need to depend on - // the definition of the global variable named 'undefined'. - return val !== void 0; -}; - -/** - * Returns true if the specified value is a string. - * @param {?} val Variable to test. - * @return {boolean} Whether variable is a string. - */ -goog.isString = function(val) { - return typeof val == 'string'; -}; - - -/** - * Returns true if the specified value is a boolean. - * @param {?} val Variable to test. - * @return {boolean} Whether variable is boolean. - */ -goog.isBoolean = function(val) { - return typeof val == 'boolean'; -}; - - -/** - * Returns true if the specified value is a number. - * @param {?} val Variable to test. - * @return {boolean} Whether variable is a number. - */ -goog.isNumber = function(val) { - return typeof val == 'number'; -}; - - -/** - * Builds an object structure for the provided namespace path, ensuring that - * names that already exist are not overwritten. For example: - * "a.b.c" -> a = {};a.b={};a.b.c={}; - * Used by goog.provide and goog.exportSymbol. - * @param {string} name name of the object that this file defines. - * @param {*=} opt_object the object to expose at the end of the path. - * @param {Object=} opt_objectToExportTo The object to add the path to; default - * is `goog.global`. - * @private - */ -goog.exportPath_ = function(name, opt_object, opt_objectToExportTo) { - var parts = name.split('.'); - var cur = opt_objectToExportTo || goog.global; - - // Internet Explorer exhibits strange behavior when throwing errors from - // methods externed in this manner. See the testExportSymbolExceptions in - // base_test.html for an example. - if (!(parts[0] in cur) && cur.execScript) { - cur.execScript('var ' + parts[0]); - } - - for (var part; parts.length && (part = parts.shift());) { - if (!parts.length && goog.isDef(opt_object)) { - // last part and we have an object; use it - cur[part] = opt_object; - } else if (cur[part] && cur[part] !== Object.prototype[part]) { - cur = cur[part]; - } else { - cur = cur[part] = {}; - } - } -}; - - -/** - * Defines a named value. In uncompiled mode, the value is retrieved from - * CLOSURE_DEFINES or CLOSURE_UNCOMPILED_DEFINES if the object is defined and - * has the property specified, and otherwise used the defined defaultValue. - * When compiled the default can be overridden using the compiler - * options or the value set in the CLOSURE_DEFINES object. - * - * @param {string} name The distinguished name to provide. - * @param {string|number|boolean} defaultValue - */ -goog.define = function(name, defaultValue) { - var value = defaultValue; - if (!COMPILED) { - if (goog.global.CLOSURE_UNCOMPILED_DEFINES && - // Anti DOM-clobbering runtime check (b/37736576). - /** @type {?} */ (goog.global.CLOSURE_UNCOMPILED_DEFINES).nodeType === - undefined && - Object.prototype.hasOwnProperty.call( - goog.global.CLOSURE_UNCOMPILED_DEFINES, name)) { - value = goog.global.CLOSURE_UNCOMPILED_DEFINES[name]; - } else if ( - goog.global.CLOSURE_DEFINES && - // Anti DOM-clobbering runtime check (b/37736576). - /** @type {?} */ (goog.global.CLOSURE_DEFINES).nodeType === undefined && - Object.prototype.hasOwnProperty.call( - goog.global.CLOSURE_DEFINES, name)) { - value = goog.global.CLOSURE_DEFINES[name]; - } - } - goog.exportPath_(name, value); -}; - - -/** - * @define {boolean} DEBUG is provided as a convenience so that debugging code - * that should not be included in a production. It can be easily stripped - * by specifying --define goog.DEBUG=false to the Closure Compiler aka - * JSCompiler. For example, most toString() methods should be declared inside an - * "if (goog.DEBUG)" conditional because they are generally used for debugging - * purposes and it is difficult for the JSCompiler to statically determine - * whether they are used. - */ -goog.define('goog.DEBUG', true); - - -/** - * @define {string} LOCALE defines the locale being used for compilation. It is - * used to select locale specific data to be compiled in js binary. BUILD rule - * can specify this value by "--define goog.LOCALE=<locale_name>" as a compiler - * option. - * - * Take into account that the locale code format is important. You should use - * the canonical Unicode format with hyphen as a delimiter. Language must be - * lowercase, Language Script - Capitalized, Region - UPPERCASE. - * There are few examples: pt-BR, en, en-US, sr-Latin-BO, zh-Hans-CN. - * - * See more info about locale codes here: - * http://www.unicode.org/reports/tr35/#Unicode_Language_and_Locale_Identifiers - * - * For language codes you should use values defined by ISO 693-1. See it here - * http://www.w3.org/WAI/ER/IG/ert/iso639.htm. There is only one exception from - * this rule: the Hebrew language. For legacy reasons the old code (iw) should - * be used instead of the new code (he). - * - */ -goog.define('goog.LOCALE', 'en'); // default to en - - -/** - * @define {boolean} Whether this code is running on trusted sites. - * - * On untrusted sites, several native functions can be defined or overridden by - * external libraries like Prototype, Datejs, and JQuery and setting this flag - * to false forces closure to use its own implementations when possible. - * - * If your JavaScript can be loaded by a third party site and you are wary about - * relying on non-standard implementations, specify - * "--define goog.TRUSTED_SITE=false" to the compiler. - */ -goog.define('goog.TRUSTED_SITE', true); - - -/** - * @define {boolean} Whether a project is expected to be running in strict mode. - * - * This define can be used to trigger alternate implementations compatible with - * running in EcmaScript Strict mode or warn about unavailable functionality. - * @see https://goo.gl/PudQ4y - * - */ -goog.define('goog.STRICT_MODE_COMPATIBLE', false); - - -/** - * @define {boolean} Whether code that calls {@link goog.setTestOnly} should - * be disallowed in the compilation unit. - */ -goog.define('goog.DISALLOW_TEST_ONLY_CODE', COMPILED && !goog.DEBUG); - - -/** - * @define {boolean} Whether to use a Chrome app CSP-compliant method for - * loading scripts via goog.require. @see appendScriptSrcNode_. - */ -goog.define('goog.ENABLE_CHROME_APP_SAFE_SCRIPT_LOADING', false); - - -/** - * Defines a namespace in Closure. - * - * A namespace may only be defined once in a codebase. It may be defined using - * goog.provide() or goog.module(). - * - * The presence of one or more goog.provide() calls in a file indicates - * that the file defines the given objects/namespaces. - * Provided symbols must not be null or undefined. - * - * In addition, goog.provide() creates the object stubs for a namespace - * (for example, goog.provide("goog.foo.bar") will create the object - * goog.foo.bar if it does not already exist). - * - * Build tools also scan for provide/require/module statements - * to discern dependencies, build dependency files (see deps.js), etc. - * - * @see goog.require - * @see goog.module - * @param {string} name Namespace provided by this file in the form - * "goog.package.part". - */ -goog.provide = function(name) { - if (goog.isInModuleLoader_()) { - throw Error('goog.provide can not be used within a goog.module.'); - } - if (!COMPILED) { - // Ensure that the same namespace isn't provided twice. - // A goog.module/goog.provide maps a goog.require to a specific file - if (goog.isProvided_(name)) { - throw Error('Namespace "' + name + '" already declared.'); - } - } - - goog.constructNamespace_(name); -}; - - -/** - * @param {string} name Namespace provided by this file in the form - * "goog.package.part". - * @param {Object=} opt_obj The object to embed in the namespace. - * @private - */ -goog.constructNamespace_ = function(name, opt_obj) { - if (!COMPILED) { - delete goog.implicitNamespaces_[name]; - - var namespace = name; - while ((namespace = namespace.substring(0, namespace.lastIndexOf('.')))) { - if (goog.getObjectByName(namespace)) { - break; - } - goog.implicitNamespaces_[namespace] = true; - } - } - - goog.exportPath_(name, opt_obj); -}; - - -/** - * Module identifier validation regexp. - * Note: This is a conservative check, it is very possible to be more lenient, - * the primary exclusion here is "/" and "\" and a leading ".", these - * restrictions are intended to leave the door open for using goog.require - * with relative file paths rather than module identifiers. - * @private - */ -goog.VALID_MODULE_RE_ = /^[a-zA-Z_$][a-zA-Z0-9._$]*$/; - - -/** - * Defines a module in Closure. - * - * Marks that this file must be loaded as a module and claims the namespace. - * - * A namespace may only be defined once in a codebase. It may be defined using - * goog.provide() or goog.module(). - * - * goog.module() has three requirements: - * - goog.module may not be used in the same file as goog.provide. - * - goog.module must be the first statement in the file. - * - only one goog.module is allowed per file. - * - * When a goog.module annotated file is loaded, it is enclosed in - * a strict function closure. This means that: - * - any variables declared in a goog.module file are private to the file - * (not global), though the compiler is expected to inline the module. - * - The code must obey all the rules of "strict" JavaScript. - * - the file will be marked as "use strict" - * - * NOTE: unlike goog.provide, goog.module does not declare any symbols by - * itself. If declared symbols are desired, use - * goog.module.declareLegacyNamespace(). - * - * - * See the public goog.module proposal: http://goo.gl/Va1hin - * - * @param {string} name Namespace provided by this file in the form - * "goog.package.part", is expected but not required. - * @return {void} - */ -goog.module = function(name) { - if (!goog.isString(name) || !name || - name.search(goog.VALID_MODULE_RE_) == -1) { - throw Error('Invalid module identifier'); - } - if (!goog.isInModuleLoader_()) { - throw Error( - 'Module ' + name + ' has been loaded incorrectly. Note, ' + - 'modules cannot be loaded as normal scripts. They require some kind of ' + - 'pre-processing step. You\'re likely trying to load a module via a ' + - 'script tag or as a part of a concatenated bundle without rewriting the ' + - 'module. For more info see: ' + - 'https://github.com/google/closure-library/wiki/goog.module:-an-ES6-module-like-alternative-to-goog.provide.'); - } - if (goog.moduleLoaderState_.moduleName) { - throw Error('goog.module may only be called once per module.'); - } - - // Store the module name for the loader. - goog.moduleLoaderState_.moduleName = name; - if (!COMPILED) { - // Ensure that the same namespace isn't provided twice. - // A goog.module/goog.provide maps a goog.require to a specific file - if (goog.isProvided_(name)) { - throw Error('Namespace "' + name + '" already declared.'); - } - delete goog.implicitNamespaces_[name]; - } -}; - - -/** - * @param {string} name The module identifier. - * @return {?} The module exports for an already loaded module or null. - * - * Note: This is not an alternative to goog.require, it does not - * indicate a hard dependency, instead it is used to indicate - * an optional dependency or to access the exports of a module - * that has already been loaded. - * @suppress {missingProvide} - */ -goog.module.get = function(name) { - return goog.module.getInternal_(name); -}; - - -/** - * @param {string} name The module identifier. - * @return {?} The module exports for an already loaded module or null. - * @private - */ -goog.module.getInternal_ = function(name) { - if (!COMPILED) { - if (name in goog.loadedModules_) { - return goog.loadedModules_[name]; - } else if (!goog.implicitNamespaces_[name]) { - var ns = goog.getObjectByName(name); - return ns != null ? ns : null; - } - } - return null; -}; - - -/** - * @private {?{moduleName: (string|undefined), declareLegacyNamespace:boolean}} - */ -goog.moduleLoaderState_ = null; - - -/** - * @private - * @return {boolean} Whether a goog.module is currently being initialized. - */ -goog.isInModuleLoader_ = function() { - return goog.moduleLoaderState_ != null; -}; - - -/** - * Provide the module's exports as a globally accessible object under the - * module's declared name. This is intended to ease migration to goog.module - * for files that have existing usages. - * @suppress {missingProvide} - */ -goog.module.declareLegacyNamespace = function() { - if (!COMPILED && !goog.isInModuleLoader_()) { - throw new Error( - 'goog.module.declareLegacyNamespace must be called from ' + - 'within a goog.module'); - } - if (!COMPILED && !goog.moduleLoaderState_.moduleName) { - throw Error( - 'goog.module must be called prior to ' + - 'goog.module.declareLegacyNamespace.'); - } - goog.moduleLoaderState_.declareLegacyNamespace = true; -}; - - -/** - * Marks that the current file should only be used for testing, and never for - * live code in production. - * - * In the case of unit tests, the message may optionally be an exact namespace - * for the test (e.g. 'goog.stringTest'). The linter will then ignore the extra - * provide (if not explicitly defined in the code). - * - * @param {string=} opt_message Optional message to add to the error that's - * raised when used in production code. - */ -goog.setTestOnly = function(opt_message) { - if (goog.DISALLOW_TEST_ONLY_CODE) { - opt_message = opt_message || ''; - throw Error( - 'Importing test-only code into non-debug environment' + - (opt_message ? ': ' + opt_message : '.')); - } -}; - - -/** - * Forward declares a symbol. This is an indication to the compiler that the - * symbol may be used in the source yet is not required and may not be provided - * in compilation. - * - * The most common usage of forward declaration is code that takes a type as a - * function parameter but does not need to require it. By forward declaring - * instead of requiring, no hard dependency is made, and (if not required - * elsewhere) the namespace may never be required and thus, not be pulled - * into the JavaScript binary. If it is required elsewhere, it will be type - * checked as normal. - * - * Before using goog.forwardDeclare, please read the documentation at - * https://github.com/google/closure-compiler/wiki/Bad-Type-Annotation to - * understand the options and tradeoffs when working with forward declarations. - * - * @param {string} name The namespace to forward declare in the form of - * "goog.package.part". - */ -goog.forwardDeclare = function(name) {}; - - -/** - * Forward declare type information. Used to assign types to goog.global - * referenced object that would otherwise result in unknown type references - * and thus block property disambiguation. - */ -goog.forwardDeclare('Document'); -goog.forwardDeclare('HTMLScriptElement'); -goog.forwardDeclare('XMLHttpRequest'); - - -if (!COMPILED) { - /** - * Check if the given name has been goog.provided. This will return false for - * names that are available only as implicit namespaces. - * @param {string} name name of the object to look for. - * @return {boolean} Whether the name has been provided. - * @private - */ - goog.isProvided_ = function(name) { - return (name in goog.loadedModules_) || - (!goog.implicitNamespaces_[name] && - goog.isDefAndNotNull(goog.getObjectByName(name))); - }; - - /** - * Namespaces implicitly defined by goog.provide. For example, - * goog.provide('goog.events.Event') implicitly declares that 'goog' and - * 'goog.events' must be namespaces. - * - * @type {!Object<string, (boolean|undefined)>} - * @private - */ - goog.implicitNamespaces_ = {'goog.module': true}; - - // NOTE: We add goog.module as an implicit namespace as goog.module is defined - // here and because the existing module package has not been moved yet out of - // the goog.module namespace. This satisifies both the debug loader and - // ahead-of-time dependency management. -} - - -/** - * Returns an object based on its fully qualified external name. The object - * is not found if null or undefined. If you are using a compilation pass that - * renames property names beware that using this function will not find renamed - * properties. - * - * @param {string} name The fully qualified name. - * @param {Object=} opt_obj The object within which to look; default is - * |goog.global|. - * @return {?} The value (object or primitive) or, if not found, null. - */ -goog.getObjectByName = function(name, opt_obj) { - var parts = name.split('.'); - var cur = opt_obj || goog.global; - for (var part; part = parts.shift();) { - if (goog.isDefAndNotNull(cur[part])) { - cur = cur[part]; - } else { - return null; - } - } - return cur; -}; - - -/** - * Globalizes a whole namespace, such as goog or goog.lang. - * - * @param {!Object} obj The namespace to globalize. - * @param {Object=} opt_global The object to add the properties to. - * @deprecated Properties may be explicitly exported to the global scope, but - * this should no longer be done in bulk. - */ -goog.globalize = function(obj, opt_global) { - var global = opt_global || goog.global; - for (var x in obj) { - global[x] = obj[x]; - } -}; - - -/** - * Adds a dependency from a file to the files it requires. - * @param {string} relPath The path to the js file. - * @param {!Array<string>} provides An array of strings with - * the names of the objects this file provides. - * @param {!Array<string>} requires An array of strings with - * the names of the objects this file requires. - * @param {boolean|!Object<string>=} opt_loadFlags Parameters indicating - * how the file must be loaded. The boolean 'true' is equivalent - * to {'module': 'goog'} for backwards-compatibility. Valid properties - * and values include {'module': 'goog'} and {'lang': 'es6'}. - */ -goog.addDependency = function(relPath, provides, requires, opt_loadFlags) { - if (goog.DEPENDENCIES_ENABLED) { - var provide, require; - var path = relPath.replace(/\\/g, '/'); - var deps = goog.dependencies_; - if (!opt_loadFlags || typeof opt_loadFlags === 'boolean') { - opt_loadFlags = opt_loadFlags ? {'module': 'goog'} : {}; - } - for (var i = 0; provide = provides[i]; i++) { - deps.nameToPath[provide] = path; - deps.loadFlags[path] = opt_loadFlags; - } - for (var j = 0; require = requires[j]; j++) { - if (!(path in deps.requires)) { - deps.requires[path] = {}; - } - deps.requires[path][require] = true; - } - } -}; - - - - -// NOTE(nnaze): The debug DOM loader was included in base.js as an original way -// to do "debug-mode" development. The dependency system can sometimes be -// confusing, as can the debug DOM loader's asynchronous nature. -// -// With the DOM loader, a call to goog.require() is not blocking -- the script -// will not load until some point after the current script. If a namespace is -// needed at runtime, it needs to be defined in a previous script, or loaded via -// require() with its registered dependencies. -// -// User-defined namespaces may need their own deps file. For a reference on -// creating a deps file, see: -// Externally: https://developers.google.com/closure/library/docs/depswriter -// -// Because of legacy clients, the DOM loader can't be easily removed from -// base.js. Work was done to make it disableable or replaceable for -// different environments (DOM-less JavaScript interpreters like Rhino or V8, -// for example). See bootstrap/ for more information. - - -/** - * @define {boolean} Whether to enable the debug loader. - * - * If enabled, a call to goog.require() will attempt to load the namespace by - * appending a script tag to the DOM (if the namespace has been registered). - * - * If disabled, goog.require() will simply assert that the namespace has been - * provided (and depend on the fact that some outside tool correctly ordered - * the script). - */ -goog.define('goog.ENABLE_DEBUG_LOADER', true); - - -/** - * @param {string} msg - * @private - */ -goog.logToConsole_ = function(msg) { - if (goog.global.console) { - goog.global.console['error'](msg); - } -}; - - -/** - * Implements a system for the dynamic resolution of dependencies that works in - * parallel with the BUILD system. Note that all calls to goog.require will be - * stripped by the compiler. - * @see goog.provide - * @param {string} name Namespace to include (as was given in goog.provide()) in - * the form "goog.package.part". - * @return {?} If called within a goog.module file, the associated namespace or - * module otherwise null. - */ -goog.require = function(name) { - // If the object already exists we do not need to do anything. - if (!COMPILED) { - if (goog.ENABLE_DEBUG_LOADER && goog.IS_OLD_IE_) { - goog.maybeProcessDeferredDep_(name); - } - - if (goog.isProvided_(name)) { - if (goog.isInModuleLoader_()) { - return goog.module.getInternal_(name); - } - } else if (goog.ENABLE_DEBUG_LOADER) { - var path = goog.getPathFromDeps_(name); - if (path) { - goog.writeScripts_(path); - } else { - var errorMessage = 'goog.require could not find: ' + name; - goog.logToConsole_(errorMessage); - - throw Error(errorMessage); - } - } - - return null; - } -}; - - -/** - * Path for included scripts. - * @type {string} - */ -goog.basePath = ''; - - -/** - * A hook for overriding the base path. - * @type {string|undefined} - */ -goog.global.CLOSURE_BASE_PATH; - - -/** - * Whether to attempt to load Closure's deps file. By default, when uncompiled, - * deps files will attempt to be loaded. - * @type {boolean|undefined} - */ -goog.global.CLOSURE_NO_DEPS; - - -/** - * A function to import a single script. This is meant to be overridden when - * Closure is being run in non-HTML contexts, such as web workers. It's defined - * in the global scope so that it can be set before base.js is loaded, which - * allows deps.js to be imported properly. - * - * The function is passed the script source, which is a relative URI. It should - * return true if the script was imported, false otherwise. - * @type {(function(string): boolean)|undefined} - */ -goog.global.CLOSURE_IMPORT_SCRIPT; - - -/** - * Null function used for default values of callbacks, etc. - * @return {void} Nothing. - */ -goog.nullFunction = function() {}; - - -/** - * When defining a class Foo with an abstract method bar(), you can do: - * Foo.prototype.bar = goog.abstractMethod - * - * Now if a subclass of Foo fails to override bar(), an error will be thrown - * when bar() is invoked. - * - * @type {!Function} - * @throws {Error} when invoked to indicate the method should be overridden. - */ -goog.abstractMethod = function() { - throw Error('unimplemented abstract method'); -}; - - -/** - * Adds a {@code getInstance} static method that always returns the same - * instance object. - * @param {!Function} ctor The constructor for the class to add the static - * method to. - */ -goog.addSingletonGetter = function(ctor) { - // instance_ is immediately set to prevent issues with sealed constructors - // such as are encountered when a constructor is returned as the export object - // of a goog.module in unoptimized code. - ctor.instance_ = undefined; - ctor.getInstance = function() { - if (ctor.instance_) { - return ctor.instance_; - } - if (goog.DEBUG) { - // NOTE: JSCompiler can't optimize away Array#push. - goog.instantiatedSingletons_[goog.instantiatedSingletons_.length] = ctor; - } - return ctor.instance_ = new ctor; - }; -}; - - -/** - * All singleton classes that have been instantiated, for testing. Don't read - * it directly, use the {@code goog.testing.singleton} module. The compiler - * removes this variable if unused. - * @type {!Array<!Function>} - * @private - */ -goog.instantiatedSingletons_ = []; - - -/** - * @define {boolean} Whether to load goog.modules using {@code eval} when using - * the debug loader. This provides a better debugging experience as the - * source is unmodified and can be edited using Chrome Workspaces or similar. - * However in some environments the use of {@code eval} is banned - * so we provide an alternative. - */ -goog.define('goog.LOAD_MODULE_USING_EVAL', true); - - -/** - * @define {boolean} Whether the exports of goog.modules should be sealed when - * possible. - */ -goog.define('goog.SEAL_MODULE_EXPORTS', goog.DEBUG); - - -/** - * The registry of initialized modules: - * the module identifier to module exports map. - * @private @const {!Object<string, ?>} - */ -goog.loadedModules_ = {}; - - -/** - * True if goog.dependencies_ is available. - * @const {boolean} - */ -goog.DEPENDENCIES_ENABLED = !COMPILED && goog.ENABLE_DEBUG_LOADER; - - -/** - * @define {string} How to decide whether to transpile. Valid values - * are 'always', 'never', and 'detect'. The default ('detect') is to - * use feature detection to determine which language levels need - * transpilation. - */ -// NOTE(user): we could expand this to accept a language level to bypass -// detection: e.g. goog.TRANSPILE == 'es5' would transpile ES6 files but -// would leave ES3 and ES5 files alone. -goog.define('goog.TRANSPILE', 'detect'); - - -/** - * @define {string} Path to the transpiler. Executing the script at this - * path (relative to base.js) should define a function $jscomp.transpile. - */ -goog.define('goog.TRANSPILER', 'transpile.js'); - - -if (goog.DEPENDENCIES_ENABLED) { - /** - * This object is used to keep track of dependencies and other data that is - * used for loading scripts. - * @private - * @type {{ - * loadFlags: !Object<string, !Object<string, string>>, - * nameToPath: !Object<string, string>, - * requires: !Object<string, !Object<string, boolean>>, - * visited: !Object<string, boolean>, - * written: !Object<string, boolean>, - * deferred: !Object<string, string> - * }} - */ - goog.dependencies_ = { - loadFlags: {}, // 1 to 1 - - nameToPath: {}, // 1 to 1 - - requires: {}, // 1 to many - - // Used when resolving dependencies to prevent us from visiting file twice. - visited: {}, - - written: {}, // Used to keep track of script files we have written. - - deferred: {} // Used to track deferred module evaluations in old IEs - }; - - - /** - * Tries to detect whether is in the context of an HTML document. - * @return {boolean} True if it looks like HTML document. - * @private - */ - goog.inHtmlDocument_ = function() { - /** @type {Document} */ - var doc = goog.global.document; - return doc != null && 'write' in doc; // XULDocument misses write. - }; - - - /** - * Tries to detect the base path of base.js script that bootstraps Closure. - * @private - */ - goog.findBasePath_ = function() { - if (goog.isDef(goog.global.CLOSURE_BASE_PATH) && - // Anti DOM-clobbering runtime check (b/37736576). - goog.isString(goog.global.CLOSURE_BASE_PATH)) { - goog.basePath = goog.global.CLOSURE_BASE_PATH; - return; - } else if (!goog.inHtmlDocument_()) { - return; - } - /** @type {Document} */ - var doc = goog.global.document; - // If we have a currentScript available, use it exclusively. - var currentScript = doc.currentScript; - if (currentScript) { - var scripts = [currentScript]; - } else { - var scripts = doc.getElementsByTagName('SCRIPT'); - } - // Search backwards since the current script is in almost all cases the one - // that has base.js. - for (var i = scripts.length - 1; i >= 0; --i) { - var script = /** @type {!HTMLScriptElement} */ (scripts[i]); - var src = script.src; - var qmark = src.lastIndexOf('?'); - var l = qmark == -1 ? src.length : qmark; - if (src.substr(l - 7, 7) == 'base.js') { - goog.basePath = src.substr(0, l - 7); - return; - } - } - }; - - - /** - * Imports a script if, and only if, that script hasn't already been imported. - * (Must be called at execution time) - * @param {string} src Script source. - * @param {string=} opt_sourceText The optionally source text to evaluate - * @private - */ - goog.importScript_ = function(src, opt_sourceText) { - var importScript = - goog.global.CLOSURE_IMPORT_SCRIPT || goog.writeScriptTag_; - if (importScript(src, opt_sourceText)) { - goog.dependencies_.written[src] = true; - } - }; - - - /** - * Whether the browser is IE9 or earlier, which needs special handling - * for deferred modules. - * @const @private {boolean} - */ - goog.IS_OLD_IE_ = - !!(!goog.global.atob && goog.global.document && goog.global.document.all); - - - /** - * Whether IE9 or earlier is waiting on a dependency. This ensures that - * deferred modules that have no non-deferred dependencies actually get - * loaded, since if we defer them and then never pull in a non-deferred - * script, then `goog.loadQueuedModules_` will never be called. Instead, - * if not waiting on anything we simply don't defer in the first place. - * @private {boolean} - */ - goog.oldIeWaiting_ = false; - - - /** - * Given a URL initiate retrieval and execution of a script that needs - * pre-processing. - * @param {string} src Script source URL. - * @param {boolean} isModule Whether this is a goog.module. - * @param {boolean} needsTranspile Whether this source needs transpilation. - * @private - */ - goog.importProcessedScript_ = function(src, isModule, needsTranspile) { - // In an attempt to keep browsers from timing out loading scripts using - // synchronous XHRs, put each load in its own script block. - var bootstrap = 'goog.retrieveAndExec_("' + src + '", ' + isModule + ', ' + - needsTranspile + ');'; - - goog.importScript_('', bootstrap); - }; - - - /** @private {!Array<string>} */ - goog.queuedModules_ = []; - - - /** - * Return an appropriate module text. Suitable to insert into - * a script tag (that is unescaped). - * @param {string} srcUrl - * @param {string} scriptText - * @return {string} - * @private - */ - goog.wrapModule_ = function(srcUrl, scriptText) { - if (!goog.LOAD_MODULE_USING_EVAL || !goog.isDef(goog.global.JSON)) { - return '' + - 'goog.loadModule(function(exports) {' + - '"use strict";' + scriptText + - '\n' + // terminate any trailing single line comment. - ';return exports' + - '});' + - '\n//# sourceURL=' + srcUrl + '\n'; - } else { - return '' + - 'goog.loadModule(' + - goog.global.JSON.stringify( - scriptText + '\n//# sourceURL=' + srcUrl + '\n') + - ');'; - } - }; - - // On IE9 and earlier, it is necessary to handle - // deferred module loads. In later browsers, the - // code to be evaluated is simply inserted as a script - // block in the correct order. To eval deferred - // code at the right time, we piggy back on goog.require to call - // goog.maybeProcessDeferredDep_. - // - // The goog.requires are used both to bootstrap - // the loading process (when no deps are available) and - // declare that they should be available. - // - // Here we eval the sources, if all the deps are available - // either already eval'd or goog.require'd. This will - // be the case when all the dependencies have already - // been loaded, and the dependent module is loaded. - // - // But this alone isn't sufficient because it is also - // necessary to handle the case where there is no root - // that is not deferred. For that there we register for an event - // and trigger goog.loadQueuedModules_ handle any remaining deferred - // evaluations. - - /** - * Handle any remaining deferred goog.module evals. - * @private - */ - goog.loadQueuedModules_ = function() { - var count = goog.queuedModules_.length; - if (count > 0) { - var queue = goog.queuedModules_; - goog.queuedModules_ = []; - for (var i = 0; i < count; i++) { - var path = queue[i]; - goog.maybeProcessDeferredPath_(path); - } - } - goog.oldIeWaiting_ = false; - }; - - - /** - * Eval the named module if its dependencies are - * available. - * @param {string} name The module to load. - * @private - */ - goog.maybeProcessDeferredDep_ = function(name) { - if (goog.isDeferredModule_(name) && goog.allDepsAreAvailable_(name)) { - var path = goog.getPathFromDeps_(name); - goog.maybeProcessDeferredPath_(goog.basePath + path); - } - }; - - /** - * @param {string} name The module to check. - * @return {boolean} Whether the name represents a - * module whose evaluation has been deferred. - * @private - */ - goog.isDeferredModule_ = function(name) { - var path = goog.getPathFromDeps_(name); - var loadFlags = path && goog.dependencies_.loadFlags[path] || {}; - var languageLevel = loadFlags['lang'] || 'es3'; - if (path && (loadFlags['module'] == 'goog' || - goog.needsTranspile_(languageLevel))) { - var abspath = goog.basePath + path; - return (abspath) in goog.dependencies_.deferred; - } - return false; - }; - - /** - * @param {string} name The module to check. - * @return {boolean} Whether the name represents a - * module whose declared dependencies have all been loaded - * (eval'd or a deferred module load) - * @private - */ - goog.allDepsAreAvailable_ = function(name) { - var path = goog.getPathFromDeps_(name); - if (path && (path in goog.dependencies_.requires)) { - for (var requireName in goog.dependencies_.requires[path]) { - if (!goog.isProvided_(requireName) && - !goog.isDeferredModule_(requireName)) { - return false; - } - } - } - return true; - }; - - - /** - * @param {string} abspath - * @private - */ - goog.maybeProcessDeferredPath_ = function(abspath) { - if (abspath in goog.dependencies_.deferred) { - var src = goog.dependencies_.deferred[abspath]; - delete goog.dependencies_.deferred[abspath]; - goog.globalEval(src); - } - }; - - - /** - * Load a goog.module from the provided URL. This is not a general purpose - * code loader and does not support late loading code, that is it should only - * be used during page load. This method exists to support unit tests and - * "debug" loaders that would otherwise have inserted script tags. Under the - * hood this needs to use a synchronous XHR and is not recommeneded for - * production code. - * - * The module's goog.requires must have already been satisified; an exception - * will be thrown if this is not the case. This assumption is that no - * "deps.js" file exists, so there is no way to discover and locate the - * module-to-be-loaded's dependencies and no attempt is made to do so. - * - * There should only be one attempt to load a module. If - * "goog.loadModuleFromUrl" is called for an already loaded module, an - * exception will be throw. - * - * @param {string} url The URL from which to attempt to load the goog.module. - */ - goog.loadModuleFromUrl = function(url) { - // Because this executes synchronously, we don't need to do any additional - // bookkeeping. When "goog.loadModule" the namespace will be marked as - // having been provided which is sufficient. - goog.retrieveAndExec_(url, true, false); - }; - - - /** - * Writes a new script pointing to {@code src} directly into the DOM. - * - * NOTE: This method is not CSP-compliant. @see goog.appendScriptSrcNode_ for - * the fallback mechanism. - * - * @param {string} src The script URL. - * @private - */ - goog.writeScriptSrcNode_ = function(src) { - goog.global.document.write( - '<script type="text/javascript" src="' + src + '"></' + - 'script>'); - }; - - - /** - * Appends a new script node to the DOM using a CSP-compliant mechanism. This - * method exists as a fallback for document.write (which is not allowed in a - * strict CSP context, e.g., Chrome apps). - * - * NOTE: This method is not analogous to using document.write to insert a - * <script> tag; specifically, the user agent will execute a script added by - * document.write immediately after the current script block finishes - * executing, whereas the DOM-appended script node will not be executed until - * the entire document is parsed and executed. That is to say, this script is - * added to the end of the script execution queue. - * - * The page must not attempt to call goog.required entities until after the - * document has loaded, e.g., in or after the window.onload callback. - * - * @param {string} src The script URL. - * @private - */ - goog.appendScriptSrcNode_ = function(src) { - /** @type {Document} */ - var doc = goog.global.document; - var scriptEl = - /** @type {HTMLScriptElement} */ (doc.createElement('script')); - scriptEl.type = 'text/javascript'; - scriptEl.src = src; - scriptEl.defer = false; - scriptEl.async = false; - doc.head.appendChild(scriptEl); - }; - - - /** - * The default implementation of the import function. Writes a script tag to - * import the script. - * - * @param {string} src The script url. - * @param {string=} opt_sourceText The optionally source text to evaluate - * @return {boolean} True if the script was imported, false otherwise. - * @private - */ - goog.writeScriptTag_ = function(src, opt_sourceText) { - if (goog.inHtmlDocument_()) { - /** @type {!HTMLDocument} */ - var doc = goog.global.document; - - // If the user tries to require a new symbol after document load, - // something has gone terribly wrong. Doing a document.write would - // wipe out the page. This does not apply to the CSP-compliant method - // of writing script tags. - if (!goog.ENABLE_CHROME_APP_SAFE_SCRIPT_LOADING && - doc.readyState == 'complete') { - // Certain test frameworks load base.js multiple times, which tries - // to write deps.js each time. If that happens, just fail silently. - // These frameworks wipe the page between each load of base.js, so this - // is OK. - var isDeps = /\bdeps.js$/.test(src); - if (isDeps) { - return false; - } else { - throw Error('Cannot write "' + src + '" after document load'); - } - } - - if (opt_sourceText === undefined) { - if (!goog.IS_OLD_IE_) { - if (goog.ENABLE_CHROME_APP_SAFE_SCRIPT_LOADING) { - goog.appendScriptSrcNode_(src); - } else { - goog.writeScriptSrcNode_(src); - } - } else { - goog.oldIeWaiting_ = true; - var state = ' onreadystatechange=\'goog.onScriptLoad_(this, ' + - ++goog.lastNonModuleScriptIndex_ + ')\' '; - doc.write( - '<script type="text/javascript" src="' + src + '"' + state + - '></' + - 'script>'); - } - } else { - doc.write( - '<script type="text/javascript">' + - goog.protectScriptTag_(opt_sourceText) + '</' + - 'script>'); - } - return true; - } else { - return false; - } - }; - - /** - * Rewrites closing script tags in input to avoid ending an enclosing script - * tag. - * - * @param {string} str - * @return {string} - * @private - */ - goog.protectScriptTag_ = function(str) { - return str.replace(/<\/(SCRIPT)/ig, '\\x3c/$1'); - }; - - /** - * Determines whether the given language needs to be transpiled. - * @param {string} lang - * @return {boolean} - * @private - */ - goog.needsTranspile_ = function(lang) { - if (goog.TRANSPILE == 'always') { - return true; - } else if (goog.TRANSPILE == 'never') { - return false; - } else if (!goog.requiresTranspilation_) { - goog.requiresTranspilation_ = goog.createRequiresTranspilation_(); - } - if (lang in goog.requiresTranspilation_) { - return goog.requiresTranspilation_[lang]; - } else { - throw new Error('Unknown language mode: ' + lang); - } - }; - - /** @private {?Object<string, boolean>} */ - goog.requiresTranspilation_ = null; - - - /** @private {number} */ - goog.lastNonModuleScriptIndex_ = 0; - - - /** - * A readystatechange handler for legacy IE - * @param {?} script - * @param {number} scriptIndex - * @return {boolean} - * @private - */ - goog.onScriptLoad_ = function(script, scriptIndex) { - // for now load the modules when we reach the last script, - // later allow more inter-mingling. - if (script.readyState == 'complete' && - goog.lastNonModuleScriptIndex_ == scriptIndex) { - goog.loadQueuedModules_(); - } - return true; - }; - - /** - * Resolves dependencies based on the dependencies added using addDependency - * and calls importScript_ in the correct order. - * @param {string} pathToLoad The path from which to start discovering - * dependencies. - * @private - */ - goog.writeScripts_ = function(pathToLoad) { - /** @type {!Array<string>} The scripts we need to write this time. */ - var scripts = []; - var seenScript = {}; - var deps = goog.dependencies_; - - /** @param {string} path */ - function visitNode(path) { - if (path in deps.written) { - return; - } - - // We have already visited this one. We can get here if we have cyclic - // dependencies. - if (path in deps.visited) { - return; - } - - deps.visited[path] = true; - - if (path in deps.requires) { - for (var requireName in deps.requires[path]) { - // If the required name is defined, we assume that it was already - // bootstrapped by other means. - if (!goog.isProvided_(requireName)) { - if (requireName in deps.nameToPath) { - visitNode(deps.nameToPath[requireName]); - } else { - throw Error('Undefined nameToPath for ' + requireName); - } - } - } - } - - if (!(path in seenScript)) { - seenScript[path] = true; - scripts.push(path); - } - } - - visitNode(pathToLoad); - - // record that we are going to load all these scripts. - for (var i = 0; i < scripts.length; i++) { - var path = scripts[i]; - goog.dependencies_.written[path] = true; - } - - // If a module is loaded synchronously then we need to - // clear the current inModuleLoader value, and restore it when we are - // done loading the current "requires". - var moduleState = goog.moduleLoaderState_; - goog.moduleLoaderState_ = null; - - for (var i = 0; i < scripts.length; i++) { - var path = scripts[i]; - if (path) { - var loadFlags = deps.loadFlags[path] || {}; - var languageLevel = loadFlags['lang'] || 'es3'; - var needsTranspile = goog.needsTranspile_(languageLevel); - if (loadFlags['module'] == 'goog' || needsTranspile) { - goog.importProcessedScript_( - goog.basePath + path, loadFlags['module'] == 'goog', - needsTranspile); - } else { - goog.importScript_(goog.basePath + path); - } - } else { - goog.moduleLoaderState_ = moduleState; - throw Error('Undefined script input'); - } - } - - // restore the current "module loading state" - goog.moduleLoaderState_ = moduleState; - }; - - - /** - * Looks at the dependency rules and tries to determine the script file that - * fulfills a particular rule. - * @param {string} rule In the form goog.namespace.Class or project.script. - * @return {?string} Url corresponding to the rule, or null. - * @private - */ - goog.getPathFromDeps_ = function(rule) { - if (rule in goog.dependencies_.nameToPath) { - return goog.dependencies_.nameToPath[rule]; - } else { - return null; - } - }; - - goog.findBasePath_(); - - // Allow projects to manage the deps files themselves. - if (!goog.global.CLOSURE_NO_DEPS) { - goog.importScript_(goog.basePath + 'deps.js'); - } -} - - -/** - * @package {?boolean} - * Visible for testing. - */ -goog.hasBadLetScoping = null; - - -/** - * @return {boolean} - * @package Visible for testing. - */ -goog.useSafari10Workaround = function() { - if (goog.hasBadLetScoping == null) { - var hasBadLetScoping; - try { - hasBadLetScoping = !eval( - '"use strict";' + - 'let x = 1; function f() { return typeof x; };' + - 'f() == "number";'); - } catch (e) { - // Assume that ES6 syntax isn't supported. - hasBadLetScoping = false; - } - goog.hasBadLetScoping = hasBadLetScoping; - } - return goog.hasBadLetScoping; -}; - - -/** - * @param {string} moduleDef - * @return {string} - * @package Visible for testing. - */ -goog.workaroundSafari10EvalBug = function(moduleDef) { - return '(function(){' + moduleDef + - '\n' + // Terminate any trailing single line comment. - ';' + // Terminate any trailing expression. - '})();\n'; -}; - - -/** - * @param {function(?):?|string} moduleDef The module definition. - */ -goog.loadModule = function(moduleDef) { - // NOTE: we allow function definitions to be either in the from - // of a string to eval (which keeps the original source intact) or - // in a eval forbidden environment (CSP) we allow a function definition - // which in its body must call {@code goog.module}, and return the exports - // of the module. - var previousState = goog.moduleLoaderState_; - try { - goog.moduleLoaderState_ = { - moduleName: undefined, - declareLegacyNamespace: false - }; - var exports; - if (goog.isFunction(moduleDef)) { - exports = moduleDef.call(undefined, {}); - } else if (goog.isString(moduleDef)) { - if (goog.useSafari10Workaround()) { - moduleDef = goog.workaroundSafari10EvalBug(moduleDef); - } - - exports = goog.loadModuleFromSource_.call(undefined, moduleDef); - } else { - throw Error('Invalid module definition'); - } - - var moduleName = goog.moduleLoaderState_.moduleName; - if (!goog.isString(moduleName) || !moduleName) { - throw Error('Invalid module name \"' + moduleName + '\"'); - } - - // Don't seal legacy namespaces as they may be uses as a parent of - // another namespace - if (goog.moduleLoaderState_.declareLegacyNamespace) { - goog.constructNamespace_(moduleName, exports); - } else if ( - goog.SEAL_MODULE_EXPORTS && Object.seal && typeof exports == 'object' && - exports != null) { - Object.seal(exports); - } - - goog.loadedModules_[moduleName] = exports; - } finally { - goog.moduleLoaderState_ = previousState; - } -}; - - -/** - * @private @const - */ -goog.loadModuleFromSource_ = /** @type {function(string):?} */ (function() { - // NOTE: we avoid declaring parameters or local variables here to avoid - // masking globals or leaking values into the module definition. - 'use strict'; - var exports = {}; - eval(arguments[0]); - return exports; -}); - - -/** - * Normalize a file path by removing redundant ".." and extraneous "." file - * path components. - * @param {string} path - * @return {string} - * @private - */ -goog.normalizePath_ = function(path) { - var components = path.split('/'); - var i = 0; - while (i < components.length) { - if (components[i] == '.') { - components.splice(i, 1); - } else if ( - i && components[i] == '..' && components[i - 1] && - components[i - 1] != '..') { - components.splice(--i, 2); - } else { - i++; - } - } - return components.join('/'); -}; - - -/** - * Provides a hook for loading a file when using Closure's goog.require() API - * with goog.modules. In particular this hook is provided to support Node.js. - * - * @type {(function(string):string)|undefined} - */ -goog.global.CLOSURE_LOAD_FILE_SYNC; - - -/** - * Loads file by synchronous XHR. Should not be used in production environments. - * @param {string} src Source URL. - * @return {?string} File contents, or null if load failed. - * @private - */ -goog.loadFileSync_ = function(src) { - if (goog.global.CLOSURE_LOAD_FILE_SYNC) { - return goog.global.CLOSURE_LOAD_FILE_SYNC(src); - } else { - try { - /** @type {XMLHttpRequest} */ - var xhr = new goog.global['XMLHttpRequest'](); - xhr.open('get', src, false); - xhr.send(); - // NOTE: Successful http: requests have a status of 200, but successful - // file: requests may have a status of zero. Any other status, or a - // thrown exception (particularly in case of file: requests) indicates - // some sort of error, which we treat as a missing or unavailable file. - return xhr.status == 0 || xhr.status == 200 ? xhr.responseText : null; - } catch (err) { - // No need to rethrow or log, since errors should show up on their own. - return null; - } - } -}; - - -/** - * Retrieve and execute a script that needs some sort of wrapping. - * @param {string} src Script source URL. - * @param {boolean} isModule Whether to load as a module. - * @param {boolean} needsTranspile Whether to transpile down to ES3. - * @private - */ -goog.retrieveAndExec_ = function(src, isModule, needsTranspile) { - if (!COMPILED) { - // The full but non-canonicalized URL for later use. - var originalPath = src; - // Canonicalize the path, removing any /./ or /../ since Chrome's debugging - // console doesn't auto-canonicalize XHR loads as it does <script> srcs. - src = goog.normalizePath_(src); - - var importScript = - goog.global.CLOSURE_IMPORT_SCRIPT || goog.writeScriptTag_; - - var scriptText = goog.loadFileSync_(src); - if (scriptText == null) { - throw new Error('Load of "' + src + '" failed'); - } - - if (needsTranspile) { - scriptText = goog.transpile_.call(goog.global, scriptText, src); - } - - if (isModule) { - scriptText = goog.wrapModule_(src, scriptText); - } else { - scriptText += '\n//# sourceURL=' + src; - } - var isOldIE = goog.IS_OLD_IE_; - if (isOldIE && goog.oldIeWaiting_) { - goog.dependencies_.deferred[originalPath] = scriptText; - goog.queuedModules_.push(originalPath); - } else { - importScript(src, scriptText); - } - } -}; - - -/** - * Lazily retrieves the transpiler and applies it to the source. - * @param {string} code JS code. - * @param {string} path Path to the code. - * @return {string} The transpiled code. - * @private - */ -goog.transpile_ = function(code, path) { - var jscomp = goog.global['$jscomp']; - if (!jscomp) { - goog.global['$jscomp'] = jscomp = {}; - } - var transpile = jscomp.transpile; - if (!transpile) { - var transpilerPath = goog.basePath + goog.TRANSPILER; - var transpilerCode = goog.loadFileSync_(transpilerPath); - if (transpilerCode) { - // This must be executed synchronously, since by the time we know we - // need it, we're about to load and write the ES6 code synchronously, - // so a normal script-tag load will be too slow. - eval(transpilerCode + '\n//# sourceURL=' + transpilerPath); - // Even though the transpiler is optional, if $gwtExport is found, it's - // a sign the transpiler was loaded and the $jscomp.transpile *should* - // be there. - if (goog.global['$gwtExport'] && goog.global['$gwtExport']['$jscomp'] && - !goog.global['$gwtExport']['$jscomp']['transpile']) { - throw new Error( - 'The transpiler did not properly export the "transpile" ' + - 'method. $gwtExport: ' + JSON.stringify(goog.global['$gwtExport'])); - } - // transpile.js only exports a single $jscomp function, transpile. We - // grab just that and add it to the existing definition of $jscomp which - // contains the polyfills. - goog.global['$jscomp'].transpile = - goog.global['$gwtExport']['$jscomp']['transpile']; - jscomp = goog.global['$jscomp']; - transpile = jscomp.transpile; - } - } - if (!transpile) { - // The transpiler is an optional component. If it's not available then - // replace it with a pass-through function that simply logs. - var suffix = ' requires transpilation but no transpiler was found.'; - transpile = jscomp.transpile = function(code, path) { - // TODO(user): figure out some way to get this error to show up - // in test results, noting that the failure may occur in many - // different ways, including in loadModule() before the test - // runner even comes up. - goog.logToConsole_(path + suffix); - return code; - }; - } - // Note: any transpilation errors/warnings will be logged to the console. - return transpile(code, path); -}; - - -//============================================================================== -// Language Enhancements -//============================================================================== - - -/** - * This is a "fixed" version of the typeof operator. It differs from the typeof - * operator in such a way that null returns 'null' and arrays return 'array'. - * @param {?} value The value to get the type of. - * @return {string} The name of the type. - */ -goog.typeOf = function(value) { - var s = typeof value; - if (s == 'object') { - if (value) { - // Check these first, so we can avoid calling Object.prototype.toString if - // possible. - // - // IE improperly marshals typeof across execution contexts, but a - // cross-context object will still return false for "instanceof Object". - if (value instanceof Array) { - return 'array'; - } else if (value instanceof Object) { - return s; - } - - // HACK: In order to use an Object prototype method on the arbitrary - // value, the compiler requires the value be cast to type Object, - // even though the ECMA spec explicitly allows it. - var className = Object.prototype.toString.call( - /** @type {!Object} */ (value)); - // In Firefox 3.6, attempting to access iframe window objects' length - // property throws an NS_ERROR_FAILURE, so we need to special-case it - // here. - if (className == '[object Window]') { - return 'object'; - } - - // We cannot always use constructor == Array or instanceof Array because - // different frames have different Array objects. In IE6, if the iframe - // where the array was created is destroyed, the array loses its - // prototype. Then dereferencing val.splice here throws an exception, so - // we can't use goog.isFunction. Calling typeof directly returns 'unknown' - // so that will work. In this case, this function will return false and - // most array functions will still work because the array is still - // array-like (supports length and []) even though it has lost its - // prototype. - // Mark Miller noticed that Object.prototype.toString - // allows access to the unforgeable [[Class]] property. - // 15.2.4.2 Object.prototype.toString ( ) - // When the toString method is called, the following steps are taken: - // 1. Get the [[Class]] property of this object. - // 2. Compute a string value by concatenating the three strings - // "[object ", Result(1), and "]". - // 3. Return Result(2). - // and this behavior survives the destruction of the execution context. - if ((className == '[object Array]' || - // In IE all non value types are wrapped as objects across window - // boundaries (not iframe though) so we have to do object detection - // for this edge case. - typeof value.length == 'number' && - typeof value.splice != 'undefined' && - typeof value.propertyIsEnumerable != 'undefined' && - !value.propertyIsEnumerable('splice') - - )) { - return 'array'; - } - // HACK: There is still an array case that fails. - // function ArrayImpostor() {} - // ArrayImpostor.prototype = []; - // var impostor = new ArrayImpostor; - // this can be fixed by getting rid of the fast path - // (value instanceof Array) and solely relying on - // (value && Object.prototype.toString.vall(value) === '[object Array]') - // but that would require many more function calls and is not warranted - // unless closure code is receiving objects from untrusted sources. - - // IE in cross-window calls does not correctly marshal the function type - // (it appears just as an object) so we cannot use just typeof val == - // 'function'. However, if the object has a call property, it is a - // function. - if ((className == '[object Function]' || - typeof value.call != 'undefined' && - typeof value.propertyIsEnumerable != 'undefined' && - !value.propertyIsEnumerable('call'))) { - return 'function'; - } - - } else { - return 'null'; - } - - } else if (s == 'function' && typeof value.call == 'undefined') { - // In Safari typeof nodeList returns 'function', and on Firefox typeof - // behaves similarly for HTML{Applet,Embed,Object}, Elements and RegExps. We - // would like to return object for those and we can detect an invalid - // function by making sure that the function object has a call method. - return 'object'; - } - return s; -}; - - -/** - * Returns true if the specified value is null. - * @param {?} val Variable to test. - * @return {boolean} Whether variable is null. - */ -goog.isNull = function(val) { - return val === null; -}; - - -/** - * Returns true if the specified value is defined and not null. - * @param {?} val Variable to test. - * @return {boolean} Whether variable is defined and not null. - */ -goog.isDefAndNotNull = function(val) { - // Note that undefined == null. - return val != null; -}; - - -/** - * Returns true if the specified value is an array. - * @param {?} val Variable to test. - * @return {boolean} Whether variable is an array. - */ -goog.isArray = function(val) { - return goog.typeOf(val) == 'array'; -}; - - -/** - * Returns true if the object looks like an array. To qualify as array like - * the value needs to be either a NodeList or an object with a Number length - * property. As a special case, a function value is not array like, because its - * length property is fixed to correspond to the number of expected arguments. - * @param {?} val Variable to test. - * @return {boolean} Whether variable is an array. - */ -goog.isArrayLike = function(val) { - var type = goog.typeOf(val); - // We do not use goog.isObject here in order to exclude function values. - return type == 'array' || type == 'object' && typeof val.length == 'number'; -}; - - -/** - * Returns true if the object looks like a Date. To qualify as Date-like the - * value needs to be an object and have a getFullYear() function. - * @param {?} val Variable to test. - * @return {boolean} Whether variable is a like a Date. - */ -goog.isDateLike = function(val) { - return goog.isObject(val) && typeof val.getFullYear == 'function'; -}; - - -/** - * Returns true if the specified value is a function. - * @param {?} val Variable to test. - * @return {boolean} Whether variable is a function. - */ -goog.isFunction = function(val) { - return goog.typeOf(val) == 'function'; -}; - - -/** - * Returns true if the specified value is an object. This includes arrays and - * functions. - * @param {?} val Variable to test. - * @return {boolean} Whether variable is an object. - */ -goog.isObject = function(val) { - var type = typeof val; - return type == 'object' && val != null || type == 'function'; - // return Object(val) === val also works, but is slower, especially if val is - // not an object. -}; - - -/** - * Gets a unique ID for an object. This mutates the object so that further calls - * with the same object as a parameter returns the same value. The unique ID is - * guaranteed to be unique across the current session amongst objects that are - * passed into {@code getUid}. There is no guarantee that the ID is unique or - * consistent across sessions. It is unsafe to generate unique ID for function - * prototypes. - * - * @param {Object} obj The object to get the unique ID for. - * @return {number} The unique ID for the object. - */ -goog.getUid = function(obj) { - // TODO(arv): Make the type stricter, do not accept null. - - // In Opera window.hasOwnProperty exists but always returns false so we avoid - // using it. As a consequence the unique ID generated for BaseClass.prototype - // and SubClass.prototype will be the same. - return obj[goog.UID_PROPERTY_] || - (obj[goog.UID_PROPERTY_] = ++goog.uidCounter_); -}; - - -/** - * Whether the given object is already assigned a unique ID. - * - * This does not modify the object. - * - * @param {!Object} obj The object to check. - * @return {boolean} Whether there is an assigned unique id for the object. - */ -goog.hasUid = function(obj) { - return !!obj[goog.UID_PROPERTY_]; -}; - - -/** - * Removes the unique ID from an object. This is useful if the object was - * previously mutated using {@code goog.getUid} in which case the mutation is - * undone. - * @param {Object} obj The object to remove the unique ID field from. - */ -goog.removeUid = function(obj) { - // TODO(arv): Make the type stricter, do not accept null. - - // In IE, DOM nodes are not instances of Object and throw an exception if we - // try to delete. Instead we try to use removeAttribute. - if (obj !== null && 'removeAttribute' in obj) { - obj.removeAttribute(goog.UID_PROPERTY_); - } - - try { - delete obj[goog.UID_PROPERTY_]; - } catch (ex) { - } -}; - - -/** - * Name for unique ID property. Initialized in a way to help avoid collisions - * with other closure JavaScript on the same page. - * @type {string} - * @private - */ -goog.UID_PROPERTY_ = 'closure_uid_' + ((Math.random() * 1e9) >>> 0); - - -/** - * Counter for UID. - * @type {number} - * @private - */ -goog.uidCounter_ = 0; - - -/** - * Adds a hash code field to an object. The hash code is unique for the - * given object. - * @param {Object} obj The object to get the hash code for. - * @return {number} The hash code for the object. - * @deprecated Use goog.getUid instead. - */ -goog.getHashCode = goog.getUid; - - -/** - * Removes the hash code field from an object. - * @param {Object} obj The object to remove the field from. - * @deprecated Use goog.removeUid instead. - */ -goog.removeHashCode = goog.removeUid; - - -/** - * Clones a value. The input may be an Object, Array, or basic type. Objects and - * arrays will be cloned recursively. - * - * WARNINGS: - * <code>goog.cloneObject</code> does not detect reference loops. Objects that - * refer to themselves will cause infinite recursion. - * - * <code>goog.cloneObject</code> is unaware of unique identifiers, and copies - * UIDs created by <code>getUid</code> into cloned results. - * - * @param {*} obj The value to clone. - * @return {*} A clone of the input value. - * @deprecated goog.cloneObject is unsafe. Prefer the goog.object methods. - */ -goog.cloneObject = function(obj) { - var type = goog.typeOf(obj); - if (type == 'object' || type == 'array') { - if (obj.clone) { - return obj.clone(); - } - var clone = type == 'array' ? [] : {}; - for (var key in obj) { - clone[key] = goog.cloneObject(obj[key]); - } - return clone; - } - - return obj; -}; - - -/** - * A native implementation of goog.bind. - * @param {?function(this:T, ...)} fn A function to partially apply. - * @param {T} selfObj Specifies the object which this should point to when the - * function is run. - * @param {...*} var_args Additional arguments that are partially applied to the - * function. - * @return {!Function} A partially-applied form of the function goog.bind() was - * invoked as a method of. - * @template T - * @private - */ -goog.bindNative_ = function(fn, selfObj, var_args) { - return /** @type {!Function} */ (fn.call.apply(fn.bind, arguments)); -}; - - -/** - * A pure-JS implementation of goog.bind. - * @param {?function(this:T, ...)} fn A function to partially apply. - * @param {T} selfObj Specifies the object which this should point to when the - * function is run. - * @param {...*} var_args Additional arguments that are partially applied to the - * function. - * @return {!Function} A partially-applied form of the function goog.bind() was - * invoked as a method of. - * @template T - * @private - */ -goog.bindJs_ = function(fn, selfObj, var_args) { - if (!fn) { - throw new Error(); - } - - if (arguments.length > 2) { - var boundArgs = Array.prototype.slice.call(arguments, 2); - return function() { - // Prepend the bound arguments to the current arguments. - var newArgs = Array.prototype.slice.call(arguments); - Array.prototype.unshift.apply(newArgs, boundArgs); - return fn.apply(selfObj, newArgs); - }; - - } else { - return function() { - return fn.apply(selfObj, arguments); - }; - } -}; - - -/** - * Partially applies this function to a particular 'this object' and zero or - * more arguments. The result is a new function with some arguments of the first - * function pre-filled and the value of this 'pre-specified'. - * - * Remaining arguments specified at call-time are appended to the pre-specified - * ones. - * - * Also see: {@link #partial}. - * - * Usage: - * <pre>var barMethBound = goog.bind(myFunction, myObj, 'arg1', 'arg2'); - * barMethBound('arg3', 'arg4');</pre> - * - * @param {?function(this:T, ...)} fn A function to partially apply. - * @param {T} selfObj Specifies the object which this should point to when the - * function is run. - * @param {...*} var_args Additional arguments that are partially applied to the - * function. - * @return {!Function} A partially-applied form of the function goog.bind() was - * invoked as a method of. - * @template T - * @suppress {deprecated} See above. - */ -goog.bind = function(fn, selfObj, var_args) { - // TODO(nicksantos): narrow the type signature. - if (Function.prototype.bind && - // NOTE(nicksantos): Somebody pulled base.js into the default Chrome - // extension environment. This means that for Chrome extensions, they get - // the implementation of Function.prototype.bind that calls goog.bind - // instead of the native one. Even worse, we don't want to introduce a - // circular dependency between goog.bind and Function.prototype.bind, so - // we have to hack this to make sure it works correctly. - Function.prototype.bind.toString().indexOf('native code') != -1) { - goog.bind = goog.bindNative_; - } else { - goog.bind = goog.bindJs_; - } - return goog.bind.apply(null, arguments); -}; - - -/** - * Like goog.bind(), except that a 'this object' is not required. Useful when - * the target function is already bound. - * - * Usage: - * var g = goog.partial(f, arg1, arg2); - * g(arg3, arg4); - * - * @param {Function} fn A function to partially apply. - * @param {...*} var_args Additional arguments that are partially applied to fn. - * @return {!Function} A partially-applied form of the function goog.partial() - * was invoked as a method of. - */ -goog.partial = function(fn, var_args) { - var args = Array.prototype.slice.call(arguments, 1); - return function() { - // Clone the array (with slice()) and append additional arguments - // to the existing arguments. - var newArgs = args.slice(); - newArgs.push.apply(newArgs, arguments); - return fn.apply(this, newArgs); - }; -}; - - -/** - * Copies all the members of a source object to a target object. This method - * does not work on all browsers for all objects that contain keys such as - * toString or hasOwnProperty. Use goog.object.extend for this purpose. - * @param {Object} target Target. - * @param {Object} source Source. - */ -goog.mixin = function(target, source) { - for (var x in source) { - target[x] = source[x]; - } - - // For IE7 or lower, the for-in-loop does not contain any properties that are - // not enumerable on the prototype object (for example, isPrototypeOf from - // Object.prototype) but also it will not include 'replace' on objects that - // extend String and change 'replace' (not that it is common for anyone to - // extend anything except Object). -}; - - -/** - * @return {number} An integer value representing the number of milliseconds - * between midnight, January 1, 1970 and the current time. - */ -goog.now = (goog.TRUSTED_SITE && Date.now) || (function() { - // Unary plus operator converts its operand to a number which in - // the case of - // a date is done by calling getTime(). - return +new Date(); - }); - - -/** - * Evals JavaScript in the global scope. In IE this uses execScript, other - * browsers use goog.global.eval. If goog.global.eval does not evaluate in the - * global scope (for example, in Safari), appends a script tag instead. - * Throws an exception if neither execScript or eval is defined. - * @param {string} script JavaScript string. - */ -goog.globalEval = function(script) { - if (goog.global.execScript) { - goog.global.execScript(script, 'JavaScript'); - } else if (goog.global.eval) { - // Test to see if eval works - if (goog.evalWorksForGlobals_ == null) { - goog.global.eval('var _evalTest_ = 1;'); - if (typeof goog.global['_evalTest_'] != 'undefined') { - try { - delete goog.global['_evalTest_']; - } catch (ignore) { - // Microsoft edge fails the deletion above in strict mode. - } - goog.evalWorksForGlobals_ = true; - } else { - goog.evalWorksForGlobals_ = false; - } - } - - if (goog.evalWorksForGlobals_) { - goog.global.eval(script); - } else { - /** @type {Document} */ - var doc = goog.global.document; - var scriptElt = - /** @type {!HTMLScriptElement} */ (doc.createElement('SCRIPT')); - scriptElt.type = 'text/javascript'; - scriptElt.defer = false; - // Note(user): can't use .innerHTML since "t('<test>')" will fail and - // .text doesn't work in Safari 2. Therefore we append a text node. - scriptElt.appendChild(doc.createTextNode(script)); - doc.body.appendChild(scriptElt); - doc.body.removeChild(scriptElt); - } - } else { - throw Error('goog.globalEval not available'); - } -}; - - -/** - * Indicates whether or not we can call 'eval' directly to eval code in the - * global scope. Set to a Boolean by the first call to goog.globalEval (which - * empirically tests whether eval works for globals). @see goog.globalEval - * @type {?boolean} - * @private - */ -goog.evalWorksForGlobals_ = null; - - -/** - * Optional map of CSS class names to obfuscated names used with - * goog.getCssName(). - * @private {!Object<string, string>|undefined} - * @see goog.setCssNameMapping - */ -goog.cssNameMapping_; - - -/** - * Optional obfuscation style for CSS class names. Should be set to either - * 'BY_WHOLE' or 'BY_PART' if defined. - * @type {string|undefined} - * @private - * @see goog.setCssNameMapping - */ -goog.cssNameMappingStyle_; - - - -/** - * A hook for modifying the default behavior goog.getCssName. The function - * if present, will recieve the standard output of the goog.getCssName as - * its input. - * - * @type {(function(string):string)|undefined} - */ -goog.global.CLOSURE_CSS_NAME_MAP_FN; - - -/** - * Handles strings that are intended to be used as CSS class names. - * - * This function works in tandem with @see goog.setCssNameMapping. - * - * Without any mapping set, the arguments are simple joined with a hyphen and - * passed through unaltered. - * - * When there is a mapping, there are two possible styles in which these - * mappings are used. In the BY_PART style, each part (i.e. in between hyphens) - * of the passed in css name is rewritten according to the map. In the BY_WHOLE - * style, the full css name is looked up in the map directly. If a rewrite is - * not specified by the map, the compiler will output a warning. - * - * When the mapping is passed to the compiler, it will replace calls to - * goog.getCssName with the strings from the mapping, e.g. - * var x = goog.getCssName('foo'); - * var y = goog.getCssName(this.baseClass, 'active'); - * becomes: - * var x = 'foo'; - * var y = this.baseClass + '-active'; - * - * If one argument is passed it will be processed, if two are passed only the - * modifier will be processed, as it is assumed the first argument was generated - * as a result of calling goog.getCssName. - * - * @param {string} className The class name. - * @param {string=} opt_modifier A modifier to be appended to the class name. - * @return {string} The class name or the concatenation of the class name and - * the modifier. - */ -goog.getCssName = function(className, opt_modifier) { - // String() is used for compatibility with compiled soy where the passed - // className can be non-string objects. - if (String(className).charAt(0) == '.') { - throw new Error( - 'className passed in goog.getCssName must not start with ".".' + - ' You passed: ' + className); - } - - var getMapping = function(cssName) { - return goog.cssNameMapping_[cssName] || cssName; - }; - - var renameByParts = function(cssName) { - // Remap all the parts individually. - var parts = cssName.split('-'); - var mapped = []; - for (var i = 0; i < parts.length; i++) { - mapped.push(getMapping(parts[i])); - } - return mapped.join('-'); - }; - - var rename; - if (goog.cssNameMapping_) { - rename = - goog.cssNameMappingStyle_ == 'BY_WHOLE' ? getMapping : renameByParts; - } else { - rename = function(a) { - return a; - }; - } - - var result = - opt_modifier ? className + '-' + rename(opt_modifier) : rename(className); - - // The special CLOSURE_CSS_NAME_MAP_FN allows users to specify further - // processing of the class name. - if (goog.global.CLOSURE_CSS_NAME_MAP_FN) { - return goog.global.CLOSURE_CSS_NAME_MAP_FN(result); - } - - return result; -}; - - -/** - * Sets the map to check when returning a value from goog.getCssName(). Example: - * <pre> - * goog.setCssNameMapping({ - * "goog": "a", - * "disabled": "b", - * }); - * - * var x = goog.getCssName('goog'); - * // The following evaluates to: "a a-b". - * goog.getCssName('goog') + ' ' + goog.getCssName(x, 'disabled') - * </pre> - * When declared as a map of string literals to string literals, the JSCompiler - * will replace all calls to goog.getCssName() using the supplied map if the - * --process_closure_primitives flag is set. - * - * @param {!Object} mapping A map of strings to strings where keys are possible - * arguments to goog.getCssName() and values are the corresponding values - * that should be returned. - * @param {string=} opt_style The style of css name mapping. There are two valid - * options: 'BY_PART', and 'BY_WHOLE'. - * @see goog.getCssName for a description. - */ -goog.setCssNameMapping = function(mapping, opt_style) { - goog.cssNameMapping_ = mapping; - goog.cssNameMappingStyle_ = opt_style; -}; - - -/** - * To use CSS renaming in compiled mode, one of the input files should have a - * call to goog.setCssNameMapping() with an object literal that the JSCompiler - * can extract and use to replace all calls to goog.getCssName(). In uncompiled - * mode, JavaScript code should be loaded before this base.js file that declares - * a global variable, CLOSURE_CSS_NAME_MAPPING, which is used below. This is - * to ensure that the mapping is loaded before any calls to goog.getCssName() - * are made in uncompiled mode. - * - * A hook for overriding the CSS name mapping. - * @type {!Object<string, string>|undefined} - */ -goog.global.CLOSURE_CSS_NAME_MAPPING; - - -if (!COMPILED && goog.global.CLOSURE_CSS_NAME_MAPPING) { - // This does not call goog.setCssNameMapping() because the JSCompiler - // requires that goog.setCssNameMapping() be called with an object literal. - goog.cssNameMapping_ = goog.global.CLOSURE_CSS_NAME_MAPPING; -} - - -/** - * Gets a localized message. - * - * This function is a compiler primitive. If you give the compiler a localized - * message bundle, it will replace the string at compile-time with a localized - * version, and expand goog.getMsg call to a concatenated string. - * - * Messages must be initialized in the form: - * <code> - * var MSG_NAME = goog.getMsg('Hello {$placeholder}', {'placeholder': 'world'}); - * </code> - * - * This function produces a string which should be treated as plain text. Use - * {@link goog.html.SafeHtmlFormatter} in conjunction with goog.getMsg to - * produce SafeHtml. - * - * @param {string} str Translatable string, places holders in the form {$foo}. - * @param {Object<string, string>=} opt_values Maps place holder name to value. - * @return {string} message with placeholders filled. - */ -goog.getMsg = function(str, opt_values) { - if (opt_values) { - str = str.replace(/\{\$([^}]+)}/g, function(match, key) { - return (opt_values != null && key in opt_values) ? opt_values[key] : - match; - }); - } - return str; -}; - - -/** - * Gets a localized message. If the message does not have a translation, gives a - * fallback message. - * - * This is useful when introducing a new message that has not yet been - * translated into all languages. - * - * This function is a compiler primitive. Must be used in the form: - * <code>var x = goog.getMsgWithFallback(MSG_A, MSG_B);</code> - * where MSG_A and MSG_B were initialized with goog.getMsg. - * - * @param {string} a The preferred message. - * @param {string} b The fallback message. - * @return {string} The best translated message. - */ -goog.getMsgWithFallback = function(a, b) { - return a; -}; - - -/** - * Exposes an unobfuscated global namespace path for the given object. - * Note that fields of the exported object *will* be obfuscated, unless they are - * exported in turn via this function or goog.exportProperty. - * - * Also handy for making public items that are defined in anonymous closures. - * - * ex. goog.exportSymbol('public.path.Foo', Foo); - * - * ex. goog.exportSymbol('public.path.Foo.staticFunction', Foo.staticFunction); - * public.path.Foo.staticFunction(); - * - * ex. goog.exportSymbol('public.path.Foo.prototype.myMethod', - * Foo.prototype.myMethod); - * new public.path.Foo().myMethod(); - * - * @param {string} publicPath Unobfuscated name to export. - * @param {*} object Object the name should point to. - * @param {Object=} opt_objectToExportTo The object to add the path to; default - * is goog.global. - */ -goog.exportSymbol = function(publicPath, object, opt_objectToExportTo) { - goog.exportPath_(publicPath, object, opt_objectToExportTo); -}; - - -/** - * Exports a property unobfuscated into the object's namespace. - * ex. goog.exportProperty(Foo, 'staticFunction', Foo.staticFunction); - * ex. goog.exportProperty(Foo.prototype, 'myMethod', Foo.prototype.myMethod); - * @param {Object} object Object whose static property is being exported. - * @param {string} publicName Unobfuscated name to export. - * @param {*} symbol Object the name should point to. - */ -goog.exportProperty = function(object, publicName, symbol) { - object[publicName] = symbol; -}; - - -/** - * Inherit the prototype methods from one constructor into another. - * - * Usage: - * <pre> - * function ParentClass(a, b) { } - * ParentClass.prototype.foo = function(a) { }; - * - * function ChildClass(a, b, c) { - * ChildClass.base(this, 'constructor', a, b); - * } - * goog.inherits(ChildClass, ParentClass); - * - * var child = new ChildClass('a', 'b', 'see'); - * child.foo(); // This works. - * </pre> - * - * @param {!Function} childCtor Child class. - * @param {!Function} parentCtor Parent class. - */ -goog.inherits = function(childCtor, parentCtor) { - /** @constructor */ - function tempCtor() {} - tempCtor.prototype = parentCtor.prototype; - childCtor.superClass_ = parentCtor.prototype; - childCtor.prototype = new tempCtor(); - /** @override */ - childCtor.prototype.constructor = childCtor; - - /** - * Calls superclass constructor/method. - * - * This function is only available if you use goog.inherits to - * express inheritance relationships between classes. - * - * NOTE: This is a replacement for goog.base and for superClass_ - * property defined in childCtor. - * - * @param {!Object} me Should always be "this". - * @param {string} methodName The method name to call. Calling - * superclass constructor can be done with the special string - * 'constructor'. - * @param {...*} var_args The arguments to pass to superclass - * method/constructor. - * @return {*} The return value of the superclass method/constructor. - */ - childCtor.base = function(me, methodName, var_args) { - // Copying using loop to avoid deop due to passing arguments object to - // function. This is faster in many JS engines as of late 2014. - var args = new Array(arguments.length - 2); - for (var i = 2; i < arguments.length; i++) { - args[i - 2] = arguments[i]; - } - return parentCtor.prototype[methodName].apply(me, args); - }; -}; - - -/** - * Call up to the superclass. - * - * If this is called from a constructor, then this calls the superclass - * constructor with arguments 1-N. - * - * If this is called from a prototype method, then you must pass the name of the - * method as the second argument to this function. If you do not, you will get a - * runtime error. This calls the superclass' method with arguments 2-N. - * - * This function only works if you use goog.inherits to express inheritance - * relationships between your classes. - * - * This function is a compiler primitive. At compile-time, the compiler will do - * macro expansion to remove a lot of the extra overhead that this function - * introduces. The compiler will also enforce a lot of the assumptions that this - * function makes, and treat it as a compiler error if you break them. - * - * @param {!Object} me Should always be "this". - * @param {*=} opt_methodName The method name if calling a super method. - * @param {...*} var_args The rest of the arguments. - * @return {*} The return value of the superclass method. - * @suppress {es5Strict} This method can not be used in strict mode, but - * all Closure Library consumers must depend on this file. - * @deprecated goog.base is not strict mode compatible. Prefer the static - * "base" method added to the constructor by goog.inherits - * or ES6 classes and the "super" keyword. - */ -goog.base = function(me, opt_methodName, var_args) { - var caller = arguments.callee.caller; - - if (goog.STRICT_MODE_COMPATIBLE || (goog.DEBUG && !caller)) { - throw Error( - 'arguments.caller not defined. goog.base() cannot be used ' + - 'with strict mode code. See ' + - 'http://www.ecma-international.org/ecma-262/5.1/#sec-C'); - } - - if (caller.superClass_) { - // Copying using loop to avoid deop due to passing arguments object to - // function. This is faster in many JS engines as of late 2014. - var ctorArgs = new Array(arguments.length - 1); - for (var i = 1; i < arguments.length; i++) { - ctorArgs[i - 1] = arguments[i]; - } - // This is a constructor. Call the superclass constructor. - return caller.superClass_.constructor.apply(me, ctorArgs); - } - - // Copying using loop to avoid deop due to passing arguments object to - // function. This is faster in many JS engines as of late 2014. - var args = new Array(arguments.length - 2); - for (var i = 2; i < arguments.length; i++) { - args[i - 2] = arguments[i]; - } - var foundCaller = false; - for (var ctor = me.constructor; ctor; - ctor = ctor.superClass_ && ctor.superClass_.constructor) { - if (ctor.prototype[opt_methodName] === caller) { - foundCaller = true; - } else if (foundCaller) { - return ctor.prototype[opt_methodName].apply(me, args); - } - } - - // If we did not find the caller in the prototype chain, then one of two - // things happened: - // 1) The caller is an instance method. - // 2) This method was not called by the right caller. - if (me[opt_methodName] === caller) { - return me.constructor.prototype[opt_methodName].apply(me, args); - } else { - throw Error( - 'goog.base called from a method of one name ' + - 'to a method of a different name'); - } -}; - - -/** - * Allow for aliasing within scope functions. This function exists for - * uncompiled code - in compiled code the calls will be inlined and the aliases - * applied. In uncompiled code the function is simply run since the aliases as - * written are valid JavaScript. - * - * - * @param {function()} fn Function to call. This function can contain aliases - * to namespaces (e.g. "var dom = goog.dom") or classes - * (e.g. "var Timer = goog.Timer"). - */ -goog.scope = function(fn) { - if (goog.isInModuleLoader_()) { - throw Error('goog.scope is not supported within a goog.module.'); - } - fn.call(goog.global); -}; - - -/* - * To support uncompiled, strict mode bundles that use eval to divide source - * like so: - * eval('someSource;//# sourceUrl sourcefile.js'); - * We need to export the globally defined symbols "goog" and "COMPILED". - * Exporting "goog" breaks the compiler optimizations, so we required that - * be defined externally. - * NOTE: We don't use goog.exportSymbol here because we don't want to trigger - * extern generation when that compiler option is enabled. - */ -if (!COMPILED) { - goog.global['COMPILED'] = COMPILED; -} - - -//============================================================================== -// goog.defineClass implementation -//============================================================================== - - -/** - * Creates a restricted form of a Closure "class": - * - from the compiler's perspective, the instance returned from the - * constructor is sealed (no new properties may be added). This enables - * better checks. - * - the compiler will rewrite this definition to a form that is optimal - * for type checking and optimization (initially this will be a more - * traditional form). - * - * @param {Function} superClass The superclass, Object or null. - * @param {goog.defineClass.ClassDescriptor} def - * An object literal describing - * the class. It may have the following properties: - * "constructor": the constructor function - * "statics": an object literal containing methods to add to the constructor - * as "static" methods or a function that will receive the constructor - * function as its only parameter to which static properties can - * be added. - * all other properties are added to the prototype. - * @return {!Function} The class constructor. - */ -goog.defineClass = function(superClass, def) { - // TODO(johnlenz): consider making the superClass an optional parameter. - var constructor = def.constructor; - var statics = def.statics; - // Wrap the constructor prior to setting up the prototype and static methods. - if (!constructor || constructor == Object.prototype.constructor) { - constructor = function() { - throw Error('cannot instantiate an interface (no constructor defined).'); - }; - } - - var cls = goog.defineClass.createSealingConstructor_(constructor, superClass); - if (superClass) { - goog.inherits(cls, superClass); - } - - // Remove all the properties that should not be copied to the prototype. - delete def.constructor; - delete def.statics; - - goog.defineClass.applyProperties_(cls.prototype, def); - if (statics != null) { - if (statics instanceof Function) { - statics(cls); - } else { - goog.defineClass.applyProperties_(cls, statics); - } - } - - return cls; -}; - - -/** - * @typedef {{ - * constructor: (!Function|undefined), - * statics: (Object|undefined|function(Function):void) - * }} - */ -goog.defineClass.ClassDescriptor; - - -/** - * @define {boolean} Whether the instances returned by goog.defineClass should - * be sealed when possible. - * - * When sealing is disabled the constructor function will not be wrapped by - * goog.defineClass, making it incompatible with ES6 class methods. - */ -goog.define('goog.defineClass.SEAL_CLASS_INSTANCES', goog.DEBUG); - - -/** - * If goog.defineClass.SEAL_CLASS_INSTANCES is enabled and Object.seal is - * defined, this function will wrap the constructor in a function that seals the - * results of the provided constructor function. - * - * @param {!Function} ctr The constructor whose results maybe be sealed. - * @param {Function} superClass The superclass constructor. - * @return {!Function} The replacement constructor. - * @private - */ -goog.defineClass.createSealingConstructor_ = function(ctr, superClass) { - if (!goog.defineClass.SEAL_CLASS_INSTANCES) { - // Do now wrap the constructor when sealing is disabled. Angular code - // depends on this for injection to work properly. - return ctr; - } - - // Compute whether the constructor is sealable at definition time, rather - // than when the instance is being constructed. - var superclassSealable = !goog.defineClass.isUnsealable_(superClass); - - /** - * @this {Object} - * @return {?} - */ - var wrappedCtr = function() { - // Don't seal an instance of a subclass when it calls the constructor of - // its super class as there is most likely still setup to do. - var instance = ctr.apply(this, arguments) || this; - instance[goog.UID_PROPERTY_] = instance[goog.UID_PROPERTY_]; - - if (this.constructor === wrappedCtr && superclassSealable && - Object.seal instanceof Function) { - Object.seal(instance); - } - return instance; - }; - - return wrappedCtr; -}; - - -/** - * @param {Function} ctr The constructor to test. - * @return {boolean} Whether the constructor has been tagged as unsealable - * using goog.tagUnsealableClass. - * @private - */ -goog.defineClass.isUnsealable_ = function(ctr) { - return ctr && ctr.prototype && - ctr.prototype[goog.UNSEALABLE_CONSTRUCTOR_PROPERTY_]; -}; - - -// TODO(johnlenz): share these values with the goog.object -/** - * The names of the fields that are defined on Object.prototype. - * @type {!Array<string>} - * @private - * @const - */ -goog.defineClass.OBJECT_PROTOTYPE_FIELDS_ = [ - 'constructor', 'hasOwnProperty', 'isPrototypeOf', 'propertyIsEnumerable', - 'toLocaleString', 'toString', 'valueOf' -]; - - -// TODO(johnlenz): share this function with the goog.object -/** - * @param {!Object} target The object to add properties to. - * @param {!Object} source The object to copy properties from. - * @private - */ -goog.defineClass.applyProperties_ = function(target, source) { - // TODO(johnlenz): update this to support ES5 getters/setters - - var key; - for (key in source) { - if (Object.prototype.hasOwnProperty.call(source, key)) { - target[key] = source[key]; - } - } - - // For IE the for-in-loop does not contain any properties that are not - // enumerable on the prototype object (for example isPrototypeOf from - // Object.prototype) and it will also not include 'replace' on objects that - // extend String and change 'replace' (not that it is common for anyone to - // extend anything except Object). - for (var i = 0; i < goog.defineClass.OBJECT_PROTOTYPE_FIELDS_.length; i++) { - key = goog.defineClass.OBJECT_PROTOTYPE_FIELDS_[i]; - if (Object.prototype.hasOwnProperty.call(source, key)) { - target[key] = source[key]; - } - } -}; - - -/** - * Sealing classes breaks the older idiom of assigning properties on the - * prototype rather than in the constructor. As such, goog.defineClass - * must not seal subclasses of these old-style classes until they are fixed. - * Until then, this marks a class as "broken", instructing defineClass - * not to seal subclasses. - * @param {!Function} ctr The legacy constructor to tag as unsealable. - */ -goog.tagUnsealableClass = function(ctr) { - if (!COMPILED && goog.defineClass.SEAL_CLASS_INSTANCES) { - ctr.prototype[goog.UNSEALABLE_CONSTRUCTOR_PROPERTY_] = true; - } -}; - - -/** - * Name for unsealable tag property. - * @const @private {string} - */ -goog.UNSEALABLE_CONSTRUCTOR_PROPERTY_ = 'goog_defineClass_legacy_unsealable'; - - -/** - * Returns a newly created map from language mode string to a boolean - * indicating whether transpilation should be done for that mode. - * - * Guaranteed invariant: - * For any two modes, l1 and l2 where l2 is a newer mode than l1, - * `map[l1] == true` implies that `map[l2] == true`. - * @private - * @return {!Object<string, boolean>} - */ -goog.createRequiresTranspilation_ = function() { - var /** !Object<string, boolean> */ requiresTranspilation = {'es3': false}; - var transpilationRequiredForAllLaterModes = false; - - /** - * Adds an entry to requiresTranspliation for the given language mode. - * - * IMPORTANT: Calls must be made in order from oldest to newest language - * mode. - * @param {string} modeName - * @param {function(): boolean} isSupported Returns true if the JS engine - * supports the given mode. - */ - function addNewerLanguageTranspilationCheck(modeName, isSupported) { - if (transpilationRequiredForAllLaterModes) { - requiresTranspilation[modeName] = true; - } else if (isSupported()) { - requiresTranspilation[modeName] = false; - } else { - requiresTranspilation[modeName] = true; - transpilationRequiredForAllLaterModes = true; - } - } - - /** - * Does the given code evaluate without syntax errors and return a truthy - * result? - */ - function /** boolean */ evalCheck(/** string */ code) { - try { - return !!eval(code); - } catch (ignored) { - return false; - } - } - - var userAgent = goog.global.navigator && goog.global.navigator.userAgent ? - goog.global.navigator.userAgent : - ''; - - // Identify ES3-only browsers by their incorrect treatment of commas. - addNewerLanguageTranspilationCheck('es5', function() { - return evalCheck('[1,].length==1'); - }); - addNewerLanguageTranspilationCheck('es6', function() { - // Edge has a non-deterministic (i.e., not reproducible) bug with ES6: - // https://github.com/Microsoft/ChakraCore/issues/1496. - var re = /Edge\/(\d+)(\.\d)*/i; - var edgeUserAgent = userAgent.match(re); - if (edgeUserAgent && Number(edgeUserAgent[1]) < 15) { - return false; - } - // Test es6: [FF50 (?), Edge 14 (?), Chrome 50] - // (a) default params (specifically shadowing locals), - // (b) destructuring, (c) block-scoped functions, - // (d) for-of (const), (e) new.target/Reflect.construct - var es6fullTest = - 'class X{constructor(){if(new.target!=String)throw 1;this.x=42}}' + - 'let q=Reflect.construct(X,[],String);if(q.x!=42||!(q instanceof ' + - 'String))throw 1;for(const a of[2,3]){if(a==2)continue;function ' + - 'f(z={a}){let a=0;return z.a}{function f(){return 0;}}return f()' + - '==3}'; - - return evalCheck('(()=>{"use strict";' + es6fullTest + '})()'); - }); - // TODO(joeltine): Remove es6-impl references for b/31340605. - // Consider es6-impl (widely-implemented es6 features) to be supported - // whenever es6 is supported. Technically es6-impl is a lower level of - // support than es6, but we don't have tests specifically for it. - addNewerLanguageTranspilationCheck('es6-impl', function() { - return true; - }); - // ** and **= are the only new features in 'es7' - addNewerLanguageTranspilationCheck('es7', function() { - return evalCheck('2 ** 2 == 4'); - }); - // async functions are the only new features in 'es8' - addNewerLanguageTranspilationCheck('es8', function() { - return evalCheck('async () => 1, true'); - }); - return requiresTranspilation; -}; - -goog.provide('ol.array'); - - -/** - * Performs a binary search on the provided sorted list and returns the index of the item if found. If it can't be found it'll return -1. - * https://github.com/darkskyapp/binary-search - * - * @param {Array.<*>} haystack Items to search through. - * @param {*} needle The item to look for. - * @param {Function=} opt_comparator Comparator function. - * @return {number} The index of the item if found, -1 if not. - */ -ol.array.binarySearch = function(haystack, needle, opt_comparator) { - var mid, cmp; - var comparator = opt_comparator || ol.array.numberSafeCompareFunction; - var low = 0; - var high = haystack.length; - var found = false; - - while (low < high) { - /* Note that "(low + high) >>> 1" may overflow, and results in a typecast - * to double (which gives the wrong results). */ - mid = low + (high - low >> 1); - cmp = +comparator(haystack[mid], needle); - - if (cmp < 0.0) { /* Too low. */ - low = mid + 1; - - } else { /* Key found or too high */ - high = mid; - found = !cmp; - } - } - - /* Key not found. */ - return found ? low : ~low; -}; - - -/** - * Compare function for array sort that is safe for numbers. - * @param {*} a The first object to be compared. - * @param {*} b The second object to be compared. - * @return {number} A negative number, zero, or a positive number as the first - * argument is less than, equal to, or greater than the second. - */ -ol.array.numberSafeCompareFunction = function(a, b) { - return a > b ? 1 : a < b ? -1 : 0; -}; - - -/** - * Whether the array contains the given object. - * @param {Array.<*>} arr The array to test for the presence of the element. - * @param {*} obj The object for which to test. - * @return {boolean} The object is in the array. - */ -ol.array.includes = function(arr, obj) { - return arr.indexOf(obj) >= 0; -}; - - -/** - * @param {Array.<number>} arr Array. - * @param {number} target Target. - * @param {number} direction 0 means return the nearest, > 0 - * means return the largest nearest, < 0 means return the - * smallest nearest. - * @return {number} Index. - */ -ol.array.linearFindNearest = function(arr, target, direction) { - var n = arr.length; - if (arr[0] <= target) { - return 0; - } else if (target <= arr[n - 1]) { - return n - 1; - } else { - var i; - if (direction > 0) { - for (i = 1; i < n; ++i) { - if (arr[i] < target) { - return i - 1; - } - } - } else if (direction < 0) { - for (i = 1; i < n; ++i) { - if (arr[i] <= target) { - return i; - } - } - } else { - for (i = 1; i < n; ++i) { - if (arr[i] == target) { - return i; - } else if (arr[i] < target) { - if (arr[i - 1] - target < target - arr[i]) { - return i - 1; - } else { - return i; - } - } - } - } - return n - 1; - } -}; - - -/** - * @param {Array.<*>} arr Array. - * @param {number} begin Begin index. - * @param {number} end End index. - */ -ol.array.reverseSubArray = function(arr, begin, end) { - while (begin < end) { - var tmp = arr[begin]; - arr[begin] = arr[end]; - arr[end] = tmp; - ++begin; - --end; - } -}; - - -/** - * @param {Array.<VALUE>} arr The array to modify. - * @param {Array.<VALUE>|VALUE} data The elements or arrays of elements - * to add to arr. - * @template VALUE - */ -ol.array.extend = function(arr, data) { - var i; - var extension = Array.isArray(data) ? data : [data]; - var length = extension.length; - for (i = 0; i < length; i++) { - arr[arr.length] = extension[i]; - } -}; - - -/** - * @param {Array.<VALUE>} arr The array to modify. - * @param {VALUE} obj The element to remove. - * @template VALUE - * @return {boolean} If the element was removed. - */ -ol.array.remove = function(arr, obj) { - var i = arr.indexOf(obj); - var found = i > -1; - if (found) { - arr.splice(i, 1); - } - return found; -}; - - -/** - * @param {Array.<VALUE>} arr The array to search in. - * @param {function(VALUE, number, ?) : boolean} func The function to compare. - * @template VALUE - * @return {VALUE} The element found. - */ -ol.array.find = function(arr, func) { - var length = arr.length >>> 0; - var value; - - for (var i = 0; i < length; i++) { - value = arr[i]; - if (func(value, i, arr)) { - return value; - } - } - return null; -}; - - -/** - * @param {Array|Uint8ClampedArray} arr1 The first array to compare. - * @param {Array|Uint8ClampedArray} arr2 The second array to compare. - * @return {boolean} Whether the two arrays are equal. - */ -ol.array.equals = function(arr1, arr2) { - var len1 = arr1.length; - if (len1 !== arr2.length) { - return false; - } - for (var i = 0; i < len1; i++) { - if (arr1[i] !== arr2[i]) { - return false; - } - } - return true; -}; - - -/** - * @param {Array.<*>} arr The array to sort (modifies original). - * @param {Function} compareFnc Comparison function. - */ -ol.array.stableSort = function(arr, compareFnc) { - var length = arr.length; - var tmp = Array(arr.length); - var i; - for (i = 0; i < length; i++) { - tmp[i] = {index: i, value: arr[i]}; - } - tmp.sort(function(a, b) { - return compareFnc(a.value, b.value) || a.index - b.index; - }); - for (i = 0; i < arr.length; i++) { - arr[i] = tmp[i].value; - } -}; - - -/** - * @param {Array.<*>} arr The array to search in. - * @param {Function} func Comparison function. - * @return {number} Return index. - */ -ol.array.findIndex = function(arr, func) { - var index; - var found = !arr.every(function(el, idx) { - index = idx; - return !func(el, idx, arr); - }); - return found ? index : -1; -}; - - -/** - * @param {Array.<*>} arr The array to test. - * @param {Function=} opt_func Comparison function. - * @param {boolean=} opt_strict Strictly sorted (default false). - * @return {boolean} Return index. - */ -ol.array.isSorted = function(arr, opt_func, opt_strict) { - var compare = opt_func || ol.array.numberSafeCompareFunction; - return arr.every(function(currentVal, index) { - if (index === 0) { - return true; - } - var res = compare(arr[index - 1], currentVal); - return !(res > 0 || opt_strict && res === 0); - }); -}; - -goog.provide('ol'); - - -/** - * Constants defined with the define tag cannot be changed in application - * code, but can be set at compile time. - * Some reduce the size of the build in advanced compile mode. - */ - - -/** - * @define {boolean} Assume touch. Default is `false`. - */ -ol.ASSUME_TOUCH = false; - - -/** - * TODO: rename this to something having to do with tile grids - * see https://github.com/openlayers/openlayers/issues/2076 - * @define {number} Default maximum zoom for default tile grids. - */ -ol.DEFAULT_MAX_ZOOM = 42; - - -/** - * @define {number} Default min zoom level for the map view. Default is `0`. - */ -ol.DEFAULT_MIN_ZOOM = 0; - - -/** - * @define {number} Default maximum allowed threshold (in pixels) for - * reprojection triangulation. Default is `0.5`. - */ -ol.DEFAULT_RASTER_REPROJECTION_ERROR_THRESHOLD = 0.5; - - -/** - * @define {number} Default tile size. - */ -ol.DEFAULT_TILE_SIZE = 256; - - -/** - * @define {string} Default WMS version. - */ -ol.DEFAULT_WMS_VERSION = '1.3.0'; - - -/** - * @define {boolean} Enable the Canvas renderer. Default is `true`. Setting - * this to false at compile time in advanced mode removes all code - * supporting the Canvas renderer from the build. - */ -ol.ENABLE_CANVAS = true; - - -/** - * @define {boolean} Enable integration with the Proj4js library. Default is - * `true`. - */ -ol.ENABLE_PROJ4JS = true; - - -/** - * @define {boolean} Enable automatic reprojection of raster sources. Default is - * `true`. - */ -ol.ENABLE_RASTER_REPROJECTION = true; - - -/** - * @define {boolean} Enable the WebGL renderer. Default is `true`. Setting - * this to false at compile time in advanced mode removes all code - * supporting the WebGL renderer from the build. - */ -ol.ENABLE_WEBGL = true; - - -/** - * @define {boolean} Include debuggable shader sources. Default is `true`. - * This should be set to `false` for production builds (if `ol.ENABLE_WEBGL` - * is `true`). - */ -ol.DEBUG_WEBGL = true; - - -/** - * @define {number} The size in pixels of the first atlas image. Default is - * `256`. - */ -ol.INITIAL_ATLAS_SIZE = 256; - - -/** - * @define {number} The maximum size in pixels of atlas images. Default is - * `-1`, meaning it is not used (and `ol.WEBGL_MAX_TEXTURE_SIZE` is - * used instead). - */ -ol.MAX_ATLAS_SIZE = -1; - - -/** - * @define {number} Maximum mouse wheel delta. - */ -ol.MOUSEWHEELZOOM_MAXDELTA = 1; - - -/** - * @define {number} Maximum width and/or height extent ratio that determines - * when the overview map should be zoomed out. - */ -ol.OVERVIEWMAP_MAX_RATIO = 0.75; - - -/** - * @define {number} Minimum width and/or height extent ratio that determines - * when the overview map should be zoomed in. - */ -ol.OVERVIEWMAP_MIN_RATIO = 0.1; - - -/** - * @define {number} Maximum number of source tiles for raster reprojection of - * a single tile. - * If too many source tiles are determined to be loaded to create a single - * reprojected tile the browser can become unresponsive or even crash. - * This can happen if the developer defines projections improperly and/or - * with unlimited extents. - * If too many tiles are required, no tiles are loaded and - * `ol.TileState.ERROR` state is set. Default is `100`. - */ -ol.RASTER_REPROJECTION_MAX_SOURCE_TILES = 100; - - -/** - * @define {number} Maximum number of subdivision steps during raster - * reprojection triangulation. Prevents high memory usage and large - * number of proj4 calls (for certain transformations and areas). - * At most `2*(2^this)` triangles are created for each triangulated - * extent (tile/image). Default is `10`. - */ -ol.RASTER_REPROJECTION_MAX_SUBDIVISION = 10; - - -/** - * @define {number} Maximum allowed size of triangle relative to world width. - * When transforming corners of world extent between certain projections, - * the resulting triangulation seems to have zero error and no subdivision - * is performed. - * If the triangle width is more than this (relative to world width; 0-1), - * subdivison is forced (up to `ol.RASTER_REPROJECTION_MAX_SUBDIVISION`). - * Default is `0.25`. - */ -ol.RASTER_REPROJECTION_MAX_TRIANGLE_WIDTH = 0.25; - - -/** - * @define {number} Tolerance for geometry simplification in device pixels. - */ -ol.SIMPLIFY_TOLERANCE = 0.5; - - -/** - * @define {number} Texture cache high water mark. - */ -ol.WEBGL_TEXTURE_CACHE_HIGH_WATER_MARK = 1024; - - -/** - * @define {string} OpenLayers version. - */ -ol.VERSION = ''; - - -/** - * The maximum supported WebGL texture size in pixels. If WebGL is not - * supported, the value is set to `undefined`. - * @const - * @type {number|undefined} - */ -ol.WEBGL_MAX_TEXTURE_SIZE; // value is set in `ol.has` - - -/** - * List of supported WebGL extensions. - * @const - * @type {Array.<string>} - */ -ol.WEBGL_EXTENSIONS; // value is set in `ol.has` - - -/** - * Inherit the prototype methods from one constructor into another. - * - * Usage: - * - * function ParentClass(a, b) { } - * ParentClass.prototype.foo = function(a) { } - * - * function ChildClass(a, b, c) { - * // Call parent constructor - * ParentClass.call(this, a, b); - * } - * ol.inherits(ChildClass, ParentClass); - * - * var child = new ChildClass('a', 'b', 'see'); - * child.foo(); // This works. - * - * @param {!Function} childCtor Child constructor. - * @param {!Function} parentCtor Parent constructor. - * @function - * @api - */ -ol.inherits = function(childCtor, parentCtor) { - childCtor.prototype = Object.create(parentCtor.prototype); - childCtor.prototype.constructor = childCtor; -}; - - -/** - * A reusable function, used e.g. as a default for callbacks. - * - * @return {undefined} Nothing. - */ -ol.nullFunction = function() {}; - - -/** - * Gets a unique ID for an object. This mutates the object so that further calls - * with the same object as a parameter returns the same value. Unique IDs are generated - * as a strictly increasing sequence. Adapted from goog.getUid. - * - * @param {Object} obj The object to get the unique ID for. - * @return {number} The unique ID for the object. - */ -ol.getUid = function(obj) { - return obj.ol_uid || - (obj.ol_uid = ++ol.uidCounter_); -}; - - -/** - * Counter for getUid. - * @type {number} - * @private - */ -ol.uidCounter_ = 0; - -goog.provide('ol.AssertionError'); - -goog.require('ol'); - -/** - * Error object thrown when an assertion failed. This is an ECMA-262 Error, - * extended with a `code` property. - * @see {@link https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Error} - * @constructor - * @extends {Error} - * @implements {oli.AssertionError} - * @param {number} code Error code. - */ -ol.AssertionError = function(code) { - - var path = ol.VERSION ? ol.VERSION.split('-')[0] : 'latest'; - - /** - * @type {string} - */ - this.message = 'Assertion failed. See https://openlayers.org/en/' + path + - '/doc/errors/#' + code + ' for details.'; - - /** - * Error code. The meaning of the code can be found on - * {@link https://openlayers.org/en/latest/doc/errors/} (replace `latest` with - * the version found in the OpenLayers script's header comment if a version - * other than the latest is used). - * @type {number} - * @api - */ - this.code = code; - - this.name = 'AssertionError'; - -}; -ol.inherits(ol.AssertionError, Error); - -goog.provide('ol.asserts'); - -goog.require('ol.AssertionError'); - - -/** - * @param {*} assertion Assertion we expected to be truthy. - * @param {number} errorCode Error code. - */ -ol.asserts.assert = function(assertion, errorCode) { - if (!assertion) { - throw new ol.AssertionError(errorCode); - } -}; - -goog.provide('ol.TileRange'); - - -/** - * A representation of a contiguous block of tiles. A tile range is specified - * by its min/max tile coordinates and is inclusive of coordinates. - * - * @constructor - * @param {number} minX Minimum X. - * @param {number} maxX Maximum X. - * @param {number} minY Minimum Y. - * @param {number} maxY Maximum Y. - * @struct - */ -ol.TileRange = function(minX, maxX, minY, maxY) { - - /** - * @type {number} - */ - this.minX = minX; - - /** - * @type {number} - */ - this.maxX = maxX; - - /** - * @type {number} - */ - this.minY = minY; - - /** - * @type {number} - */ - this.maxY = maxY; - -}; - - -/** - * @param {number} minX Minimum X. - * @param {number} maxX Maximum X. - * @param {number} minY Minimum Y. - * @param {number} maxY Maximum Y. - * @param {ol.TileRange|undefined} tileRange TileRange. - * @return {ol.TileRange} Tile range. - */ -ol.TileRange.createOrUpdate = function(minX, maxX, minY, maxY, tileRange) { - if (tileRange !== undefined) { - tileRange.minX = minX; - tileRange.maxX = maxX; - tileRange.minY = minY; - tileRange.maxY = maxY; - return tileRange; - } else { - return new ol.TileRange(minX, maxX, minY, maxY); - } -}; - - -/** - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @return {boolean} Contains tile coordinate. - */ -ol.TileRange.prototype.contains = function(tileCoord) { - return this.containsXY(tileCoord[1], tileCoord[2]); -}; - - -/** - * @param {ol.TileRange} tileRange Tile range. - * @return {boolean} Contains. - */ -ol.TileRange.prototype.containsTileRange = function(tileRange) { - return this.minX <= tileRange.minX && tileRange.maxX <= this.maxX && - this.minY <= tileRange.minY && tileRange.maxY <= this.maxY; -}; - - -/** - * @param {number} x Tile coordinate x. - * @param {number} y Tile coordinate y. - * @return {boolean} Contains coordinate. - */ -ol.TileRange.prototype.containsXY = function(x, y) { - return this.minX <= x && x <= this.maxX && this.minY <= y && y <= this.maxY; -}; - - -/** - * @param {ol.TileRange} tileRange Tile range. - * @return {boolean} Equals. - */ -ol.TileRange.prototype.equals = function(tileRange) { - return this.minX == tileRange.minX && this.minY == tileRange.minY && - this.maxX == tileRange.maxX && this.maxY == tileRange.maxY; -}; - - -/** - * @param {ol.TileRange} tileRange Tile range. - */ -ol.TileRange.prototype.extend = function(tileRange) { - if (tileRange.minX < this.minX) { - this.minX = tileRange.minX; - } - if (tileRange.maxX > this.maxX) { - this.maxX = tileRange.maxX; - } - if (tileRange.minY < this.minY) { - this.minY = tileRange.minY; - } - if (tileRange.maxY > this.maxY) { - this.maxY = tileRange.maxY; - } -}; - - -/** - * @return {number} Height. - */ -ol.TileRange.prototype.getHeight = function() { - return this.maxY - this.minY + 1; -}; - - -/** - * @return {ol.Size} Size. - */ -ol.TileRange.prototype.getSize = function() { - return [this.getWidth(), this.getHeight()]; -}; - - -/** - * @return {number} Width. - */ -ol.TileRange.prototype.getWidth = function() { - return this.maxX - this.minX + 1; -}; - - -/** - * @param {ol.TileRange} tileRange Tile range. - * @return {boolean} Intersects. - */ -ol.TileRange.prototype.intersects = function(tileRange) { - return this.minX <= tileRange.maxX && - this.maxX >= tileRange.minX && - this.minY <= tileRange.maxY && - this.maxY >= tileRange.minY; -}; - -goog.provide('ol.math'); - -goog.require('ol.asserts'); - - -/** - * Takes a number and clamps it to within the provided bounds. - * @param {number} value The input number. - * @param {number} min The minimum value to return. - * @param {number} max The maximum value to return. - * @return {number} The input number if it is within bounds, or the nearest - * number within the bounds. - */ -ol.math.clamp = function(value, min, max) { - return Math.min(Math.max(value, min), max); -}; - - -/** - * Return the hyperbolic cosine of a given number. The method will use the - * native `Math.cosh` function if it is available, otherwise the hyperbolic - * cosine will be calculated via the reference implementation of the Mozilla - * developer network. - * - * @param {number} x X. - * @return {number} Hyperbolic cosine of x. - */ -ol.math.cosh = (function() { - // Wrapped in a iife, to save the overhead of checking for the native - // implementation on every invocation. - var cosh; - if ('cosh' in Math) { - // The environment supports the native Math.cosh function, use it… - cosh = Math.cosh; - } else { - // … else, use the reference implementation of MDN: - cosh = function(x) { - var y = Math.exp(x); - return (y + 1 / y) / 2; - }; - } - return cosh; -}()); - - -/** - * @param {number} x X. - * @return {number} The smallest power of two greater than or equal to x. - */ -ol.math.roundUpToPowerOfTwo = function(x) { - ol.asserts.assert(0 < x, 29); // `x` must be greater than `0` - return Math.pow(2, Math.ceil(Math.log(x) / Math.LN2)); -}; - - -/** - * Returns the square of the closest distance between the point (x, y) and the - * line segment (x1, y1) to (x2, y2). - * @param {number} x X. - * @param {number} y Y. - * @param {number} x1 X1. - * @param {number} y1 Y1. - * @param {number} x2 X2. - * @param {number} y2 Y2. - * @return {number} Squared distance. - */ -ol.math.squaredSegmentDistance = function(x, y, x1, y1, x2, y2) { - var dx = x2 - x1; - var dy = y2 - y1; - if (dx !== 0 || dy !== 0) { - var t = ((x - x1) * dx + (y - y1) * dy) / (dx * dx + dy * dy); - if (t > 1) { - x1 = x2; - y1 = y2; - } else if (t > 0) { - x1 += dx * t; - y1 += dy * t; - } - } - return ol.math.squaredDistance(x, y, x1, y1); -}; - - -/** - * Returns the square of the distance between the points (x1, y1) and (x2, y2). - * @param {number} x1 X1. - * @param {number} y1 Y1. - * @param {number} x2 X2. - * @param {number} y2 Y2. - * @return {number} Squared distance. - */ -ol.math.squaredDistance = function(x1, y1, x2, y2) { - var dx = x2 - x1; - var dy = y2 - y1; - return dx * dx + dy * dy; -}; - - -/** - * Solves system of linear equations using Gaussian elimination method. - * - * @param {Array.<Array.<number>>} mat Augmented matrix (n x n + 1 column) - * in row-major order. - * @return {Array.<number>} The resulting vector. - */ -ol.math.solveLinearSystem = function(mat) { - var n = mat.length; - - for (var i = 0; i < n; i++) { - // Find max in the i-th column (ignoring i - 1 first rows) - var maxRow = i; - var maxEl = Math.abs(mat[i][i]); - for (var r = i + 1; r < n; r++) { - var absValue = Math.abs(mat[r][i]); - if (absValue > maxEl) { - maxEl = absValue; - maxRow = r; - } - } - - if (maxEl === 0) { - return null; // matrix is singular - } - - // Swap max row with i-th (current) row - var tmp = mat[maxRow]; - mat[maxRow] = mat[i]; - mat[i] = tmp; - - // Subtract the i-th row to make all the remaining rows 0 in the i-th column - for (var j = i + 1; j < n; j++) { - var coef = -mat[j][i] / mat[i][i]; - for (var k = i; k < n + 1; k++) { - if (i == k) { - mat[j][k] = 0; - } else { - mat[j][k] += coef * mat[i][k]; - } - } - } - } - - // Solve Ax=b for upper triangular matrix A (mat) - var x = new Array(n); - for (var l = n - 1; l >= 0; l--) { - x[l] = mat[l][n] / mat[l][l]; - for (var m = l - 1; m >= 0; m--) { - mat[m][n] -= mat[m][l] * x[l]; - } - } - return x; -}; - - -/** - * Converts radians to to degrees. - * - * @param {number} angleInRadians Angle in radians. - * @return {number} Angle in degrees. - */ -ol.math.toDegrees = function(angleInRadians) { - return angleInRadians * 180 / Math.PI; -}; - - -/** - * Converts degrees to radians. - * - * @param {number} angleInDegrees Angle in degrees. - * @return {number} Angle in radians. - */ -ol.math.toRadians = function(angleInDegrees) { - return angleInDegrees * Math.PI / 180; -}; - -/** - * Returns the modulo of a / b, depending on the sign of b. - * - * @param {number} a Dividend. - * @param {number} b Divisor. - * @return {number} Modulo. - */ -ol.math.modulo = function(a, b) { - var r = a % b; - return r * b < 0 ? r + b : r; -}; - -/** - * Calculates the linearly interpolated value of x between a and b. - * - * @param {number} a Number - * @param {number} b Number - * @param {number} x Value to be interpolated. - * @return {number} Interpolated value. - */ -ol.math.lerp = function(a, b, x) { - return a + x * (b - a); -}; - -goog.provide('ol.size'); - - -/** - * Returns a buffered size. - * @param {ol.Size} size Size. - * @param {number} buffer Buffer. - * @param {ol.Size=} opt_size Optional reusable size array. - * @return {ol.Size} The buffered size. - */ -ol.size.buffer = function(size, buffer, opt_size) { - if (opt_size === undefined) { - opt_size = [0, 0]; - } - opt_size[0] = size[0] + 2 * buffer; - opt_size[1] = size[1] + 2 * buffer; - return opt_size; -}; - - -/** - * Determines if a size has a positive area. - * @param {ol.Size} size The size to test. - * @return {boolean} The size has a positive area. - */ -ol.size.hasArea = function(size) { - return size[0] > 0 && size[1] > 0; -}; - - -/** - * Returns a size scaled by a ratio. The result will be an array of integers. - * @param {ol.Size} size Size. - * @param {number} ratio Ratio. - * @param {ol.Size=} opt_size Optional reusable size array. - * @return {ol.Size} The scaled size. - */ -ol.size.scale = function(size, ratio, opt_size) { - if (opt_size === undefined) { - opt_size = [0, 0]; - } - opt_size[0] = (size[0] * ratio + 0.5) | 0; - opt_size[1] = (size[1] * ratio + 0.5) | 0; - return opt_size; -}; - - -/** - * Returns an `ol.Size` array for the passed in number (meaning: square) or - * `ol.Size` array. - * (meaning: non-square), - * @param {number|ol.Size} size Width and height. - * @param {ol.Size=} opt_size Optional reusable size array. - * @return {ol.Size} Size. - * @api - */ -ol.size.toSize = function(size, opt_size) { - if (Array.isArray(size)) { - return size; - } else { - if (opt_size === undefined) { - opt_size = [size, size]; - } else { - opt_size[0] = opt_size[1] = /** @type {number} */ (size); - } - return opt_size; - } -}; - -goog.provide('ol.extent.Corner'); - -/** - * Extent corner. - * @enum {string} - */ -ol.extent.Corner = { - BOTTOM_LEFT: 'bottom-left', - BOTTOM_RIGHT: 'bottom-right', - TOP_LEFT: 'top-left', - TOP_RIGHT: 'top-right' -}; - -goog.provide('ol.extent.Relationship'); - - -/** - * Relationship to an extent. - * @enum {number} - */ -ol.extent.Relationship = { - UNKNOWN: 0, - INTERSECTING: 1, - ABOVE: 2, - RIGHT: 4, - BELOW: 8, - LEFT: 16 -}; - -goog.provide('ol.extent'); - -goog.require('ol.asserts'); -goog.require('ol.extent.Corner'); -goog.require('ol.extent.Relationship'); - - -/** - * Build an extent that includes all given coordinates. - * - * @param {Array.<ol.Coordinate>} coordinates Coordinates. - * @return {ol.Extent} Bounding extent. - * @api - */ -ol.extent.boundingExtent = function(coordinates) { - var extent = ol.extent.createEmpty(); - for (var i = 0, ii = coordinates.length; i < ii; ++i) { - ol.extent.extendCoordinate(extent, coordinates[i]); - } - return extent; -}; - - -/** - * @param {Array.<number>} xs Xs. - * @param {Array.<number>} ys Ys. - * @param {ol.Extent=} opt_extent Destination extent. - * @private - * @return {ol.Extent} Extent. - */ -ol.extent.boundingExtentXYs_ = function(xs, ys, opt_extent) { - var minX = Math.min.apply(null, xs); - var minY = Math.min.apply(null, ys); - var maxX = Math.max.apply(null, xs); - var maxY = Math.max.apply(null, ys); - return ol.extent.createOrUpdate(minX, minY, maxX, maxY, opt_extent); -}; - - -/** - * Return extent increased by the provided value. - * @param {ol.Extent} extent Extent. - * @param {number} value The amount by which the extent should be buffered. - * @param {ol.Extent=} opt_extent Extent. - * @return {ol.Extent} Extent. - * @api - */ -ol.extent.buffer = function(extent, value, opt_extent) { - if (opt_extent) { - opt_extent[0] = extent[0] - value; - opt_extent[1] = extent[1] - value; - opt_extent[2] = extent[2] + value; - opt_extent[3] = extent[3] + value; - return opt_extent; - } else { - return [ - extent[0] - value, - extent[1] - value, - extent[2] + value, - extent[3] + value - ]; - } -}; - - -/** - * Creates a clone of an extent. - * - * @param {ol.Extent} extent Extent to clone. - * @param {ol.Extent=} opt_extent Extent. - * @return {ol.Extent} The clone. - */ -ol.extent.clone = function(extent, opt_extent) { - if (opt_extent) { - opt_extent[0] = extent[0]; - opt_extent[1] = extent[1]; - opt_extent[2] = extent[2]; - opt_extent[3] = extent[3]; - return opt_extent; - } else { - return extent.slice(); - } -}; - - -/** - * @param {ol.Extent} extent Extent. - * @param {number} x X. - * @param {number} y Y. - * @return {number} Closest squared distance. - */ -ol.extent.closestSquaredDistanceXY = function(extent, x, y) { - var dx, dy; - if (x < extent[0]) { - dx = extent[0] - x; - } else if (extent[2] < x) { - dx = x - extent[2]; - } else { - dx = 0; - } - if (y < extent[1]) { - dy = extent[1] - y; - } else if (extent[3] < y) { - dy = y - extent[3]; - } else { - dy = 0; - } - return dx * dx + dy * dy; -}; - - -/** - * Check if the passed coordinate is contained or on the edge of the extent. - * - * @param {ol.Extent} extent Extent. - * @param {ol.Coordinate} coordinate Coordinate. - * @return {boolean} The coordinate is contained in the extent. - * @api - */ -ol.extent.containsCoordinate = function(extent, coordinate) { - return ol.extent.containsXY(extent, coordinate[0], coordinate[1]); -}; - - -/** - * Check if one extent contains another. - * - * An extent is deemed contained if it lies completely within the other extent, - * including if they share one or more edges. - * - * @param {ol.Extent} extent1 Extent 1. - * @param {ol.Extent} extent2 Extent 2. - * @return {boolean} The second extent is contained by or on the edge of the - * first. - * @api - */ -ol.extent.containsExtent = function(extent1, extent2) { - return extent1[0] <= extent2[0] && extent2[2] <= extent1[2] && - extent1[1] <= extent2[1] && extent2[3] <= extent1[3]; -}; - - -/** - * Check if the passed coordinate is contained or on the edge of the extent. - * - * @param {ol.Extent} extent Extent. - * @param {number} x X coordinate. - * @param {number} y Y coordinate. - * @return {boolean} The x, y values are contained in the extent. - * @api - */ -ol.extent.containsXY = function(extent, x, y) { - return extent[0] <= x && x <= extent[2] && extent[1] <= y && y <= extent[3]; -}; - - -/** - * Get the relationship between a coordinate and extent. - * @param {ol.Extent} extent The extent. - * @param {ol.Coordinate} coordinate The coordinate. - * @return {number} The relationship (bitwise compare with - * ol.extent.Relationship). - */ -ol.extent.coordinateRelationship = function(extent, coordinate) { - var minX = extent[0]; - var minY = extent[1]; - var maxX = extent[2]; - var maxY = extent[3]; - var x = coordinate[0]; - var y = coordinate[1]; - var relationship = ol.extent.Relationship.UNKNOWN; - if (x < minX) { - relationship = relationship | ol.extent.Relationship.LEFT; - } else if (x > maxX) { - relationship = relationship | ol.extent.Relationship.RIGHT; - } - if (y < minY) { - relationship = relationship | ol.extent.Relationship.BELOW; - } else if (y > maxY) { - relationship = relationship | ol.extent.Relationship.ABOVE; - } - if (relationship === ol.extent.Relationship.UNKNOWN) { - relationship = ol.extent.Relationship.INTERSECTING; - } - return relationship; -}; - - -/** - * Create an empty extent. - * @return {ol.Extent} Empty extent. - * @api - */ -ol.extent.createEmpty = function() { - return [Infinity, Infinity, -Infinity, -Infinity]; -}; - - -/** - * Create a new extent or update the provided extent. - * @param {number} minX Minimum X. - * @param {number} minY Minimum Y. - * @param {number} maxX Maximum X. - * @param {number} maxY Maximum Y. - * @param {ol.Extent=} opt_extent Destination extent. - * @return {ol.Extent} Extent. - */ -ol.extent.createOrUpdate = function(minX, minY, maxX, maxY, opt_extent) { - if (opt_extent) { - opt_extent[0] = minX; - opt_extent[1] = minY; - opt_extent[2] = maxX; - opt_extent[3] = maxY; - return opt_extent; - } else { - return [minX, minY, maxX, maxY]; - } -}; - - -/** - * Create a new empty extent or make the provided one empty. - * @param {ol.Extent=} opt_extent Extent. - * @return {ol.Extent} Extent. - */ -ol.extent.createOrUpdateEmpty = function(opt_extent) { - return ol.extent.createOrUpdate( - Infinity, Infinity, -Infinity, -Infinity, opt_extent); -}; - - -/** - * @param {ol.Coordinate} coordinate Coordinate. - * @param {ol.Extent=} opt_extent Extent. - * @return {ol.Extent} Extent. - */ -ol.extent.createOrUpdateFromCoordinate = function(coordinate, opt_extent) { - var x = coordinate[0]; - var y = coordinate[1]; - return ol.extent.createOrUpdate(x, y, x, y, opt_extent); -}; - - -/** - * @param {Array.<ol.Coordinate>} coordinates Coordinates. - * @param {ol.Extent=} opt_extent Extent. - * @return {ol.Extent} Extent. - */ -ol.extent.createOrUpdateFromCoordinates = function(coordinates, opt_extent) { - var extent = ol.extent.createOrUpdateEmpty(opt_extent); - return ol.extent.extendCoordinates(extent, coordinates); -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {ol.Extent=} opt_extent Extent. - * @return {ol.Extent} Extent. - */ -ol.extent.createOrUpdateFromFlatCoordinates = function(flatCoordinates, offset, end, stride, opt_extent) { - var extent = ol.extent.createOrUpdateEmpty(opt_extent); - return ol.extent.extendFlatCoordinates( - extent, flatCoordinates, offset, end, stride); -}; - - -/** - * @param {Array.<Array.<ol.Coordinate>>} rings Rings. - * @param {ol.Extent=} opt_extent Extent. - * @return {ol.Extent} Extent. - */ -ol.extent.createOrUpdateFromRings = function(rings, opt_extent) { - var extent = ol.extent.createOrUpdateEmpty(opt_extent); - return ol.extent.extendRings(extent, rings); -}; - - -/** - * Determine if two extents are equivalent. - * @param {ol.Extent} extent1 Extent 1. - * @param {ol.Extent} extent2 Extent 2. - * @return {boolean} The two extents are equivalent. - * @api - */ -ol.extent.equals = function(extent1, extent2) { - return extent1[0] == extent2[0] && extent1[2] == extent2[2] && - extent1[1] == extent2[1] && extent1[3] == extent2[3]; -}; - - -/** - * Modify an extent to include another extent. - * @param {ol.Extent} extent1 The extent to be modified. - * @param {ol.Extent} extent2 The extent that will be included in the first. - * @return {ol.Extent} A reference to the first (extended) extent. - * @api - */ -ol.extent.extend = function(extent1, extent2) { - if (extent2[0] < extent1[0]) { - extent1[0] = extent2[0]; - } - if (extent2[2] > extent1[2]) { - extent1[2] = extent2[2]; - } - if (extent2[1] < extent1[1]) { - extent1[1] = extent2[1]; - } - if (extent2[3] > extent1[3]) { - extent1[3] = extent2[3]; - } - return extent1; -}; - - -/** - * @param {ol.Extent} extent Extent. - * @param {ol.Coordinate} coordinate Coordinate. - */ -ol.extent.extendCoordinate = function(extent, coordinate) { - if (coordinate[0] < extent[0]) { - extent[0] = coordinate[0]; - } - if (coordinate[0] > extent[2]) { - extent[2] = coordinate[0]; - } - if (coordinate[1] < extent[1]) { - extent[1] = coordinate[1]; - } - if (coordinate[1] > extent[3]) { - extent[3] = coordinate[1]; - } -}; - - -/** - * @param {ol.Extent} extent Extent. - * @param {Array.<ol.Coordinate>} coordinates Coordinates. - * @return {ol.Extent} Extent. - */ -ol.extent.extendCoordinates = function(extent, coordinates) { - var i, ii; - for (i = 0, ii = coordinates.length; i < ii; ++i) { - ol.extent.extendCoordinate(extent, coordinates[i]); - } - return extent; -}; - - -/** - * @param {ol.Extent} extent Extent. - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @return {ol.Extent} Extent. - */ -ol.extent.extendFlatCoordinates = function(extent, flatCoordinates, offset, end, stride) { - for (; offset < end; offset += stride) { - ol.extent.extendXY( - extent, flatCoordinates[offset], flatCoordinates[offset + 1]); - } - return extent; -}; - - -/** - * @param {ol.Extent} extent Extent. - * @param {Array.<Array.<ol.Coordinate>>} rings Rings. - * @return {ol.Extent} Extent. - */ -ol.extent.extendRings = function(extent, rings) { - var i, ii; - for (i = 0, ii = rings.length; i < ii; ++i) { - ol.extent.extendCoordinates(extent, rings[i]); - } - return extent; -}; - - -/** - * @param {ol.Extent} extent Extent. - * @param {number} x X. - * @param {number} y Y. - */ -ol.extent.extendXY = function(extent, x, y) { - extent[0] = Math.min(extent[0], x); - extent[1] = Math.min(extent[1], y); - extent[2] = Math.max(extent[2], x); - extent[3] = Math.max(extent[3], y); -}; - - -/** - * This function calls `callback` for each corner of the extent. If the - * callback returns a truthy value the function returns that value - * immediately. Otherwise the function returns `false`. - * @param {ol.Extent} extent Extent. - * @param {function(this:T, ol.Coordinate): S} callback Callback. - * @param {T=} opt_this Value to use as `this` when executing `callback`. - * @return {S|boolean} Value. - * @template S, T - */ -ol.extent.forEachCorner = function(extent, callback, opt_this) { - var val; - val = callback.call(opt_this, ol.extent.getBottomLeft(extent)); - if (val) { - return val; - } - val = callback.call(opt_this, ol.extent.getBottomRight(extent)); - if (val) { - return val; - } - val = callback.call(opt_this, ol.extent.getTopRight(extent)); - if (val) { - return val; - } - val = callback.call(opt_this, ol.extent.getTopLeft(extent)); - if (val) { - return val; - } - return false; -}; - - -/** - * Get the size of an extent. - * @param {ol.Extent} extent Extent. - * @return {number} Area. - * @api - */ -ol.extent.getArea = function(extent) { - var area = 0; - if (!ol.extent.isEmpty(extent)) { - area = ol.extent.getWidth(extent) * ol.extent.getHeight(extent); - } - return area; -}; - - -/** - * Get the bottom left coordinate of an extent. - * @param {ol.Extent} extent Extent. - * @return {ol.Coordinate} Bottom left coordinate. - * @api - */ -ol.extent.getBottomLeft = function(extent) { - return [extent[0], extent[1]]; -}; - - -/** - * Get the bottom right coordinate of an extent. - * @param {ol.Extent} extent Extent. - * @return {ol.Coordinate} Bottom right coordinate. - * @api - */ -ol.extent.getBottomRight = function(extent) { - return [extent[2], extent[1]]; -}; - - -/** - * Get the center coordinate of an extent. - * @param {ol.Extent} extent Extent. - * @return {ol.Coordinate} Center. - * @api - */ -ol.extent.getCenter = function(extent) { - return [(extent[0] + extent[2]) / 2, (extent[1] + extent[3]) / 2]; -}; - - -/** - * Get a corner coordinate of an extent. - * @param {ol.Extent} extent Extent. - * @param {ol.extent.Corner} corner Corner. - * @return {ol.Coordinate} Corner coordinate. - */ -ol.extent.getCorner = function(extent, corner) { - var coordinate; - if (corner === ol.extent.Corner.BOTTOM_LEFT) { - coordinate = ol.extent.getBottomLeft(extent); - } else if (corner === ol.extent.Corner.BOTTOM_RIGHT) { - coordinate = ol.extent.getBottomRight(extent); - } else if (corner === ol.extent.Corner.TOP_LEFT) { - coordinate = ol.extent.getTopLeft(extent); - } else if (corner === ol.extent.Corner.TOP_RIGHT) { - coordinate = ol.extent.getTopRight(extent); - } else { - ol.asserts.assert(false, 13); // Invalid corner - } - return /** @type {!ol.Coordinate} */ (coordinate); -}; - - -/** - * @param {ol.Extent} extent1 Extent 1. - * @param {ol.Extent} extent2 Extent 2. - * @return {number} Enlarged area. - */ -ol.extent.getEnlargedArea = function(extent1, extent2) { - var minX = Math.min(extent1[0], extent2[0]); - var minY = Math.min(extent1[1], extent2[1]); - var maxX = Math.max(extent1[2], extent2[2]); - var maxY = Math.max(extent1[3], extent2[3]); - return (maxX - minX) * (maxY - minY); -}; - - -/** - * @param {ol.Coordinate} center Center. - * @param {number} resolution Resolution. - * @param {number} rotation Rotation. - * @param {ol.Size} size Size. - * @param {ol.Extent=} opt_extent Destination extent. - * @return {ol.Extent} Extent. - */ -ol.extent.getForViewAndSize = function(center, resolution, rotation, size, opt_extent) { - var dx = resolution * size[0] / 2; - var dy = resolution * size[1] / 2; - var cosRotation = Math.cos(rotation); - var sinRotation = Math.sin(rotation); - var xCos = dx * cosRotation; - var xSin = dx * sinRotation; - var yCos = dy * cosRotation; - var ySin = dy * sinRotation; - var x = center[0]; - var y = center[1]; - var x0 = x - xCos + ySin; - var x1 = x - xCos - ySin; - var x2 = x + xCos - ySin; - var x3 = x + xCos + ySin; - var y0 = y - xSin - yCos; - var y1 = y - xSin + yCos; - var y2 = y + xSin + yCos; - var y3 = y + xSin - yCos; - return ol.extent.createOrUpdate( - Math.min(x0, x1, x2, x3), Math.min(y0, y1, y2, y3), - Math.max(x0, x1, x2, x3), Math.max(y0, y1, y2, y3), - opt_extent); -}; - - -/** - * Get the height of an extent. - * @param {ol.Extent} extent Extent. - * @return {number} Height. - * @api - */ -ol.extent.getHeight = function(extent) { - return extent[3] - extent[1]; -}; - - -/** - * @param {ol.Extent} extent1 Extent 1. - * @param {ol.Extent} extent2 Extent 2. - * @return {number} Intersection area. - */ -ol.extent.getIntersectionArea = function(extent1, extent2) { - var intersection = ol.extent.getIntersection(extent1, extent2); - return ol.extent.getArea(intersection); -}; - - -/** - * Get the intersection of two extents. - * @param {ol.Extent} extent1 Extent 1. - * @param {ol.Extent} extent2 Extent 2. - * @param {ol.Extent=} opt_extent Optional extent to populate with intersection. - * @return {ol.Extent} Intersecting extent. - * @api - */ -ol.extent.getIntersection = function(extent1, extent2, opt_extent) { - var intersection = opt_extent ? opt_extent : ol.extent.createEmpty(); - if (ol.extent.intersects(extent1, extent2)) { - if (extent1[0] > extent2[0]) { - intersection[0] = extent1[0]; - } else { - intersection[0] = extent2[0]; - } - if (extent1[1] > extent2[1]) { - intersection[1] = extent1[1]; - } else { - intersection[1] = extent2[1]; - } - if (extent1[2] < extent2[2]) { - intersection[2] = extent1[2]; - } else { - intersection[2] = extent2[2]; - } - if (extent1[3] < extent2[3]) { - intersection[3] = extent1[3]; - } else { - intersection[3] = extent2[3]; - } - } - return intersection; -}; - - -/** - * @param {ol.Extent} extent Extent. - * @return {number} Margin. - */ -ol.extent.getMargin = function(extent) { - return ol.extent.getWidth(extent) + ol.extent.getHeight(extent); -}; - - -/** - * Get the size (width, height) of an extent. - * @param {ol.Extent} extent The extent. - * @return {ol.Size} The extent size. - * @api - */ -ol.extent.getSize = function(extent) { - return [extent[2] - extent[0], extent[3] - extent[1]]; -}; - - -/** - * Get the top left coordinate of an extent. - * @param {ol.Extent} extent Extent. - * @return {ol.Coordinate} Top left coordinate. - * @api - */ -ol.extent.getTopLeft = function(extent) { - return [extent[0], extent[3]]; -}; - - -/** - * Get the top right coordinate of an extent. - * @param {ol.Extent} extent Extent. - * @return {ol.Coordinate} Top right coordinate. - * @api - */ -ol.extent.getTopRight = function(extent) { - return [extent[2], extent[3]]; -}; - - -/** - * Get the width of an extent. - * @param {ol.Extent} extent Extent. - * @return {number} Width. - * @api - */ -ol.extent.getWidth = function(extent) { - return extent[2] - extent[0]; -}; - - -/** - * Determine if one extent intersects another. - * @param {ol.Extent} extent1 Extent 1. - * @param {ol.Extent} extent2 Extent. - * @return {boolean} The two extents intersect. - * @api - */ -ol.extent.intersects = function(extent1, extent2) { - return extent1[0] <= extent2[2] && - extent1[2] >= extent2[0] && - extent1[1] <= extent2[3] && - extent1[3] >= extent2[1]; -}; - - -/** - * Determine if an extent is empty. - * @param {ol.Extent} extent Extent. - * @return {boolean} Is empty. - * @api - */ -ol.extent.isEmpty = function(extent) { - return extent[2] < extent[0] || extent[3] < extent[1]; -}; - - -/** - * @param {ol.Extent} extent Extent. - * @param {ol.Extent=} opt_extent Extent. - * @return {ol.Extent} Extent. - */ -ol.extent.returnOrUpdate = function(extent, opt_extent) { - if (opt_extent) { - opt_extent[0] = extent[0]; - opt_extent[1] = extent[1]; - opt_extent[2] = extent[2]; - opt_extent[3] = extent[3]; - return opt_extent; - } else { - return extent; - } -}; - - -/** - * @param {ol.Extent} extent Extent. - * @param {number} value Value. - */ -ol.extent.scaleFromCenter = function(extent, value) { - var deltaX = ((extent[2] - extent[0]) / 2) * (value - 1); - var deltaY = ((extent[3] - extent[1]) / 2) * (value - 1); - extent[0] -= deltaX; - extent[2] += deltaX; - extent[1] -= deltaY; - extent[3] += deltaY; -}; - - -/** - * Determine if the segment between two coordinates intersects (crosses, - * touches, or is contained by) the provided extent. - * @param {ol.Extent} extent The extent. - * @param {ol.Coordinate} start Segment start coordinate. - * @param {ol.Coordinate} end Segment end coordinate. - * @return {boolean} The segment intersects the extent. - */ -ol.extent.intersectsSegment = function(extent, start, end) { - var intersects = false; - var startRel = ol.extent.coordinateRelationship(extent, start); - var endRel = ol.extent.coordinateRelationship(extent, end); - if (startRel === ol.extent.Relationship.INTERSECTING || - endRel === ol.extent.Relationship.INTERSECTING) { - intersects = true; - } else { - var minX = extent[0]; - var minY = extent[1]; - var maxX = extent[2]; - var maxY = extent[3]; - var startX = start[0]; - var startY = start[1]; - var endX = end[0]; - var endY = end[1]; - var slope = (endY - startY) / (endX - startX); - var x, y; - if (!!(endRel & ol.extent.Relationship.ABOVE) && - !(startRel & ol.extent.Relationship.ABOVE)) { - // potentially intersects top - x = endX - ((endY - maxY) / slope); - intersects = x >= minX && x <= maxX; - } - if (!intersects && !!(endRel & ol.extent.Relationship.RIGHT) && - !(startRel & ol.extent.Relationship.RIGHT)) { - // potentially intersects right - y = endY - ((endX - maxX) * slope); - intersects = y >= minY && y <= maxY; - } - if (!intersects && !!(endRel & ol.extent.Relationship.BELOW) && - !(startRel & ol.extent.Relationship.BELOW)) { - // potentially intersects bottom - x = endX - ((endY - minY) / slope); - intersects = x >= minX && x <= maxX; - } - if (!intersects && !!(endRel & ol.extent.Relationship.LEFT) && - !(startRel & ol.extent.Relationship.LEFT)) { - // potentially intersects left - y = endY - ((endX - minX) * slope); - intersects = y >= minY && y <= maxY; - } - - } - return intersects; -}; - - -/** - * Apply a transform function to the extent. - * @param {ol.Extent} extent Extent. - * @param {ol.TransformFunction} transformFn Transform function. Called with - * [minX, minY, maxX, maxY] extent coordinates. - * @param {ol.Extent=} opt_extent Destination extent. - * @return {ol.Extent} Extent. - * @api - */ -ol.extent.applyTransform = function(extent, transformFn, opt_extent) { - var coordinates = [ - extent[0], extent[1], - extent[0], extent[3], - extent[2], extent[1], - extent[2], extent[3] - ]; - transformFn(coordinates, coordinates, 2); - var xs = [coordinates[0], coordinates[2], coordinates[4], coordinates[6]]; - var ys = [coordinates[1], coordinates[3], coordinates[5], coordinates[7]]; - return ol.extent.boundingExtentXYs_(xs, ys, opt_extent); -}; - -goog.provide('ol.obj'); - - -/** - * Polyfill for Object.assign(). Assigns enumerable and own properties from - * one or more source objects to a target object. - * - * @see https://developer.mozilla.org/en/docs/Web/JavaScript/Reference/Global_Objects/Object/assign - * @param {!Object} target The target object. - * @param {...Object} var_sources The source object(s). - * @return {!Object} The modified target object. - */ -ol.obj.assign = (typeof Object.assign === 'function') ? Object.assign : function(target, var_sources) { - if (target === undefined || target === null) { - throw new TypeError('Cannot convert undefined or null to object'); - } - - var output = Object(target); - for (var i = 1, ii = arguments.length; i < ii; ++i) { - var source = arguments[i]; - if (source !== undefined && source !== null) { - for (var key in source) { - if (source.hasOwnProperty(key)) { - output[key] = source[key]; - } - } - } - } - return output; -}; - - -/** - * Removes all properties from an object. - * @param {Object} object The object to clear. - */ -ol.obj.clear = function(object) { - for (var property in object) { - delete object[property]; - } -}; - - -/** - * Get an array of property values from an object. - * @param {Object<K,V>} object The object from which to get the values. - * @return {!Array<V>} The property values. - * @template K,V - */ -ol.obj.getValues = function(object) { - var values = []; - for (var property in object) { - values.push(object[property]); - } - return values; -}; - - -/** - * Determine if an object has any properties. - * @param {Object} object The object to check. - * @return {boolean} The object is empty. - */ -ol.obj.isEmpty = function(object) { - var property; - for (property in object) { - return false; - } - return !property; -}; - -goog.provide('ol.geom.GeometryType'); - - -/** - * The geometry type. One of `'Point'`, `'LineString'`, `'LinearRing'`, - * `'Polygon'`, `'MultiPoint'`, `'MultiLineString'`, `'MultiPolygon'`, - * `'GeometryCollection'`, `'Circle'`. - * @enum {string} - */ -ol.geom.GeometryType = { - POINT: 'Point', - LINE_STRING: 'LineString', - LINEAR_RING: 'LinearRing', - POLYGON: 'Polygon', - MULTI_POINT: 'MultiPoint', - MULTI_LINE_STRING: 'MultiLineString', - MULTI_POLYGON: 'MultiPolygon', - GEOMETRY_COLLECTION: 'GeometryCollection', - CIRCLE: 'Circle' -}; - -/** - * @license - * Latitude/longitude spherical geodesy formulae taken from - * http://www.movable-type.co.uk/scripts/latlong.html - * Licensed under CC-BY-3.0. - */ - -goog.provide('ol.Sphere'); - -goog.require('ol.math'); -goog.require('ol.geom.GeometryType'); - - -/** - * @classdesc - * Class to create objects that can be used with {@link - * ol.geom.Polygon.circular}. - * - * For example to create a sphere whose radius is equal to the semi-major - * axis of the WGS84 ellipsoid: - * - * ```js - * var wgs84Sphere= new ol.Sphere(6378137); - * ``` - * - * @constructor - * @param {number} radius Radius. - * @api - */ -ol.Sphere = function(radius) { - - /** - * @type {number} - */ - this.radius = radius; - -}; - - -/** - * Returns the geodesic area for a list of coordinates. - * - * [Reference](https://trs-new.jpl.nasa.gov/handle/2014/40409) - * Robert. G. Chamberlain and William H. Duquette, "Some Algorithms for - * Polygons on a Sphere", JPL Publication 07-03, Jet Propulsion - * Laboratory, Pasadena, CA, June 2007 - * - * @param {Array.<ol.Coordinate>} coordinates List of coordinates of a linear - * ring. If the ring is oriented clockwise, the area will be positive, - * otherwise it will be negative. - * @return {number} Area. - * @api - */ -ol.Sphere.prototype.geodesicArea = function(coordinates) { - return ol.Sphere.getArea_(coordinates, this.radius); -}; - - -/** - * Returns the distance from c1 to c2 using the haversine formula. - * - * @param {ol.Coordinate} c1 Coordinate 1. - * @param {ol.Coordinate} c2 Coordinate 2. - * @return {number} Haversine distance. - * @api - */ -ol.Sphere.prototype.haversineDistance = function(c1, c2) { - return ol.Sphere.getDistance_(c1, c2, this.radius); -}; - - -/** - * Returns the coordinate at the given distance and bearing from `c1`. - * - * @param {ol.Coordinate} c1 The origin point (`[lon, lat]` in degrees). - * @param {number} distance The great-circle distance between the origin - * point and the target point. - * @param {number} bearing The bearing (in radians). - * @return {ol.Coordinate} The target point. - */ -ol.Sphere.prototype.offset = function(c1, distance, bearing) { - var lat1 = ol.math.toRadians(c1[1]); - var lon1 = ol.math.toRadians(c1[0]); - var dByR = distance / this.radius; - var lat = Math.asin( - Math.sin(lat1) * Math.cos(dByR) + - Math.cos(lat1) * Math.sin(dByR) * Math.cos(bearing)); - var lon = lon1 + Math.atan2( - Math.sin(bearing) * Math.sin(dByR) * Math.cos(lat1), - Math.cos(dByR) - Math.sin(lat1) * Math.sin(lat)); - return [ol.math.toDegrees(lon), ol.math.toDegrees(lat)]; -}; - - -/** - * The mean Earth radius (1/3 * (2a + b)) for the WGS84 ellipsoid. - * https://en.wikipedia.org/wiki/Earth_radius#Mean_radius - * @type {number} - */ -ol.Sphere.DEFAULT_RADIUS = 6371008.8; - - -/** - * Get the spherical length of a geometry. This length is the sum of the - * great circle distances between coordinates. For polygons, the length is - * the sum of all rings. For points, the length is zero. For multi-part - * geometries, the length is the sum of the length of each part. - * @param {ol.geom.Geometry} geometry A geometry. - * @param {olx.SphereMetricOptions=} opt_options Options for the length - * calculation. By default, geometries are assumed to be in 'EPSG:3857'. - * You can change this by providing a `projection` option. - * @return {number} The spherical length (in meters). - * @api - */ -ol.Sphere.getLength = function(geometry, opt_options) { - var options = opt_options || {}; - var radius = options.radius || ol.Sphere.DEFAULT_RADIUS; - var projection = options.projection || 'EPSG:3857'; - geometry = geometry.clone().transform(projection, 'EPSG:4326'); - var type = geometry.getType(); - var length = 0; - var coordinates, coords, i, ii, j, jj; - switch (type) { - case ol.geom.GeometryType.POINT: - case ol.geom.GeometryType.MULTI_POINT: { - break; - } - case ol.geom.GeometryType.LINE_STRING: - case ol.geom.GeometryType.LINEAR_RING: { - coordinates = /** @type {ol.geom.SimpleGeometry} */ (geometry).getCoordinates(); - length = ol.Sphere.getLength_(coordinates, radius); - break; - } - case ol.geom.GeometryType.MULTI_LINE_STRING: - case ol.geom.GeometryType.POLYGON: { - coordinates = /** @type {ol.geom.SimpleGeometry} */ (geometry).getCoordinates(); - for (i = 0, ii = coordinates.length; i < ii; ++i) { - length += ol.Sphere.getLength_(coordinates[i], radius); - } - break; - } - case ol.geom.GeometryType.MULTI_POLYGON: { - coordinates = /** @type {ol.geom.SimpleGeometry} */ (geometry).getCoordinates(); - for (i = 0, ii = coordinates.length; i < ii; ++i) { - coords = coordinates[i]; - for (j = 0, jj = coords.length; j < jj; ++j) { - length += ol.Sphere.getLength_(coords[j], radius); - } - } - break; - } - case ol.geom.GeometryType.GEOMETRY_COLLECTION: { - var geometries = /** @type {ol.geom.GeometryCollection} */ (geometry).getGeometries(); - for (i = 0, ii = geometries.length; i < ii; ++i) { - length += ol.Sphere.getLength(geometries[i], opt_options); - } - break; - } - default: { - throw new Error('Unsupported geometry type: ' + type); - } - } - return length; -}; - - -/** - * Get the cumulative great circle length of linestring coordinates (geographic). - * @param {Array} coordinates Linestring coordinates. - * @param {number} radius The sphere radius to use. - * @return {number} The length (in meters). - */ -ol.Sphere.getLength_ = function(coordinates, radius) { - var length = 0; - for (var i = 0, ii = coordinates.length; i < ii - 1; ++i) { - length += ol.Sphere.getDistance_(coordinates[i], coordinates[i + 1], radius); - } - return length; -}; - - -/** - * Get the great circle distance between two geographic coordinates. - * @param {Array} c1 Starting coordinate. - * @param {Array} c2 Ending coordinate. - * @param {number} radius The sphere radius to use. - * @return {number} The great circle distance between the points (in meters). - */ -ol.Sphere.getDistance_ = function(c1, c2, radius) { - var lat1 = ol.math.toRadians(c1[1]); - var lat2 = ol.math.toRadians(c2[1]); - var deltaLatBy2 = (lat2 - lat1) / 2; - var deltaLonBy2 = ol.math.toRadians(c2[0] - c1[0]) / 2; - var a = Math.sin(deltaLatBy2) * Math.sin(deltaLatBy2) + - Math.sin(deltaLonBy2) * Math.sin(deltaLonBy2) * - Math.cos(lat1) * Math.cos(lat2); - return 2 * radius * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a)); -}; - - -/** - * Get the spherical area of a geometry. This is the area (in meters) assuming - * that polygon edges are segments of great circles on a sphere. - * @param {ol.geom.Geometry} geometry A geometry. - * @param {olx.SphereMetricOptions=} opt_options Options for the area - * calculation. By default, geometries are assumed to be in 'EPSG:3857'. - * You can change this by providing a `projection` option. - * @return {number} The spherical area (in square meters). - * @api - */ -ol.Sphere.getArea = function(geometry, opt_options) { - var options = opt_options || {}; - var radius = options.radius || ol.Sphere.DEFAULT_RADIUS; - var projection = options.projection || 'EPSG:3857'; - geometry = geometry.clone().transform(projection, 'EPSG:4326'); - var type = geometry.getType(); - var area = 0; - var coordinates, coords, i, ii, j, jj; - switch (type) { - case ol.geom.GeometryType.POINT: - case ol.geom.GeometryType.MULTI_POINT: - case ol.geom.GeometryType.LINE_STRING: - case ol.geom.GeometryType.MULTI_LINE_STRING: - case ol.geom.GeometryType.LINEAR_RING: { - break; - } - case ol.geom.GeometryType.POLYGON: { - coordinates = /** @type {ol.geom.Polygon} */ (geometry).getCoordinates(); - area = Math.abs(ol.Sphere.getArea_(coordinates[0], radius)); - for (i = 1, ii = coordinates.length; i < ii; ++i) { - area -= Math.abs(ol.Sphere.getArea_(coordinates[i], radius)); - } - break; - } - case ol.geom.GeometryType.MULTI_POLYGON: { - coordinates = /** @type {ol.geom.SimpleGeometry} */ (geometry).getCoordinates(); - for (i = 0, ii = coordinates.length; i < ii; ++i) { - coords = coordinates[i]; - area += Math.abs(ol.Sphere.getArea_(coords[0], radius)); - for (j = 1, jj = coords.length; j < jj; ++j) { - area -= Math.abs(ol.Sphere.getArea_(coords[j], radius)); - } - } - break; - } - case ol.geom.GeometryType.GEOMETRY_COLLECTION: { - var geometries = /** @type {ol.geom.GeometryCollection} */ (geometry).getGeometries(); - for (i = 0, ii = geometries.length; i < ii; ++i) { - area += ol.Sphere.getArea(geometries[i], opt_options); - } - break; - } - default: { - throw new Error('Unsupported geometry type: ' + type); - } - } - return area; -}; - - -/** - * Returns the spherical area for a list of coordinates. - * - * [Reference](https://trs-new.jpl.nasa.gov/handle/2014/40409) - * Robert. G. Chamberlain and William H. Duquette, "Some Algorithms for - * Polygons on a Sphere", JPL Publication 07-03, Jet Propulsion - * Laboratory, Pasadena, CA, June 2007 - * - * @param {Array.<ol.Coordinate>} coordinates List of coordinates of a linear - * ring. If the ring is oriented clockwise, the area will be positive, - * otherwise it will be negative. - * @param {number} radius The sphere radius. - * @return {number} Area (in square meters). - */ -ol.Sphere.getArea_ = function(coordinates, radius) { - var area = 0, len = coordinates.length; - var x1 = coordinates[len - 1][0]; - var y1 = coordinates[len - 1][1]; - for (var i = 0; i < len; i++) { - var x2 = coordinates[i][0], y2 = coordinates[i][1]; - area += ol.math.toRadians(x2 - x1) * - (2 + Math.sin(ol.math.toRadians(y1)) + - Math.sin(ol.math.toRadians(y2))); - x1 = x2; - y1 = y2; - } - return area * radius * radius / 2.0; -}; - -goog.provide('ol.proj.Units'); - - -/** - * Projection units: `'degrees'`, `'ft'`, `'m'`, `'pixels'`, `'tile-pixels'` or - * `'us-ft'`. - * @enum {string} - */ -ol.proj.Units = { - DEGREES: 'degrees', - FEET: 'ft', - METERS: 'm', - PIXELS: 'pixels', - TILE_PIXELS: 'tile-pixels', - USFEET: 'us-ft' -}; - - -/** - * Meters per unit lookup table. - * @const - * @type {Object.<ol.proj.Units, number>} - * @api - */ -ol.proj.Units.METERS_PER_UNIT = {}; -// use the radius of the Normal sphere -ol.proj.Units.METERS_PER_UNIT[ol.proj.Units.DEGREES] = - 2 * Math.PI * 6370997 / 360; -ol.proj.Units.METERS_PER_UNIT[ol.proj.Units.FEET] = 0.3048; -ol.proj.Units.METERS_PER_UNIT[ol.proj.Units.METERS] = 1; -ol.proj.Units.METERS_PER_UNIT[ol.proj.Units.USFEET] = 1200 / 3937; - -goog.provide('ol.proj.proj4'); - - -/** - * @private - * @type {Proj4} - */ -ol.proj.proj4.cache_ = null; - - -/** - * Store the proj4 function. - * @param {Proj4} proj4 The proj4 function. - */ -ol.proj.proj4.set = function(proj4) { - ol.proj.proj4.cache_ = proj4; -}; - - -/** - * Get proj4. - * @return {Proj4} The proj4 function set above or available globally. - */ -ol.proj.proj4.get = function() { - return ol.proj.proj4.cache_ || window['proj4']; -}; - -goog.provide('ol.proj.Projection'); - -goog.require('ol'); -goog.require('ol.proj.Units'); -goog.require('ol.proj.proj4'); - - -/** - * @classdesc - * Projection definition class. One of these is created for each projection - * supported in the application and stored in the {@link ol.proj} namespace. - * You can use these in applications, but this is not required, as API params - * and options use {@link ol.ProjectionLike} which means the simple string - * code will suffice. - * - * You can use {@link ol.proj.get} to retrieve the object for a particular - * projection. - * - * The library includes definitions for `EPSG:4326` and `EPSG:3857`, together - * with the following aliases: - * * `EPSG:4326`: CRS:84, urn:ogc:def:crs:EPSG:6.6:4326, - * urn:ogc:def:crs:OGC:1.3:CRS84, urn:ogc:def:crs:OGC:2:84, - * http://www.opengis.net/gml/srs/epsg.xml#4326, - * urn:x-ogc:def:crs:EPSG:4326 - * * `EPSG:3857`: EPSG:102100, EPSG:102113, EPSG:900913, - * urn:ogc:def:crs:EPSG:6.18:3:3857, - * http://www.opengis.net/gml/srs/epsg.xml#3857 - * - * If you use proj4js, aliases can be added using `proj4.defs()`; see - * [documentation](https://github.com/proj4js/proj4js). To set an alternative - * namespace for proj4, use {@link ol.proj.setProj4}. - * - * @constructor - * @param {olx.ProjectionOptions} options Projection options. - * @struct - * @api - */ -ol.proj.Projection = function(options) { - /** - * @private - * @type {string} - */ - this.code_ = options.code; - - /** - * Units of projected coordinates. When set to `ol.proj.Units.TILE_PIXELS`, a - * `this.extent_` and `this.worldExtent_` must be configured properly for each - * tile. - * @private - * @type {ol.proj.Units} - */ - this.units_ = /** @type {ol.proj.Units} */ (options.units); - - /** - * Validity extent of the projection in projected coordinates. For projections - * with `ol.proj.Units.TILE_PIXELS` units, this is the extent of the tile in - * tile pixel space. - * @private - * @type {ol.Extent} - */ - this.extent_ = options.extent !== undefined ? options.extent : null; - - /** - * Extent of the world in EPSG:4326. For projections with - * `ol.proj.Units.TILE_PIXELS` units, this is the extent of the tile in - * projected coordinate space. - * @private - * @type {ol.Extent} - */ - this.worldExtent_ = options.worldExtent !== undefined ? - options.worldExtent : null; - - /** - * @private - * @type {string} - */ - this.axisOrientation_ = options.axisOrientation !== undefined ? - options.axisOrientation : 'enu'; - - /** - * @private - * @type {boolean} - */ - this.global_ = options.global !== undefined ? options.global : false; - - /** - * @private - * @type {boolean} - */ - this.canWrapX_ = !!(this.global_ && this.extent_); - - /** - * @private - * @type {function(number, ol.Coordinate):number|undefined} - */ - this.getPointResolutionFunc_ = options.getPointResolution; - - /** - * @private - * @type {ol.tilegrid.TileGrid} - */ - this.defaultTileGrid_ = null; - - /** - * @private - * @type {number|undefined} - */ - this.metersPerUnit_ = options.metersPerUnit; - - var code = options.code; - if (ol.ENABLE_PROJ4JS) { - var proj4js = ol.proj.proj4.get(); - if (typeof proj4js == 'function') { - var def = proj4js.defs(code); - if (def !== undefined) { - if (def.axis !== undefined && options.axisOrientation === undefined) { - this.axisOrientation_ = def.axis; - } - if (options.metersPerUnit === undefined) { - this.metersPerUnit_ = def.to_meter; - } - if (options.units === undefined) { - this.units_ = def.units; - } - } - } - } -}; - - -/** - * @return {boolean} The projection is suitable for wrapping the x-axis - */ -ol.proj.Projection.prototype.canWrapX = function() { - return this.canWrapX_; -}; - - -/** - * Get the code for this projection, e.g. 'EPSG:4326'. - * @return {string} Code. - * @api - */ -ol.proj.Projection.prototype.getCode = function() { - return this.code_; -}; - - -/** - * Get the validity extent for this projection. - * @return {ol.Extent} Extent. - * @api - */ -ol.proj.Projection.prototype.getExtent = function() { - return this.extent_; -}; - - -/** - * Get the units of this projection. - * @return {ol.proj.Units} Units. - * @api - */ -ol.proj.Projection.prototype.getUnits = function() { - return this.units_; -}; - - -/** - * Get the amount of meters per unit of this projection. If the projection is - * not configured with `metersPerUnit` or a units identifier, the return is - * `undefined`. - * @return {number|undefined} Meters. - * @api - */ -ol.proj.Projection.prototype.getMetersPerUnit = function() { - return this.metersPerUnit_ || ol.proj.Units.METERS_PER_UNIT[this.units_]; -}; - - -/** - * Get the world extent for this projection. - * @return {ol.Extent} Extent. - * @api - */ -ol.proj.Projection.prototype.getWorldExtent = function() { - return this.worldExtent_; -}; - - -/** - * Get the axis orientation of this projection. - * Example values are: - * enu - the default easting, northing, elevation. - * neu - northing, easting, up - useful for "lat/long" geographic coordinates, - * or south orientated transverse mercator. - * wnu - westing, northing, up - some planetary coordinate systems have - * "west positive" coordinate systems - * @return {string} Axis orientation. - */ -ol.proj.Projection.prototype.getAxisOrientation = function() { - return this.axisOrientation_; -}; - - -/** - * Is this projection a global projection which spans the whole world? - * @return {boolean} Whether the projection is global. - * @api - */ -ol.proj.Projection.prototype.isGlobal = function() { - return this.global_; -}; - - -/** -* Set if the projection is a global projection which spans the whole world -* @param {boolean} global Whether the projection is global. -* @api -*/ -ol.proj.Projection.prototype.setGlobal = function(global) { - this.global_ = global; - this.canWrapX_ = !!(global && this.extent_); -}; - - -/** - * @return {ol.tilegrid.TileGrid} The default tile grid. - */ -ol.proj.Projection.prototype.getDefaultTileGrid = function() { - return this.defaultTileGrid_; -}; - - -/** - * @param {ol.tilegrid.TileGrid} tileGrid The default tile grid. - */ -ol.proj.Projection.prototype.setDefaultTileGrid = function(tileGrid) { - this.defaultTileGrid_ = tileGrid; -}; - - -/** - * Set the validity extent for this projection. - * @param {ol.Extent} extent Extent. - * @api - */ -ol.proj.Projection.prototype.setExtent = function(extent) { - this.extent_ = extent; - this.canWrapX_ = !!(this.global_ && extent); -}; - - -/** - * Set the world extent for this projection. - * @param {ol.Extent} worldExtent World extent - * [minlon, minlat, maxlon, maxlat]. - * @api - */ -ol.proj.Projection.prototype.setWorldExtent = function(worldExtent) { - this.worldExtent_ = worldExtent; -}; - - -/** - * Set the getPointResolution function (see {@link ol.proj#getPointResolution} - * for this projection. - * @param {function(number, ol.Coordinate):number} func Function - * @api - */ -ol.proj.Projection.prototype.setGetPointResolution = function(func) { - this.getPointResolutionFunc_ = func; -}; - - -/** - * Get the custom point resolution function for this projection (if set). - * @return {function(number, ol.Coordinate):number|undefined} The custom point - * resolution function (if set). - */ -ol.proj.Projection.prototype.getPointResolutionFunc = function() { - return this.getPointResolutionFunc_; -}; - -goog.provide('ol.proj.EPSG3857'); - -goog.require('ol'); -goog.require('ol.math'); -goog.require('ol.proj.Projection'); -goog.require('ol.proj.Units'); - - -/** - * @classdesc - * Projection object for web/spherical Mercator (EPSG:3857). - * - * @constructor - * @extends {ol.proj.Projection} - * @param {string} code Code. - * @private - */ -ol.proj.EPSG3857.Projection_ = function(code) { - ol.proj.Projection.call(this, { - code: code, - units: ol.proj.Units.METERS, - extent: ol.proj.EPSG3857.EXTENT, - global: true, - worldExtent: ol.proj.EPSG3857.WORLD_EXTENT, - getPointResolution: function(resolution, point) { - return resolution / ol.math.cosh(point[1] / ol.proj.EPSG3857.RADIUS); - } - }); -}; -ol.inherits(ol.proj.EPSG3857.Projection_, ol.proj.Projection); - - -/** - * Radius of WGS84 sphere - * - * @const - * @type {number} - */ -ol.proj.EPSG3857.RADIUS = 6378137; - - -/** - * @const - * @type {number} - */ -ol.proj.EPSG3857.HALF_SIZE = Math.PI * ol.proj.EPSG3857.RADIUS; - - -/** - * @const - * @type {ol.Extent} - */ -ol.proj.EPSG3857.EXTENT = [ - -ol.proj.EPSG3857.HALF_SIZE, -ol.proj.EPSG3857.HALF_SIZE, - ol.proj.EPSG3857.HALF_SIZE, ol.proj.EPSG3857.HALF_SIZE -]; - - -/** - * @const - * @type {ol.Extent} - */ -ol.proj.EPSG3857.WORLD_EXTENT = [-180, -85, 180, 85]; - - -/** - * Projections equal to EPSG:3857. - * - * @const - * @type {Array.<ol.proj.Projection>} - */ -ol.proj.EPSG3857.PROJECTIONS = [ - new ol.proj.EPSG3857.Projection_('EPSG:3857'), - new ol.proj.EPSG3857.Projection_('EPSG:102100'), - new ol.proj.EPSG3857.Projection_('EPSG:102113'), - new ol.proj.EPSG3857.Projection_('EPSG:900913'), - new ol.proj.EPSG3857.Projection_('urn:ogc:def:crs:EPSG:6.18:3:3857'), - new ol.proj.EPSG3857.Projection_('urn:ogc:def:crs:EPSG::3857'), - new ol.proj.EPSG3857.Projection_('http://www.opengis.net/gml/srs/epsg.xml#3857') -]; - - -/** - * Transformation from EPSG:4326 to EPSG:3857. - * - * @param {Array.<number>} input Input array of coordinate values. - * @param {Array.<number>=} opt_output Output array of coordinate values. - * @param {number=} opt_dimension Dimension (default is `2`). - * @return {Array.<number>} Output array of coordinate values. - */ -ol.proj.EPSG3857.fromEPSG4326 = function(input, opt_output, opt_dimension) { - var length = input.length, - dimension = opt_dimension > 1 ? opt_dimension : 2, - output = opt_output; - if (output === undefined) { - if (dimension > 2) { - // preserve values beyond second dimension - output = input.slice(); - } else { - output = new Array(length); - } - } - var halfSize = ol.proj.EPSG3857.HALF_SIZE; - for (var i = 0; i < length; i += dimension) { - output[i] = halfSize * input[i] / 180; - var y = ol.proj.EPSG3857.RADIUS * - Math.log(Math.tan(Math.PI * (input[i + 1] + 90) / 360)); - if (y > halfSize) { - y = halfSize; - } else if (y < -halfSize) { - y = -halfSize; - } - output[i + 1] = y; - } - return output; -}; - - -/** - * Transformation from EPSG:3857 to EPSG:4326. - * - * @param {Array.<number>} input Input array of coordinate values. - * @param {Array.<number>=} opt_output Output array of coordinate values. - * @param {number=} opt_dimension Dimension (default is `2`). - * @return {Array.<number>} Output array of coordinate values. - */ -ol.proj.EPSG3857.toEPSG4326 = function(input, opt_output, opt_dimension) { - var length = input.length, - dimension = opt_dimension > 1 ? opt_dimension : 2, - output = opt_output; - if (output === undefined) { - if (dimension > 2) { - // preserve values beyond second dimension - output = input.slice(); - } else { - output = new Array(length); - } - } - for (var i = 0; i < length; i += dimension) { - output[i] = 180 * input[i] / ol.proj.EPSG3857.HALF_SIZE; - output[i + 1] = 360 * Math.atan( - Math.exp(input[i + 1] / ol.proj.EPSG3857.RADIUS)) / Math.PI - 90; - } - return output; -}; - -goog.provide('ol.proj.EPSG4326'); - -goog.require('ol'); -goog.require('ol.proj.Projection'); -goog.require('ol.proj.Units'); - - -/** - * @classdesc - * Projection object for WGS84 geographic coordinates (EPSG:4326). - * - * Note that OpenLayers does not strictly comply with the EPSG definition. - * The EPSG registry defines 4326 as a CRS for Latitude,Longitude (y,x). - * OpenLayers treats EPSG:4326 as a pseudo-projection, with x,y coordinates. - * - * @constructor - * @extends {ol.proj.Projection} - * @param {string} code Code. - * @param {string=} opt_axisOrientation Axis orientation. - * @private - */ -ol.proj.EPSG4326.Projection_ = function(code, opt_axisOrientation) { - ol.proj.Projection.call(this, { - code: code, - units: ol.proj.Units.DEGREES, - extent: ol.proj.EPSG4326.EXTENT, - axisOrientation: opt_axisOrientation, - global: true, - metersPerUnit: ol.proj.EPSG4326.METERS_PER_UNIT, - worldExtent: ol.proj.EPSG4326.EXTENT - }); -}; -ol.inherits(ol.proj.EPSG4326.Projection_, ol.proj.Projection); - - -/** - * Radius of WGS84 sphere - * - * @const - * @type {number} - */ -ol.proj.EPSG4326.RADIUS = 6378137; - - -/** - * Extent of the EPSG:4326 projection which is the whole world. - * - * @const - * @type {ol.Extent} - */ -ol.proj.EPSG4326.EXTENT = [-180, -90, 180, 90]; - - -/** - * @const - * @type {number} - */ -ol.proj.EPSG4326.METERS_PER_UNIT = Math.PI * ol.proj.EPSG4326.RADIUS / 180; - - -/** - * Projections equal to EPSG:4326. - * - * @const - * @type {Array.<ol.proj.Projection>} - */ -ol.proj.EPSG4326.PROJECTIONS = [ - new ol.proj.EPSG4326.Projection_('CRS:84'), - new ol.proj.EPSG4326.Projection_('EPSG:4326', 'neu'), - new ol.proj.EPSG4326.Projection_('urn:ogc:def:crs:EPSG::4326', 'neu'), - new ol.proj.EPSG4326.Projection_('urn:ogc:def:crs:EPSG:6.6:4326', 'neu'), - new ol.proj.EPSG4326.Projection_('urn:ogc:def:crs:OGC:1.3:CRS84'), - new ol.proj.EPSG4326.Projection_('urn:ogc:def:crs:OGC:2:84'), - new ol.proj.EPSG4326.Projection_('http://www.opengis.net/gml/srs/epsg.xml#4326', 'neu'), - new ol.proj.EPSG4326.Projection_('urn:x-ogc:def:crs:EPSG:4326', 'neu') -]; - -goog.provide('ol.proj.projections'); - - -/** - * @private - * @type {Object.<string, ol.proj.Projection>} - */ -ol.proj.projections.cache_ = {}; - - -/** - * Clear the projections cache. - */ -ol.proj.projections.clear = function() { - ol.proj.projections.cache_ = {}; -}; - - -/** - * Get a cached projection by code. - * @param {string} code The code for the projection. - * @return {ol.proj.Projection} The projection (if cached). - */ -ol.proj.projections.get = function(code) { - var projections = ol.proj.projections.cache_; - return projections[code] || null; -}; - - -/** - * Add a projection to the cache. - * @param {string} code The projection code. - * @param {ol.proj.Projection} projection The projection to cache. - */ -ol.proj.projections.add = function(code, projection) { - var projections = ol.proj.projections.cache_; - projections[code] = projection; -}; - -goog.provide('ol.proj.transforms'); - -goog.require('ol.obj'); - - -/** - * @private - * @type {Object.<string, Object.<string, ol.TransformFunction>>} - */ -ol.proj.transforms.cache_ = {}; - - -/** - * Clear the transform cache. - */ -ol.proj.transforms.clear = function() { - ol.proj.transforms.cache_ = {}; -}; - - -/** - * Registers a conversion function to convert coordinates from the source - * projection to the destination projection. - * - * @param {ol.proj.Projection} source Source. - * @param {ol.proj.Projection} destination Destination. - * @param {ol.TransformFunction} transformFn Transform. - */ -ol.proj.transforms.add = function(source, destination, transformFn) { - var sourceCode = source.getCode(); - var destinationCode = destination.getCode(); - var transforms = ol.proj.transforms.cache_; - if (!(sourceCode in transforms)) { - transforms[sourceCode] = {}; - } - transforms[sourceCode][destinationCode] = transformFn; -}; - - -/** - * Unregisters the conversion function to convert coordinates from the source - * projection to the destination projection. This method is used to clean up - * cached transforms during testing. - * - * @param {ol.proj.Projection} source Source projection. - * @param {ol.proj.Projection} destination Destination projection. - * @return {ol.TransformFunction} transformFn The unregistered transform. - */ -ol.proj.transforms.remove = function(source, destination) { - var sourceCode = source.getCode(); - var destinationCode = destination.getCode(); - var transforms = ol.proj.transforms.cache_; - var transform = transforms[sourceCode][destinationCode]; - delete transforms[sourceCode][destinationCode]; - if (ol.obj.isEmpty(transforms[sourceCode])) { - delete transforms[sourceCode]; - } - return transform; -}; - - -/** - * Get a transform given a source code and a destination code. - * @param {string} sourceCode The code for the source projection. - * @param {string} destinationCode The code for the destination projection. - * @return {ol.TransformFunction|undefined} The transform function (if found). - */ -ol.proj.transforms.get = function(sourceCode, destinationCode) { - var transform; - var transforms = ol.proj.transforms.cache_; - if (sourceCode in transforms && destinationCode in transforms[sourceCode]) { - transform = transforms[sourceCode][destinationCode]; - } - return transform; -}; - -goog.provide('ol.proj'); - -goog.require('ol'); -goog.require('ol.Sphere'); -goog.require('ol.extent'); -goog.require('ol.proj.EPSG3857'); -goog.require('ol.proj.EPSG4326'); -goog.require('ol.proj.Projection'); -goog.require('ol.proj.Units'); -goog.require('ol.proj.proj4'); -goog.require('ol.proj.projections'); -goog.require('ol.proj.transforms'); - - -/** - * Meters per unit lookup table. - * @const - * @type {Object.<ol.proj.Units, number>} - * @api - */ -ol.proj.METERS_PER_UNIT = ol.proj.Units.METERS_PER_UNIT; - - -/** - * A place to store the mean radius of the Earth. - * @private - * @type {ol.Sphere} - */ -ol.proj.SPHERE_ = new ol.Sphere(ol.Sphere.DEFAULT_RADIUS); - - -if (ol.ENABLE_PROJ4JS) { - /** - * Register proj4. If not explicitly registered, it will be assumed that - * proj4js will be loaded in the global namespace. For example in a - * browserify ES6 environment you could use: - * - * import ol from 'openlayers'; - * import proj4 from 'proj4'; - * ol.proj.setProj4(proj4); - * - * @param {Proj4} proj4 Proj4. - * @api - */ - ol.proj.setProj4 = function(proj4) { - ol.proj.proj4.set(proj4); - }; -} - - -/** - * Get the resolution of the point in degrees or distance units. - * For projections with degrees as the unit this will simply return the - * provided resolution. For other projections the point resolution is - * by default estimated by transforming the 'point' pixel to EPSG:4326, - * measuring its width and height on the normal sphere, - * and taking the average of the width and height. - * A custom function can be provided for a specific projection, either - * by setting the `getPointResolution` option in the - * {@link ol.proj.Projection} constructor or by using - * {@link ol.proj.Projection#setGetPointResolution} to change an existing - * projection object. - * @param {ol.ProjectionLike} projection The projection. - * @param {number} resolution Nominal resolution in projection units. - * @param {ol.Coordinate} point Point to find adjusted resolution at. - * @param {ol.proj.Units=} opt_units Units to get the point resolution in. - * Default is the projection's units. - * @return {number} Point resolution. - * @api - */ -ol.proj.getPointResolution = function(projection, resolution, point, opt_units) { - projection = ol.proj.get(projection); - var pointResolution; - var getter = projection.getPointResolutionFunc(); - if (getter) { - pointResolution = getter(resolution, point); - } else { - var units = projection.getUnits(); - if (units == ol.proj.Units.DEGREES && !opt_units || opt_units == ol.proj.Units.DEGREES) { - pointResolution = resolution; - } else { - // Estimate point resolution by transforming the center pixel to EPSG:4326, - // measuring its width and height on the normal sphere, and taking the - // average of the width and height. - var toEPSG4326 = ol.proj.getTransformFromProjections(projection, ol.proj.get('EPSG:4326')); - var vertices = [ - point[0] - resolution / 2, point[1], - point[0] + resolution / 2, point[1], - point[0], point[1] - resolution / 2, - point[0], point[1] + resolution / 2 - ]; - vertices = toEPSG4326(vertices, vertices, 2); - var width = ol.proj.SPHERE_.haversineDistance( - vertices.slice(0, 2), vertices.slice(2, 4)); - var height = ol.proj.SPHERE_.haversineDistance( - vertices.slice(4, 6), vertices.slice(6, 8)); - pointResolution = (width + height) / 2; - var metersPerUnit = opt_units ? - ol.proj.Units.METERS_PER_UNIT[opt_units] : - projection.getMetersPerUnit(); - if (metersPerUnit !== undefined) { - pointResolution /= metersPerUnit; - } - } - } - return pointResolution; -}; - - -/** - * Registers transformation functions that don't alter coordinates. Those allow - * to transform between projections with equal meaning. - * - * @param {Array.<ol.proj.Projection>} projections Projections. - * @api - */ -ol.proj.addEquivalentProjections = function(projections) { - ol.proj.addProjections(projections); - projections.forEach(function(source) { - projections.forEach(function(destination) { - if (source !== destination) { - ol.proj.transforms.add(source, destination, ol.proj.cloneTransform); - } - }); - }); -}; - - -/** - * Registers transformation functions to convert coordinates in any projection - * in projection1 to any projection in projection2. - * - * @param {Array.<ol.proj.Projection>} projections1 Projections with equal - * meaning. - * @param {Array.<ol.proj.Projection>} projections2 Projections with equal - * meaning. - * @param {ol.TransformFunction} forwardTransform Transformation from any - * projection in projection1 to any projection in projection2. - * @param {ol.TransformFunction} inverseTransform Transform from any projection - * in projection2 to any projection in projection1.. - */ -ol.proj.addEquivalentTransforms = function(projections1, projections2, forwardTransform, inverseTransform) { - projections1.forEach(function(projection1) { - projections2.forEach(function(projection2) { - ol.proj.transforms.add(projection1, projection2, forwardTransform); - ol.proj.transforms.add(projection2, projection1, inverseTransform); - }); - }); -}; - - -/** - * Add a Projection object to the list of supported projections that can be - * looked up by their code. - * - * @param {ol.proj.Projection} projection Projection instance. - * @api - */ -ol.proj.addProjection = function(projection) { - ol.proj.projections.add(projection.getCode(), projection); - ol.proj.transforms.add(projection, projection, ol.proj.cloneTransform); -}; - - -/** - * @param {Array.<ol.proj.Projection>} projections Projections. - */ -ol.proj.addProjections = function(projections) { - projections.forEach(ol.proj.addProjection); -}; - - -/** - * Clear all cached projections and transforms. - */ -ol.proj.clearAllProjections = function() { - ol.proj.projections.clear(); - ol.proj.transforms.clear(); -}; - - -/** - * @param {ol.proj.Projection|string|undefined} projection Projection. - * @param {string} defaultCode Default code. - * @return {ol.proj.Projection} Projection. - */ -ol.proj.createProjection = function(projection, defaultCode) { - if (!projection) { - return ol.proj.get(defaultCode); - } else if (typeof projection === 'string') { - return ol.proj.get(projection); - } else { - return /** @type {ol.proj.Projection} */ (projection); - } -}; - - -/** - * Registers coordinate transform functions to convert coordinates between the - * source projection and the destination projection. - * The forward and inverse functions convert coordinate pairs; this function - * converts these into the functions used internally which also handle - * extents and coordinate arrays. - * - * @param {ol.ProjectionLike} source Source projection. - * @param {ol.ProjectionLike} destination Destination projection. - * @param {function(ol.Coordinate): ol.Coordinate} forward The forward transform - * function (that is, from the source projection to the destination - * projection) that takes a {@link ol.Coordinate} as argument and returns - * the transformed {@link ol.Coordinate}. - * @param {function(ol.Coordinate): ol.Coordinate} inverse The inverse transform - * function (that is, from the destination projection to the source - * projection) that takes a {@link ol.Coordinate} as argument and returns - * the transformed {@link ol.Coordinate}. - * @api - */ -ol.proj.addCoordinateTransforms = function(source, destination, forward, inverse) { - var sourceProj = ol.proj.get(source); - var destProj = ol.proj.get(destination); - ol.proj.transforms.add(sourceProj, destProj, - ol.proj.createTransformFromCoordinateTransform(forward)); - ol.proj.transforms.add(destProj, sourceProj, - ol.proj.createTransformFromCoordinateTransform(inverse)); -}; - - -/** - * Creates a {@link ol.TransformFunction} from a simple 2D coordinate transform - * function. - * @param {function(ol.Coordinate): ol.Coordinate} transform Coordinate - * transform. - * @return {ol.TransformFunction} Transform function. - */ -ol.proj.createTransformFromCoordinateTransform = function(transform) { - return ( - /** - * @param {Array.<number>} input Input. - * @param {Array.<number>=} opt_output Output. - * @param {number=} opt_dimension Dimension. - * @return {Array.<number>} Output. - */ - function(input, opt_output, opt_dimension) { - var length = input.length; - var dimension = opt_dimension !== undefined ? opt_dimension : 2; - var output = opt_output !== undefined ? opt_output : new Array(length); - var point, i, j; - for (i = 0; i < length; i += dimension) { - point = transform([input[i], input[i + 1]]); - output[i] = point[0]; - output[i + 1] = point[1]; - for (j = dimension - 1; j >= 2; --j) { - output[i + j] = input[i + j]; - } - } - return output; - }); -}; - - -/** - * Transforms a coordinate from longitude/latitude to a different projection. - * @param {ol.Coordinate} coordinate Coordinate as longitude and latitude, i.e. - * an array with longitude as 1st and latitude as 2nd element. - * @param {ol.ProjectionLike=} opt_projection Target projection. The - * default is Web Mercator, i.e. 'EPSG:3857'. - * @return {ol.Coordinate} Coordinate projected to the target projection. - * @api - */ -ol.proj.fromLonLat = function(coordinate, opt_projection) { - return ol.proj.transform(coordinate, 'EPSG:4326', - opt_projection !== undefined ? opt_projection : 'EPSG:3857'); -}; - - -/** - * Transforms a coordinate to longitude/latitude. - * @param {ol.Coordinate} coordinate Projected coordinate. - * @param {ol.ProjectionLike=} opt_projection Projection of the coordinate. - * The default is Web Mercator, i.e. 'EPSG:3857'. - * @return {ol.Coordinate} Coordinate as longitude and latitude, i.e. an array - * with longitude as 1st and latitude as 2nd element. - * @api - */ -ol.proj.toLonLat = function(coordinate, opt_projection) { - return ol.proj.transform(coordinate, - opt_projection !== undefined ? opt_projection : 'EPSG:3857', 'EPSG:4326'); -}; - - -/** - * Fetches a Projection object for the code specified. - * - * @param {ol.ProjectionLike} projectionLike Either a code string which is - * a combination of authority and identifier such as "EPSG:4326", or an - * existing projection object, or undefined. - * @return {ol.proj.Projection} Projection object, or null if not in list. - * @api - */ -ol.proj.get = function(projectionLike) { - var projection = null; - if (projectionLike instanceof ol.proj.Projection) { - projection = projectionLike; - } else if (typeof projectionLike === 'string') { - var code = projectionLike; - projection = ol.proj.projections.get(code); - if (ol.ENABLE_PROJ4JS && !projection) { - var proj4js = ol.proj.proj4.get(); - if (typeof proj4js == 'function' && - proj4js.defs(code) !== undefined) { - projection = new ol.proj.Projection({code: code}); - ol.proj.addProjection(projection); - } - } - } - return projection; -}; - - -/** - * Checks if two projections are the same, that is every coordinate in one - * projection does represent the same geographic point as the same coordinate in - * the other projection. - * - * @param {ol.proj.Projection} projection1 Projection 1. - * @param {ol.proj.Projection} projection2 Projection 2. - * @return {boolean} Equivalent. - * @api - */ -ol.proj.equivalent = function(projection1, projection2) { - if (projection1 === projection2) { - return true; - } - var equalUnits = projection1.getUnits() === projection2.getUnits(); - if (projection1.getCode() === projection2.getCode()) { - return equalUnits; - } else { - var transformFn = ol.proj.getTransformFromProjections( - projection1, projection2); - return transformFn === ol.proj.cloneTransform && equalUnits; - } -}; - - -/** - * Given the projection-like objects, searches for a transformation - * function to convert a coordinates array from the source projection to the - * destination projection. - * - * @param {ol.ProjectionLike} source Source. - * @param {ol.ProjectionLike} destination Destination. - * @return {ol.TransformFunction} Transform function. - * @api - */ -ol.proj.getTransform = function(source, destination) { - var sourceProjection = ol.proj.get(source); - var destinationProjection = ol.proj.get(destination); - return ol.proj.getTransformFromProjections( - sourceProjection, destinationProjection); -}; - - -/** - * Searches in the list of transform functions for the function for converting - * coordinates from the source projection to the destination projection. - * - * @param {ol.proj.Projection} sourceProjection Source Projection object. - * @param {ol.proj.Projection} destinationProjection Destination Projection - * object. - * @return {ol.TransformFunction} Transform function. - */ -ol.proj.getTransformFromProjections = function(sourceProjection, destinationProjection) { - var sourceCode = sourceProjection.getCode(); - var destinationCode = destinationProjection.getCode(); - var transform = ol.proj.transforms.get(sourceCode, destinationCode); - if (ol.ENABLE_PROJ4JS && !transform) { - var proj4js = ol.proj.proj4.get(); - if (typeof proj4js == 'function') { - var sourceDef = proj4js.defs(sourceCode); - var destinationDef = proj4js.defs(destinationCode); - - if (sourceDef !== undefined && destinationDef !== undefined) { - if (sourceDef === destinationDef) { - ol.proj.addEquivalentProjections([destinationProjection, sourceProjection]); - } else { - var proj4Transform = proj4js(destinationCode, sourceCode); - ol.proj.addCoordinateTransforms(destinationProjection, sourceProjection, - proj4Transform.forward, proj4Transform.inverse); - } - transform = ol.proj.transforms.get(sourceCode, destinationCode); - } - } - } - if (!transform) { - transform = ol.proj.identityTransform; - } - return transform; -}; - - -/** - * @param {Array.<number>} input Input coordinate array. - * @param {Array.<number>=} opt_output Output array of coordinate values. - * @param {number=} opt_dimension Dimension. - * @return {Array.<number>} Input coordinate array (same array as input). - */ -ol.proj.identityTransform = function(input, opt_output, opt_dimension) { - if (opt_output !== undefined && input !== opt_output) { - for (var i = 0, ii = input.length; i < ii; ++i) { - opt_output[i] = input[i]; - } - input = opt_output; - } - return input; -}; - - -/** - * @param {Array.<number>} input Input coordinate array. - * @param {Array.<number>=} opt_output Output array of coordinate values. - * @param {number=} opt_dimension Dimension. - * @return {Array.<number>} Output coordinate array (new array, same coordinate - * values). - */ -ol.proj.cloneTransform = function(input, opt_output, opt_dimension) { - var output; - if (opt_output !== undefined) { - for (var i = 0, ii = input.length; i < ii; ++i) { - opt_output[i] = input[i]; - } - output = opt_output; - } else { - output = input.slice(); - } - return output; -}; - - -/** - * Transforms a coordinate from source projection to destination projection. - * This returns a new coordinate (and does not modify the original). - * - * See {@link ol.proj.transformExtent} for extent transformation. - * See the transform method of {@link ol.geom.Geometry} and its subclasses for - * geometry transforms. - * - * @param {ol.Coordinate} coordinate Coordinate. - * @param {ol.ProjectionLike} source Source projection-like. - * @param {ol.ProjectionLike} destination Destination projection-like. - * @return {ol.Coordinate} Coordinate. - * @api - */ -ol.proj.transform = function(coordinate, source, destination) { - var transformFn = ol.proj.getTransform(source, destination); - return transformFn(coordinate, undefined, coordinate.length); -}; - - -/** - * Transforms an extent from source projection to destination projection. This - * returns a new extent (and does not modify the original). - * - * @param {ol.Extent} extent The extent to transform. - * @param {ol.ProjectionLike} source Source projection-like. - * @param {ol.ProjectionLike} destination Destination projection-like. - * @return {ol.Extent} The transformed extent. - * @api - */ -ol.proj.transformExtent = function(extent, source, destination) { - var transformFn = ol.proj.getTransform(source, destination); - return ol.extent.applyTransform(extent, transformFn); -}; - - -/** - * Transforms the given point to the destination projection. - * - * @param {ol.Coordinate} point Point. - * @param {ol.proj.Projection} sourceProjection Source projection. - * @param {ol.proj.Projection} destinationProjection Destination projection. - * @return {ol.Coordinate} Point. - */ -ol.proj.transformWithProjections = function(point, sourceProjection, destinationProjection) { - var transformFn = ol.proj.getTransformFromProjections( - sourceProjection, destinationProjection); - return transformFn(point); -}; - -/** - * Add transforms to and from EPSG:4326 and EPSG:3857. This function is called - * by when this module is executed and should only need to be called again after - * `ol.proj.clearAllProjections()` is called (e.g. in tests). - */ -ol.proj.addCommon = function() { - // Add transformations that don't alter coordinates to convert within set of - // projections with equal meaning. - ol.proj.addEquivalentProjections(ol.proj.EPSG3857.PROJECTIONS); - ol.proj.addEquivalentProjections(ol.proj.EPSG4326.PROJECTIONS); - // Add transformations to convert EPSG:4326 like coordinates to EPSG:3857 like - // coordinates and back. - ol.proj.addEquivalentTransforms( - ol.proj.EPSG4326.PROJECTIONS, - ol.proj.EPSG3857.PROJECTIONS, - ol.proj.EPSG3857.fromEPSG4326, - ol.proj.EPSG3857.toEPSG4326); -}; - -ol.proj.addCommon(); - -goog.provide('ol.tilecoord'); - - -/** - * @param {number} z Z. - * @param {number} x X. - * @param {number} y Y. - * @param {ol.TileCoord=} opt_tileCoord Tile coordinate. - * @return {ol.TileCoord} Tile coordinate. - */ -ol.tilecoord.createOrUpdate = function(z, x, y, opt_tileCoord) { - if (opt_tileCoord !== undefined) { - opt_tileCoord[0] = z; - opt_tileCoord[1] = x; - opt_tileCoord[2] = y; - return opt_tileCoord; - } else { - return [z, x, y]; - } -}; - - -/** - * @param {number} z Z. - * @param {number} x X. - * @param {number} y Y. - * @return {string} Key. - */ -ol.tilecoord.getKeyZXY = function(z, x, y) { - return z + '/' + x + '/' + y; -}; - - -/** - * Get the key for a tile coord. - * @param {ol.TileCoord} tileCoord The tile coord. - * @return {string} Key. - */ -ol.tilecoord.getKey = function(tileCoord) { - return ol.tilecoord.getKeyZXY(tileCoord[0], tileCoord[1], tileCoord[2]); -}; - - -/** - * Get a tile coord given a key. - * @param {string} key The tile coord key. - * @return {ol.TileCoord} The tile coord. - */ -ol.tilecoord.fromKey = function(key) { - return key.split('/').map(Number); -}; - - -/** - * @param {ol.TileCoord} tileCoord Tile coord. - * @return {number} Hash. - */ -ol.tilecoord.hash = function(tileCoord) { - return (tileCoord[1] << tileCoord[0]) + tileCoord[2]; -}; - - -/** - * @param {ol.TileCoord} tileCoord Tile coord. - * @return {string} Quad key. - */ -ol.tilecoord.quadKey = function(tileCoord) { - var z = tileCoord[0]; - var digits = new Array(z); - var mask = 1 << (z - 1); - var i, charCode; - for (i = 0; i < z; ++i) { - // 48 is charCode for 0 - '0'.charCodeAt(0) - charCode = 48; - if (tileCoord[1] & mask) { - charCode += 1; - } - if (tileCoord[2] & mask) { - charCode += 2; - } - digits[i] = String.fromCharCode(charCode); - mask >>= 1; - } - return digits.join(''); -}; - - -/** - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {!ol.tilegrid.TileGrid} tileGrid Tile grid. - * @return {boolean} Tile coordinate is within extent and zoom level range. - */ -ol.tilecoord.withinExtentAndZ = function(tileCoord, tileGrid) { - var z = tileCoord[0]; - var x = tileCoord[1]; - var y = tileCoord[2]; - - if (tileGrid.getMinZoom() > z || z > tileGrid.getMaxZoom()) { - return false; - } - var extent = tileGrid.getExtent(); - var tileRange; - if (!extent) { - tileRange = tileGrid.getFullTileRange(z); - } else { - tileRange = tileGrid.getTileRangeForExtentAndZ(extent, z); - } - if (!tileRange) { - return true; - } else { - return tileRange.containsXY(x, y); - } -}; - -goog.provide('ol.tilegrid.TileGrid'); - -goog.require('ol'); -goog.require('ol.asserts'); -goog.require('ol.TileRange'); -goog.require('ol.array'); -goog.require('ol.extent'); -goog.require('ol.math'); -goog.require('ol.size'); -goog.require('ol.tilecoord'); - - -/** - * @classdesc - * Base class for setting the grid pattern for sources accessing tiled-image - * servers. - * - * @constructor - * @param {olx.tilegrid.TileGridOptions} options Tile grid options. - * @struct - * @api - */ -ol.tilegrid.TileGrid = function(options) { - - /** - * @protected - * @type {number} - */ - this.minZoom = options.minZoom !== undefined ? options.minZoom : 0; - - /** - * @private - * @type {!Array.<number>} - */ - this.resolutions_ = options.resolutions; - ol.asserts.assert(ol.array.isSorted(this.resolutions_, function(a, b) { - return b - a; - }, true), 17); // `resolutions` must be sorted in descending order - - - // check if we've got a consistent zoom factor and origin - var zoomFactor; - if (!options.origins) { - for (var i = 0, ii = this.resolutions_.length - 1; i < ii; ++i) { - if (!zoomFactor) { - zoomFactor = this.resolutions_[i] / this.resolutions_[i + 1]; - } else { - if (this.resolutions_[i] / this.resolutions_[i + 1] !== zoomFactor) { - zoomFactor = undefined; - break; - } - } - } - } - - - /** - * @private - * @type {number|undefined} - */ - this.zoomFactor_ = zoomFactor; - - - /** - * @protected - * @type {number} - */ - this.maxZoom = this.resolutions_.length - 1; - - /** - * @private - * @type {ol.Coordinate} - */ - this.origin_ = options.origin !== undefined ? options.origin : null; - - /** - * @private - * @type {Array.<ol.Coordinate>} - */ - this.origins_ = null; - if (options.origins !== undefined) { - this.origins_ = options.origins; - ol.asserts.assert(this.origins_.length == this.resolutions_.length, - 20); // Number of `origins` and `resolutions` must be equal - } - - var extent = options.extent; - - if (extent !== undefined && - !this.origin_ && !this.origins_) { - this.origin_ = ol.extent.getTopLeft(extent); - } - - ol.asserts.assert( - (!this.origin_ && this.origins_) || (this.origin_ && !this.origins_), - 18); // Either `origin` or `origins` must be configured, never both - - /** - * @private - * @type {Array.<number|ol.Size>} - */ - this.tileSizes_ = null; - if (options.tileSizes !== undefined) { - this.tileSizes_ = options.tileSizes; - ol.asserts.assert(this.tileSizes_.length == this.resolutions_.length, - 19); // Number of `tileSizes` and `resolutions` must be equal - } - - /** - * @private - * @type {number|ol.Size} - */ - this.tileSize_ = options.tileSize !== undefined ? - options.tileSize : - !this.tileSizes_ ? ol.DEFAULT_TILE_SIZE : null; - ol.asserts.assert( - (!this.tileSize_ && this.tileSizes_) || - (this.tileSize_ && !this.tileSizes_), - 22); // Either `tileSize` or `tileSizes` must be configured, never both - - /** - * @private - * @type {ol.Extent} - */ - this.extent_ = extent !== undefined ? extent : null; - - - /** - * @private - * @type {Array.<ol.TileRange>} - */ - this.fullTileRanges_ = null; - - /** - * @private - * @type {ol.Size} - */ - this.tmpSize_ = [0, 0]; - - if (options.sizes !== undefined) { - this.fullTileRanges_ = options.sizes.map(function(size, z) { - var tileRange = new ol.TileRange( - Math.min(0, size[0]), Math.max(size[0] - 1, -1), - Math.min(0, size[1]), Math.max(size[1] - 1, -1)); - return tileRange; - }, this); - } else if (extent) { - this.calculateTileRanges_(extent); - } - -}; - - -/** - * @private - * @type {ol.TileCoord} - */ -ol.tilegrid.TileGrid.tmpTileCoord_ = [0, 0, 0]; - - -/** - * Call a function with each tile coordinate for a given extent and zoom level. - * - * @param {ol.Extent} extent Extent. - * @param {number} zoom Integer zoom level. - * @param {function(ol.TileCoord)} callback Function called with each tile coordinate. - * @api - */ -ol.tilegrid.TileGrid.prototype.forEachTileCoord = function(extent, zoom, callback) { - var tileRange = this.getTileRangeForExtentAndZ(extent, zoom); - for (var i = tileRange.minX, ii = tileRange.maxX; i <= ii; ++i) { - for (var j = tileRange.minY, jj = tileRange.maxY; j <= jj; ++j) { - callback([zoom, i, j]); - } - } -}; - - -/** - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {function(this: T, number, ol.TileRange): boolean} callback Callback. - * @param {T=} opt_this The object to use as `this` in `callback`. - * @param {ol.TileRange=} opt_tileRange Temporary ol.TileRange object. - * @param {ol.Extent=} opt_extent Temporary ol.Extent object. - * @return {boolean} Callback succeeded. - * @template T - */ -ol.tilegrid.TileGrid.prototype.forEachTileCoordParentTileRange = function(tileCoord, callback, opt_this, opt_tileRange, opt_extent) { - var tileRange, x, y; - var tileCoordExtent = null; - var z = tileCoord[0] - 1; - if (this.zoomFactor_ === 2) { - x = tileCoord[1]; - y = tileCoord[2]; - } else { - tileCoordExtent = this.getTileCoordExtent(tileCoord, opt_extent); - } - while (z >= this.minZoom) { - if (this.zoomFactor_ === 2) { - x = Math.floor(x / 2); - y = Math.floor(y / 2); - tileRange = ol.TileRange.createOrUpdate(x, x, y, y, opt_tileRange); - } else { - tileRange = this.getTileRangeForExtentAndZ(tileCoordExtent, z, opt_tileRange); - } - if (callback.call(opt_this, z, tileRange)) { - return true; - } - --z; - } - return false; -}; - - -/** - * Get the extent for this tile grid, if it was configured. - * @return {ol.Extent} Extent. - */ -ol.tilegrid.TileGrid.prototype.getExtent = function() { - return this.extent_; -}; - - -/** - * Get the maximum zoom level for the grid. - * @return {number} Max zoom. - * @api - */ -ol.tilegrid.TileGrid.prototype.getMaxZoom = function() { - return this.maxZoom; -}; - - -/** - * Get the minimum zoom level for the grid. - * @return {number} Min zoom. - * @api - */ -ol.tilegrid.TileGrid.prototype.getMinZoom = function() { - return this.minZoom; -}; - - -/** - * Get the origin for the grid at the given zoom level. - * @param {number} z Integer zoom level. - * @return {ol.Coordinate} Origin. - * @api - */ -ol.tilegrid.TileGrid.prototype.getOrigin = function(z) { - if (this.origin_) { - return this.origin_; - } else { - return this.origins_[z]; - } -}; - - -/** - * Get the resolution for the given zoom level. - * @param {number} z Integer zoom level. - * @return {number} Resolution. - * @api - */ -ol.tilegrid.TileGrid.prototype.getResolution = function(z) { - return this.resolutions_[z]; -}; - - -/** - * Get the list of resolutions for the tile grid. - * @return {Array.<number>} Resolutions. - * @api - */ -ol.tilegrid.TileGrid.prototype.getResolutions = function() { - return this.resolutions_; -}; - - -/** - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {ol.TileRange=} opt_tileRange Temporary ol.TileRange object. - * @param {ol.Extent=} opt_extent Temporary ol.Extent object. - * @return {ol.TileRange} Tile range. - */ -ol.tilegrid.TileGrid.prototype.getTileCoordChildTileRange = function(tileCoord, opt_tileRange, opt_extent) { - if (tileCoord[0] < this.maxZoom) { - if (this.zoomFactor_ === 2) { - var minX = tileCoord[1] * 2; - var minY = tileCoord[2] * 2; - return ol.TileRange.createOrUpdate(minX, minX + 1, minY, minY + 1, opt_tileRange); - } - var tileCoordExtent = this.getTileCoordExtent(tileCoord, opt_extent); - return this.getTileRangeForExtentAndZ( - tileCoordExtent, tileCoord[0] + 1, opt_tileRange); - } - return null; -}; - - -/** - * Get the extent for a tile range. - * @param {number} z Integer zoom level. - * @param {ol.TileRange} tileRange Tile range. - * @param {ol.Extent=} opt_extent Temporary ol.Extent object. - * @return {ol.Extent} Extent. - */ -ol.tilegrid.TileGrid.prototype.getTileRangeExtent = function(z, tileRange, opt_extent) { - var origin = this.getOrigin(z); - var resolution = this.getResolution(z); - var tileSize = ol.size.toSize(this.getTileSize(z), this.tmpSize_); - var minX = origin[0] + tileRange.minX * tileSize[0] * resolution; - var maxX = origin[0] + (tileRange.maxX + 1) * tileSize[0] * resolution; - var minY = origin[1] + tileRange.minY * tileSize[1] * resolution; - var maxY = origin[1] + (tileRange.maxY + 1) * tileSize[1] * resolution; - return ol.extent.createOrUpdate(minX, minY, maxX, maxY, opt_extent); -}; - - -/** - * Get a tile range for the given extent and integer zoom level. - * @param {ol.Extent} extent Extent. - * @param {number} z Integer zoom level. - * @param {ol.TileRange=} opt_tileRange Temporary tile range object. - * @return {ol.TileRange} Tile range. - */ -ol.tilegrid.TileGrid.prototype.getTileRangeForExtentAndZ = function(extent, z, opt_tileRange) { - var tileCoord = ol.tilegrid.TileGrid.tmpTileCoord_; - this.getTileCoordForXYAndZ_(extent[0], extent[1], z, false, tileCoord); - var minX = tileCoord[1]; - var minY = tileCoord[2]; - this.getTileCoordForXYAndZ_(extent[2], extent[3], z, true, tileCoord); - return ol.TileRange.createOrUpdate( - minX, tileCoord[1], minY, tileCoord[2], opt_tileRange); -}; - - -/** - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @return {ol.Coordinate} Tile center. - */ -ol.tilegrid.TileGrid.prototype.getTileCoordCenter = function(tileCoord) { - var origin = this.getOrigin(tileCoord[0]); - var resolution = this.getResolution(tileCoord[0]); - var tileSize = ol.size.toSize(this.getTileSize(tileCoord[0]), this.tmpSize_); - return [ - origin[0] + (tileCoord[1] + 0.5) * tileSize[0] * resolution, - origin[1] + (tileCoord[2] + 0.5) * tileSize[1] * resolution - ]; -}; - - -/** - * Get the extent of a tile coordinate. - * - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {ol.Extent=} opt_extent Temporary extent object. - * @return {ol.Extent} Extent. - * @api - */ -ol.tilegrid.TileGrid.prototype.getTileCoordExtent = function(tileCoord, opt_extent) { - var origin = this.getOrigin(tileCoord[0]); - var resolution = this.getResolution(tileCoord[0]); - var tileSize = ol.size.toSize(this.getTileSize(tileCoord[0]), this.tmpSize_); - var minX = origin[0] + tileCoord[1] * tileSize[0] * resolution; - var minY = origin[1] + tileCoord[2] * tileSize[1] * resolution; - var maxX = minX + tileSize[0] * resolution; - var maxY = minY + tileSize[1] * resolution; - return ol.extent.createOrUpdate(minX, minY, maxX, maxY, opt_extent); -}; - - -/** - * Get the tile coordinate for the given map coordinate and resolution. This - * method considers that coordinates that intersect tile boundaries should be - * assigned the higher tile coordinate. - * - * @param {ol.Coordinate} coordinate Coordinate. - * @param {number} resolution Resolution. - * @param {ol.TileCoord=} opt_tileCoord Destination ol.TileCoord object. - * @return {ol.TileCoord} Tile coordinate. - * @api - */ -ol.tilegrid.TileGrid.prototype.getTileCoordForCoordAndResolution = function(coordinate, resolution, opt_tileCoord) { - return this.getTileCoordForXYAndResolution_( - coordinate[0], coordinate[1], resolution, false, opt_tileCoord); -}; - - -/** - * Note that this method should not be called for resolutions that correspond - * to an integer zoom level. Instead call the `getTileCoordForXYAndZ_` method. - * @param {number} x X. - * @param {number} y Y. - * @param {number} resolution Resolution (for a non-integer zoom level). - * @param {boolean} reverseIntersectionPolicy Instead of letting edge - * intersections go to the higher tile coordinate, let edge intersections - * go to the lower tile coordinate. - * @param {ol.TileCoord=} opt_tileCoord Temporary ol.TileCoord object. - * @return {ol.TileCoord} Tile coordinate. - * @private - */ -ol.tilegrid.TileGrid.prototype.getTileCoordForXYAndResolution_ = function( - x, y, resolution, reverseIntersectionPolicy, opt_tileCoord) { - var z = this.getZForResolution(resolution); - var scale = resolution / this.getResolution(z); - var origin = this.getOrigin(z); - var tileSize = ol.size.toSize(this.getTileSize(z), this.tmpSize_); - - var adjustX = reverseIntersectionPolicy ? 0.5 : 0; - var adjustY = reverseIntersectionPolicy ? 0 : 0.5; - var xFromOrigin = Math.floor((x - origin[0]) / resolution + adjustX); - var yFromOrigin = Math.floor((y - origin[1]) / resolution + adjustY); - var tileCoordX = scale * xFromOrigin / tileSize[0]; - var tileCoordY = scale * yFromOrigin / tileSize[1]; - - if (reverseIntersectionPolicy) { - tileCoordX = Math.ceil(tileCoordX) - 1; - tileCoordY = Math.ceil(tileCoordY) - 1; - } else { - tileCoordX = Math.floor(tileCoordX); - tileCoordY = Math.floor(tileCoordY); - } - - return ol.tilecoord.createOrUpdate(z, tileCoordX, tileCoordY, opt_tileCoord); -}; - - -/** - * Although there is repetition between this method and `getTileCoordForXYAndResolution_`, - * they should have separate implementations. This method is for integer zoom - * levels. The other method should only be called for resolutions corresponding - * to non-integer zoom levels. - * @param {number} x Map x coordinate. - * @param {number} y Map y coordinate. - * @param {number} z Integer zoom level. - * @param {boolean} reverseIntersectionPolicy Instead of letting edge - * intersections go to the higher tile coordinate, let edge intersections - * go to the lower tile coordinate. - * @param {ol.TileCoord=} opt_tileCoord Temporary ol.TileCoord object. - * @return {ol.TileCoord} Tile coordinate. - * @private - */ -ol.tilegrid.TileGrid.prototype.getTileCoordForXYAndZ_ = function(x, y, z, reverseIntersectionPolicy, opt_tileCoord) { - var origin = this.getOrigin(z); - var resolution = this.getResolution(z); - var tileSize = ol.size.toSize(this.getTileSize(z), this.tmpSize_); - - var adjustX = reverseIntersectionPolicy ? 0.5 : 0; - var adjustY = reverseIntersectionPolicy ? 0 : 0.5; - var xFromOrigin = Math.floor((x - origin[0]) / resolution + adjustX); - var yFromOrigin = Math.floor((y - origin[1]) / resolution + adjustY); - var tileCoordX = xFromOrigin / tileSize[0]; - var tileCoordY = yFromOrigin / tileSize[1]; - - if (reverseIntersectionPolicy) { - tileCoordX = Math.ceil(tileCoordX) - 1; - tileCoordY = Math.ceil(tileCoordY) - 1; - } else { - tileCoordX = Math.floor(tileCoordX); - tileCoordY = Math.floor(tileCoordY); - } - - return ol.tilecoord.createOrUpdate(z, tileCoordX, tileCoordY, opt_tileCoord); -}; - - -/** - * Get a tile coordinate given a map coordinate and zoom level. - * @param {ol.Coordinate} coordinate Coordinate. - * @param {number} z Zoom level. - * @param {ol.TileCoord=} opt_tileCoord Destination ol.TileCoord object. - * @return {ol.TileCoord} Tile coordinate. - * @api - */ -ol.tilegrid.TileGrid.prototype.getTileCoordForCoordAndZ = function(coordinate, z, opt_tileCoord) { - return this.getTileCoordForXYAndZ_( - coordinate[0], coordinate[1], z, false, opt_tileCoord); -}; - - -/** - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @return {number} Tile resolution. - */ -ol.tilegrid.TileGrid.prototype.getTileCoordResolution = function(tileCoord) { - return this.resolutions_[tileCoord[0]]; -}; - - -/** - * Get the tile size for a zoom level. The type of the return value matches the - * `tileSize` or `tileSizes` that the tile grid was configured with. To always - * get an `ol.Size`, run the result through `ol.size.toSize()`. - * @param {number} z Z. - * @return {number|ol.Size} Tile size. - * @api - */ -ol.tilegrid.TileGrid.prototype.getTileSize = function(z) { - if (this.tileSize_) { - return this.tileSize_; - } else { - return this.tileSizes_[z]; - } -}; - - -/** - * @param {number} z Zoom level. - * @return {ol.TileRange} Extent tile range for the specified zoom level. - */ -ol.tilegrid.TileGrid.prototype.getFullTileRange = function(z) { - if (!this.fullTileRanges_) { - return null; - } else { - return this.fullTileRanges_[z]; - } -}; - - -/** - * @param {number} resolution Resolution. - * @param {number=} opt_direction If 0, the nearest resolution will be used. - * If 1, the nearest lower resolution will be used. If -1, the nearest - * higher resolution will be used. Default is 0. - * @return {number} Z. - * @api - */ -ol.tilegrid.TileGrid.prototype.getZForResolution = function( - resolution, opt_direction) { - var z = ol.array.linearFindNearest(this.resolutions_, resolution, - opt_direction || 0); - return ol.math.clamp(z, this.minZoom, this.maxZoom); -}; - - -/** - * @param {!ol.Extent} extent Extent for this tile grid. - * @private - */ -ol.tilegrid.TileGrid.prototype.calculateTileRanges_ = function(extent) { - var length = this.resolutions_.length; - var fullTileRanges = new Array(length); - for (var z = this.minZoom; z < length; ++z) { - fullTileRanges[z] = this.getTileRangeForExtentAndZ(extent, z); - } - this.fullTileRanges_ = fullTileRanges; -}; - -goog.provide('ol.tilegrid'); - -goog.require('ol'); -goog.require('ol.size'); -goog.require('ol.extent'); -goog.require('ol.extent.Corner'); -goog.require('ol.obj'); -goog.require('ol.proj'); -goog.require('ol.proj.Units'); -goog.require('ol.tilegrid.TileGrid'); - - -/** - * @param {ol.proj.Projection} projection Projection. - * @return {!ol.tilegrid.TileGrid} Default tile grid for the passed projection. - */ -ol.tilegrid.getForProjection = function(projection) { - var tileGrid = projection.getDefaultTileGrid(); - if (!tileGrid) { - tileGrid = ol.tilegrid.createForProjection(projection); - projection.setDefaultTileGrid(tileGrid); - } - return tileGrid; -}; - - -/** - * @param {ol.tilegrid.TileGrid} tileGrid Tile grid. - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {ol.proj.Projection} projection Projection. - * @return {ol.TileCoord} Tile coordinate. - */ -ol.tilegrid.wrapX = function(tileGrid, tileCoord, projection) { - var z = tileCoord[0]; - var center = tileGrid.getTileCoordCenter(tileCoord); - var projectionExtent = ol.tilegrid.extentFromProjection(projection); - if (!ol.extent.containsCoordinate(projectionExtent, center)) { - var worldWidth = ol.extent.getWidth(projectionExtent); - var worldsAway = Math.ceil((projectionExtent[0] - center[0]) / worldWidth); - center[0] += worldWidth * worldsAway; - return tileGrid.getTileCoordForCoordAndZ(center, z); - } else { - return tileCoord; - } -}; - - -/** - * @param {ol.Extent} extent Extent. - * @param {number=} opt_maxZoom Maximum zoom level (default is - * ol.DEFAULT_MAX_ZOOM). - * @param {number|ol.Size=} opt_tileSize Tile size (default uses - * ol.DEFAULT_TILE_SIZE). - * @param {ol.extent.Corner=} opt_corner Extent corner (default is - * ol.extent.Corner.TOP_LEFT). - * @return {!ol.tilegrid.TileGrid} TileGrid instance. - */ -ol.tilegrid.createForExtent = function(extent, opt_maxZoom, opt_tileSize, opt_corner) { - var corner = opt_corner !== undefined ? - opt_corner : ol.extent.Corner.TOP_LEFT; - - var resolutions = ol.tilegrid.resolutionsFromExtent( - extent, opt_maxZoom, opt_tileSize); - - return new ol.tilegrid.TileGrid({ - extent: extent, - origin: ol.extent.getCorner(extent, corner), - resolutions: resolutions, - tileSize: opt_tileSize - }); -}; - - -/** - * Creates a tile grid with a standard XYZ tiling scheme. - * @param {olx.tilegrid.XYZOptions=} opt_options Tile grid options. - * @return {!ol.tilegrid.TileGrid} Tile grid instance. - * @api - */ -ol.tilegrid.createXYZ = function(opt_options) { - var options = /** @type {olx.tilegrid.TileGridOptions} */ ({}); - ol.obj.assign(options, opt_options !== undefined ? - opt_options : /** @type {olx.tilegrid.XYZOptions} */ ({})); - if (options.extent === undefined) { - options.extent = ol.proj.get('EPSG:3857').getExtent(); - } - options.resolutions = ol.tilegrid.resolutionsFromExtent( - options.extent, options.maxZoom, options.tileSize); - delete options.maxZoom; - - return new ol.tilegrid.TileGrid(options); -}; - - -/** - * Create a resolutions array from an extent. A zoom factor of 2 is assumed. - * @param {ol.Extent} extent Extent. - * @param {number=} opt_maxZoom Maximum zoom level (default is - * ol.DEFAULT_MAX_ZOOM). - * @param {number|ol.Size=} opt_tileSize Tile size (default uses - * ol.DEFAULT_TILE_SIZE). - * @return {!Array.<number>} Resolutions array. - */ -ol.tilegrid.resolutionsFromExtent = function(extent, opt_maxZoom, opt_tileSize) { - var maxZoom = opt_maxZoom !== undefined ? - opt_maxZoom : ol.DEFAULT_MAX_ZOOM; - - var height = ol.extent.getHeight(extent); - var width = ol.extent.getWidth(extent); - - var tileSize = ol.size.toSize(opt_tileSize !== undefined ? - opt_tileSize : ol.DEFAULT_TILE_SIZE); - var maxResolution = Math.max( - width / tileSize[0], height / tileSize[1]); - - var length = maxZoom + 1; - var resolutions = new Array(length); - for (var z = 0; z < length; ++z) { - resolutions[z] = maxResolution / Math.pow(2, z); - } - return resolutions; -}; - - -/** - * @param {ol.ProjectionLike} projection Projection. - * @param {number=} opt_maxZoom Maximum zoom level (default is - * ol.DEFAULT_MAX_ZOOM). - * @param {number|ol.Size=} opt_tileSize Tile size (default uses - * ol.DEFAULT_TILE_SIZE). - * @param {ol.extent.Corner=} opt_corner Extent corner (default is - * ol.extent.Corner.BOTTOM_LEFT). - * @return {!ol.tilegrid.TileGrid} TileGrid instance. - */ -ol.tilegrid.createForProjection = function(projection, opt_maxZoom, opt_tileSize, opt_corner) { - var extent = ol.tilegrid.extentFromProjection(projection); - return ol.tilegrid.createForExtent( - extent, opt_maxZoom, opt_tileSize, opt_corner); -}; - - -/** - * Generate a tile grid extent from a projection. If the projection has an - * extent, it is used. If not, a global extent is assumed. - * @param {ol.ProjectionLike} projection Projection. - * @return {ol.Extent} Extent. - */ -ol.tilegrid.extentFromProjection = function(projection) { - projection = ol.proj.get(projection); - var extent = projection.getExtent(); - if (!extent) { - var half = 180 * ol.proj.METERS_PER_UNIT[ol.proj.Units.DEGREES] / - projection.getMetersPerUnit(); - extent = ol.extent.createOrUpdate(-half, -half, half, half); - } - return extent; -}; - -goog.provide('ol.Attribution'); - -goog.require('ol.TileRange'); -goog.require('ol.math'); -goog.require('ol.tilegrid'); - - -/** - * @classdesc - * An attribution for a layer source. - * - * Example: - * - * source: new ol.source.OSM({ - * attributions: [ - * new ol.Attribution({ - * html: 'All maps © ' + - * '<a href="https://www.opencyclemap.org/">OpenCycleMap</a>' - * }), - * ol.source.OSM.ATTRIBUTION - * ], - * .. - * - * @constructor - * @param {olx.AttributionOptions} options Attribution options. - * @struct - * @api - */ -ol.Attribution = function(options) { - - /** - * @private - * @type {string} - */ - this.html_ = options.html; - - /** - * @private - * @type {Object.<string, Array.<ol.TileRange>>} - */ - this.tileRanges_ = options.tileRanges ? options.tileRanges : null; - -}; - - -/** - * Get the attribution markup. - * @return {string} The attribution HTML. - * @api - */ -ol.Attribution.prototype.getHTML = function() { - return this.html_; -}; - - -/** - * @param {Object.<string, ol.TileRange>} tileRanges Tile ranges. - * @param {!ol.tilegrid.TileGrid} tileGrid Tile grid. - * @param {!ol.proj.Projection} projection Projection. - * @return {boolean} Intersects any tile range. - */ -ol.Attribution.prototype.intersectsAnyTileRange = function(tileRanges, tileGrid, projection) { - if (!this.tileRanges_) { - return true; - } - var i, ii, tileRange, zKey; - for (zKey in tileRanges) { - if (!(zKey in this.tileRanges_)) { - continue; - } - tileRange = tileRanges[zKey]; - var testTileRange; - for (i = 0, ii = this.tileRanges_[zKey].length; i < ii; ++i) { - testTileRange = this.tileRanges_[zKey][i]; - if (testTileRange.intersects(tileRange)) { - return true; - } - var extentTileRange = tileGrid.getTileRangeForExtentAndZ( - ol.tilegrid.extentFromProjection(projection), parseInt(zKey, 10)); - var width = extentTileRange.getWidth(); - if (tileRange.minX < extentTileRange.minX || - tileRange.maxX > extentTileRange.maxX) { - if (testTileRange.intersects(new ol.TileRange( - ol.math.modulo(tileRange.minX, width), - ol.math.modulo(tileRange.maxX, width), - tileRange.minY, tileRange.maxY))) { - return true; - } - if (tileRange.getWidth() > width && - testTileRange.intersects(extentTileRange)) { - return true; - } - } - } - } - return false; -}; - -goog.provide('ol.CollectionEventType'); - -/** - * @enum {string} - */ -ol.CollectionEventType = { - /** - * Triggered when an item is added to the collection. - * @event ol.Collection.Event#add - * @api - */ - ADD: 'add', - /** - * Triggered when an item is removed from the collection. - * @event ol.Collection.Event#remove - * @api - */ - REMOVE: 'remove' -}; - -goog.provide('ol.ObjectEventType'); - -/** - * @enum {string} - */ -ol.ObjectEventType = { - /** - * Triggered when a property is changed. - * @event ol.Object.Event#propertychange - * @api - */ - PROPERTYCHANGE: 'propertychange' -}; - -goog.provide('ol.events'); - -goog.require('ol.obj'); - - -/** - * @param {ol.EventsKey} listenerObj Listener object. - * @return {ol.EventsListenerFunctionType} Bound listener. - */ -ol.events.bindListener_ = function(listenerObj) { - var boundListener = function(evt) { - var listener = listenerObj.listener; - var bindTo = listenerObj.bindTo || listenerObj.target; - if (listenerObj.callOnce) { - ol.events.unlistenByKey(listenerObj); - } - return listener.call(bindTo, evt); - }; - listenerObj.boundListener = boundListener; - return boundListener; -}; - - -/** - * Finds the matching {@link ol.EventsKey} in the given listener - * array. - * - * @param {!Array<!ol.EventsKey>} listeners Array of listeners. - * @param {!Function} listener The listener function. - * @param {Object=} opt_this The `this` value inside the listener. - * @param {boolean=} opt_setDeleteIndex Set the deleteIndex on the matching - * listener, for {@link ol.events.unlistenByKey}. - * @return {ol.EventsKey|undefined} The matching listener object. - * @private - */ -ol.events.findListener_ = function(listeners, listener, opt_this, - opt_setDeleteIndex) { - var listenerObj; - for (var i = 0, ii = listeners.length; i < ii; ++i) { - listenerObj = listeners[i]; - if (listenerObj.listener === listener && - listenerObj.bindTo === opt_this) { - if (opt_setDeleteIndex) { - listenerObj.deleteIndex = i; - } - return listenerObj; - } - } - return undefined; -}; - - -/** - * @param {ol.EventTargetLike} target Target. - * @param {string} type Type. - * @return {Array.<ol.EventsKey>|undefined} Listeners. - */ -ol.events.getListeners = function(target, type) { - var listenerMap = target.ol_lm; - return listenerMap ? listenerMap[type] : undefined; -}; - - -/** - * Get the lookup of listeners. If one does not exist on the target, it is - * created. - * @param {ol.EventTargetLike} target Target. - * @return {!Object.<string, Array.<ol.EventsKey>>} Map of - * listeners by event type. - * @private - */ -ol.events.getListenerMap_ = function(target) { - var listenerMap = target.ol_lm; - if (!listenerMap) { - listenerMap = target.ol_lm = {}; - } - return listenerMap; -}; - - -/** - * Clean up all listener objects of the given type. All properties on the - * listener objects will be removed, and if no listeners remain in the listener - * map, it will be removed from the target. - * @param {ol.EventTargetLike} target Target. - * @param {string} type Type. - * @private - */ -ol.events.removeListeners_ = function(target, type) { - var listeners = ol.events.getListeners(target, type); - if (listeners) { - for (var i = 0, ii = listeners.length; i < ii; ++i) { - target.removeEventListener(type, listeners[i].boundListener); - ol.obj.clear(listeners[i]); - } - listeners.length = 0; - var listenerMap = target.ol_lm; - if (listenerMap) { - delete listenerMap[type]; - if (Object.keys(listenerMap).length === 0) { - delete target.ol_lm; - } - } - } -}; - - -/** - * Registers an event listener on an event target. Inspired by - * {@link https://google.github.io/closure-library/api/source/closure/goog/events/events.js.src.html} - * - * This function efficiently binds a `listener` to a `this` object, and returns - * a key for use with {@link ol.events.unlistenByKey}. - * - * @param {ol.EventTargetLike} target Event target. - * @param {string} type Event type. - * @param {ol.EventsListenerFunctionType} listener Listener. - * @param {Object=} opt_this Object referenced by the `this` keyword in the - * listener. Default is the `target`. - * @param {boolean=} opt_once If true, add the listener as one-off listener. - * @return {ol.EventsKey} Unique key for the listener. - */ -ol.events.listen = function(target, type, listener, opt_this, opt_once) { - var listenerMap = ol.events.getListenerMap_(target); - var listeners = listenerMap[type]; - if (!listeners) { - listeners = listenerMap[type] = []; - } - var listenerObj = ol.events.findListener_(listeners, listener, opt_this, - false); - if (listenerObj) { - if (!opt_once) { - // Turn one-off listener into a permanent one. - listenerObj.callOnce = false; - } - } else { - listenerObj = /** @type {ol.EventsKey} */ ({ - bindTo: opt_this, - callOnce: !!opt_once, - listener: listener, - target: target, - type: type - }); - target.addEventListener(type, ol.events.bindListener_(listenerObj)); - listeners.push(listenerObj); - } - - return listenerObj; -}; - - -/** - * Registers a one-off event listener on an event target. Inspired by - * {@link https://google.github.io/closure-library/api/source/closure/goog/events/events.js.src.html} - * - * This function efficiently binds a `listener` as self-unregistering listener - * to a `this` object, and returns a key for use with - * {@link ol.events.unlistenByKey} in case the listener needs to be unregistered - * before it is called. - * - * When {@link ol.events.listen} is called with the same arguments after this - * function, the self-unregistering listener will be turned into a permanent - * listener. - * - * @param {ol.EventTargetLike} target Event target. - * @param {string} type Event type. - * @param {ol.EventsListenerFunctionType} listener Listener. - * @param {Object=} opt_this Object referenced by the `this` keyword in the - * listener. Default is the `target`. - * @return {ol.EventsKey} Key for unlistenByKey. - */ -ol.events.listenOnce = function(target, type, listener, opt_this) { - return ol.events.listen(target, type, listener, opt_this, true); -}; - - -/** - * Unregisters an event listener on an event target. Inspired by - * {@link https://google.github.io/closure-library/api/source/closure/goog/events/events.js.src.html} - * - * To return a listener, this function needs to be called with the exact same - * arguments that were used for a previous {@link ol.events.listen} call. - * - * @param {ol.EventTargetLike} target Event target. - * @param {string} type Event type. - * @param {ol.EventsListenerFunctionType} listener Listener. - * @param {Object=} opt_this Object referenced by the `this` keyword in the - * listener. Default is the `target`. - */ -ol.events.unlisten = function(target, type, listener, opt_this) { - var listeners = ol.events.getListeners(target, type); - if (listeners) { - var listenerObj = ol.events.findListener_(listeners, listener, opt_this, - true); - if (listenerObj) { - ol.events.unlistenByKey(listenerObj); - } - } -}; - - -/** - * Unregisters event listeners on an event target. Inspired by - * {@link https://google.github.io/closure-library/api/source/closure/goog/events/events.js.src.html} - * - * The argument passed to this function is the key returned from - * {@link ol.events.listen} or {@link ol.events.listenOnce}. - * - * @param {ol.EventsKey} key The key. - */ -ol.events.unlistenByKey = function(key) { - if (key && key.target) { - key.target.removeEventListener(key.type, key.boundListener); - var listeners = ol.events.getListeners(key.target, key.type); - if (listeners) { - var i = 'deleteIndex' in key ? key.deleteIndex : listeners.indexOf(key); - if (i !== -1) { - listeners.splice(i, 1); - } - if (listeners.length === 0) { - ol.events.removeListeners_(key.target, key.type); - } - } - ol.obj.clear(key); - } -}; - - -/** - * Unregisters all event listeners on an event target. Inspired by - * {@link https://google.github.io/closure-library/api/source/closure/goog/events/events.js.src.html} - * - * @param {ol.EventTargetLike} target Target. - */ -ol.events.unlistenAll = function(target) { - var listenerMap = ol.events.getListenerMap_(target); - for (var type in listenerMap) { - ol.events.removeListeners_(target, type); - } -}; - -goog.provide('ol.Disposable'); - -goog.require('ol'); - -/** - * Objects that need to clean up after themselves. - * @constructor - */ -ol.Disposable = function() {}; - -/** - * The object has already been disposed. - * @type {boolean} - * @private - */ -ol.Disposable.prototype.disposed_ = false; - -/** - * Clean up. - */ -ol.Disposable.prototype.dispose = function() { - if (!this.disposed_) { - this.disposed_ = true; - this.disposeInternal(); - } -}; - -/** - * Extension point for disposable objects. - * @protected - */ -ol.Disposable.prototype.disposeInternal = ol.nullFunction; - -goog.provide('ol.events.Event'); - - -/** - * @classdesc - * Stripped down implementation of the W3C DOM Level 2 Event interface. - * @see {@link https://www.w3.org/TR/DOM-Level-2-Events/events.html#Events-interface} - * - * This implementation only provides `type` and `target` properties, and - * `stopPropagation` and `preventDefault` methods. It is meant as base class - * for higher level events defined in the library, and works with - * {@link ol.events.EventTarget}. - * - * @constructor - * @implements {oli.events.Event} - * @param {string} type Type. - */ -ol.events.Event = function(type) { - - /** - * @type {boolean} - */ - this.propagationStopped; - - /** - * The event type. - * @type {string} - * @api - */ - this.type = type; - - /** - * The event target. - * @type {Object} - * @api - */ - this.target = null; - -}; - - -/** - * Stop event propagation. - * @function - * @override - * @api - */ -ol.events.Event.prototype.preventDefault = - - /** - * Stop event propagation. - * @function - * @override - * @api - */ - ol.events.Event.prototype.stopPropagation = function() { - this.propagationStopped = true; - }; - - -/** - * @param {Event|ol.events.Event} evt Event - */ -ol.events.Event.stopPropagation = function(evt) { - evt.stopPropagation(); -}; - - -/** - * @param {Event|ol.events.Event} evt Event - */ -ol.events.Event.preventDefault = function(evt) { - evt.preventDefault(); -}; - -goog.provide('ol.events.EventTarget'); - -goog.require('ol'); -goog.require('ol.Disposable'); -goog.require('ol.events'); -goog.require('ol.events.Event'); - - -/** - * @classdesc - * A simplified implementation of the W3C DOM Level 2 EventTarget interface. - * @see {@link https://www.w3.org/TR/2000/REC-DOM-Level-2-Events-20001113/events.html#Events-EventTarget} - * - * There are two important simplifications compared to the specification: - * - * 1. The handling of `useCapture` in `addEventListener` and - * `removeEventListener`. There is no real capture model. - * 2. The handling of `stopPropagation` and `preventDefault` on `dispatchEvent`. - * There is no event target hierarchy. When a listener calls - * `stopPropagation` or `preventDefault` on an event object, it means that no - * more listeners after this one will be called. Same as when the listener - * returns false. - * - * @constructor - * @extends {ol.Disposable} - */ -ol.events.EventTarget = function() { - - ol.Disposable.call(this); - - /** - * @private - * @type {!Object.<string, number>} - */ - this.pendingRemovals_ = {}; - - /** - * @private - * @type {!Object.<string, number>} - */ - this.dispatching_ = {}; - - /** - * @private - * @type {!Object.<string, Array.<ol.EventsListenerFunctionType>>} - */ - this.listeners_ = {}; - -}; -ol.inherits(ol.events.EventTarget, ol.Disposable); - - -/** - * @param {string} type Type. - * @param {ol.EventsListenerFunctionType} listener Listener. - */ -ol.events.EventTarget.prototype.addEventListener = function(type, listener) { - var listeners = this.listeners_[type]; - if (!listeners) { - listeners = this.listeners_[type] = []; - } - if (listeners.indexOf(listener) === -1) { - listeners.push(listener); - } -}; - - -/** - * @param {{type: string, - * target: (EventTarget|ol.events.EventTarget|undefined)}|ol.events.Event| - * string} event Event or event type. - * @return {boolean|undefined} `false` if anyone called preventDefault on the - * event object or if any of the listeners returned false. - */ -ol.events.EventTarget.prototype.dispatchEvent = function(event) { - var evt = typeof event === 'string' ? new ol.events.Event(event) : event; - var type = evt.type; - evt.target = this; - var listeners = this.listeners_[type]; - var propagate; - if (listeners) { - if (!(type in this.dispatching_)) { - this.dispatching_[type] = 0; - this.pendingRemovals_[type] = 0; - } - ++this.dispatching_[type]; - for (var i = 0, ii = listeners.length; i < ii; ++i) { - if (listeners[i].call(this, evt) === false || evt.propagationStopped) { - propagate = false; - break; - } - } - --this.dispatching_[type]; - if (this.dispatching_[type] === 0) { - var pendingRemovals = this.pendingRemovals_[type]; - delete this.pendingRemovals_[type]; - while (pendingRemovals--) { - this.removeEventListener(type, ol.nullFunction); - } - delete this.dispatching_[type]; - } - return propagate; - } -}; - - -/** - * @inheritDoc - */ -ol.events.EventTarget.prototype.disposeInternal = function() { - ol.events.unlistenAll(this); -}; - - -/** - * Get the listeners for a specified event type. Listeners are returned in the - * order that they will be called in. - * - * @param {string} type Type. - * @return {Array.<ol.EventsListenerFunctionType>} Listeners. - */ -ol.events.EventTarget.prototype.getListeners = function(type) { - return this.listeners_[type]; -}; - - -/** - * @param {string=} opt_type Type. If not provided, - * `true` will be returned if this EventTarget has any listeners. - * @return {boolean} Has listeners. - */ -ol.events.EventTarget.prototype.hasListener = function(opt_type) { - return opt_type ? - opt_type in this.listeners_ : - Object.keys(this.listeners_).length > 0; -}; - - -/** - * @param {string} type Type. - * @param {ol.EventsListenerFunctionType} listener Listener. - */ -ol.events.EventTarget.prototype.removeEventListener = function(type, listener) { - var listeners = this.listeners_[type]; - if (listeners) { - var index = listeners.indexOf(listener); - if (type in this.pendingRemovals_) { - // make listener a no-op, and remove later in #dispatchEvent() - listeners[index] = ol.nullFunction; - ++this.pendingRemovals_[type]; - } else { - listeners.splice(index, 1); - if (listeners.length === 0) { - delete this.listeners_[type]; - } - } - } -}; - -goog.provide('ol.events.EventType'); - -/** - * @enum {string} - * @const - */ -ol.events.EventType = { - /** - * Generic change event. Triggered when the revision counter is increased. - * @event ol.events.Event#change - * @api - */ - CHANGE: 'change', - - CLICK: 'click', - DBLCLICK: 'dblclick', - DRAGENTER: 'dragenter', - DRAGOVER: 'dragover', - DROP: 'drop', - ERROR: 'error', - KEYDOWN: 'keydown', - KEYPRESS: 'keypress', - LOAD: 'load', - MOUSEDOWN: 'mousedown', - MOUSEMOVE: 'mousemove', - MOUSEOUT: 'mouseout', - MOUSEUP: 'mouseup', - MOUSEWHEEL: 'mousewheel', - MSPOINTERDOWN: 'MSPointerDown', - RESIZE: 'resize', - TOUCHSTART: 'touchstart', - TOUCHMOVE: 'touchmove', - TOUCHEND: 'touchend', - WHEEL: 'wheel' -}; - -goog.provide('ol.Observable'); - -goog.require('ol'); -goog.require('ol.events'); -goog.require('ol.events.EventTarget'); -goog.require('ol.events.EventType'); - - -/** - * @classdesc - * Abstract base class; normally only used for creating subclasses and not - * instantiated in apps. - * An event target providing convenient methods for listener registration - * and unregistration. A generic `change` event is always available through - * {@link ol.Observable#changed}. - * - * @constructor - * @extends {ol.events.EventTarget} - * @fires ol.events.Event - * @struct - * @api - */ -ol.Observable = function() { - - ol.events.EventTarget.call(this); - - /** - * @private - * @type {number} - */ - this.revision_ = 0; - -}; -ol.inherits(ol.Observable, ol.events.EventTarget); - - -/** - * Removes an event listener using the key returned by `on()` or `once()`. - * @param {ol.EventsKey|Array.<ol.EventsKey>} key The key returned by `on()` - * or `once()` (or an array of keys). - * @api - */ -ol.Observable.unByKey = function(key) { - if (Array.isArray(key)) { - for (var i = 0, ii = key.length; i < ii; ++i) { - ol.events.unlistenByKey(key[i]); - } - } else { - ol.events.unlistenByKey(/** @type {ol.EventsKey} */ (key)); - } -}; - - -/** - * Increases the revision counter and dispatches a 'change' event. - * @api - */ -ol.Observable.prototype.changed = function() { - ++this.revision_; - this.dispatchEvent(ol.events.EventType.CHANGE); -}; - - -/** - * Dispatches an event and calls all listeners listening for events - * of this type. The event parameter can either be a string or an - * Object with a `type` property. - * - * @param {{type: string, - * target: (EventTarget|ol.events.EventTarget|undefined)}|ol.events.Event| - * string} event Event object. - * @function - * @api - */ -ol.Observable.prototype.dispatchEvent; - - -/** - * Get the version number for this object. Each time the object is modified, - * its version number will be incremented. - * @return {number} Revision. - * @api - */ -ol.Observable.prototype.getRevision = function() { - return this.revision_; -}; - - -/** - * Listen for a certain type of event. - * @param {string|Array.<string>} type The event type or array of event types. - * @param {function(?): ?} listener The listener function. - * @param {Object=} opt_this The object to use as `this` in `listener`. - * @return {ol.EventsKey|Array.<ol.EventsKey>} Unique key for the listener. If - * called with an array of event types as the first argument, the return - * will be an array of keys. - * @api - */ -ol.Observable.prototype.on = function(type, listener, opt_this) { - if (Array.isArray(type)) { - var len = type.length; - var keys = new Array(len); - for (var i = 0; i < len; ++i) { - keys[i] = ol.events.listen(this, type[i], listener, opt_this); - } - return keys; - } else { - return ol.events.listen( - this, /** @type {string} */ (type), listener, opt_this); - } -}; - - -/** - * Listen once for a certain type of event. - * @param {string|Array.<string>} type The event type or array of event types. - * @param {function(?): ?} listener The listener function. - * @param {Object=} opt_this The object to use as `this` in `listener`. - * @return {ol.EventsKey|Array.<ol.EventsKey>} Unique key for the listener. If - * called with an array of event types as the first argument, the return - * will be an array of keys. - * @api - */ -ol.Observable.prototype.once = function(type, listener, opt_this) { - if (Array.isArray(type)) { - var len = type.length; - var keys = new Array(len); - for (var i = 0; i < len; ++i) { - keys[i] = ol.events.listenOnce(this, type[i], listener, opt_this); - } - return keys; - } else { - return ol.events.listenOnce( - this, /** @type {string} */ (type), listener, opt_this); - } -}; - - -/** - * Unlisten for a certain type of event. - * @param {string|Array.<string>} type The event type or array of event types. - * @param {function(?): ?} listener The listener function. - * @param {Object=} opt_this The object which was used as `this` by the - * `listener`. - * @api - */ -ol.Observable.prototype.un = function(type, listener, opt_this) { - if (Array.isArray(type)) { - for (var i = 0, ii = type.length; i < ii; ++i) { - ol.events.unlisten(this, type[i], listener, opt_this); - } - return; - } else { - ol.events.unlisten(this, /** @type {string} */ (type), listener, opt_this); - } -}; - -goog.provide('ol.Object'); - -goog.require('ol'); -goog.require('ol.ObjectEventType'); -goog.require('ol.Observable'); -goog.require('ol.events.Event'); -goog.require('ol.obj'); - - -/** - * @classdesc - * Abstract base class; normally only used for creating subclasses and not - * instantiated in apps. - * Most non-trivial classes inherit from this. - * - * This extends {@link ol.Observable} with observable properties, where each - * property is observable as well as the object as a whole. - * - * Classes that inherit from this have pre-defined properties, to which you can - * add your owns. The pre-defined properties are listed in this documentation as - * 'Observable Properties', and have their own accessors; for example, - * {@link ol.Map} has a `target` property, accessed with `getTarget()` and - * changed with `setTarget()`. Not all properties are however settable. There - * are also general-purpose accessors `get()` and `set()`. For example, - * `get('target')` is equivalent to `getTarget()`. - * - * The `set` accessors trigger a change event, and you can monitor this by - * registering a listener. For example, {@link ol.View} has a `center` - * property, so `view.on('change:center', function(evt) {...});` would call the - * function whenever the value of the center property changes. Within the - * function, `evt.target` would be the view, so `evt.target.getCenter()` would - * return the new center. - * - * You can add your own observable properties with - * `object.set('prop', 'value')`, and retrieve that with `object.get('prop')`. - * You can listen for changes on that property value with - * `object.on('change:prop', listener)`. You can get a list of all - * properties with {@link ol.Object#getProperties object.getProperties()}. - * - * Note that the observable properties are separate from standard JS properties. - * You can, for example, give your map object a title with - * `map.title='New title'` and with `map.set('title', 'Another title')`. The - * first will be a `hasOwnProperty`; the second will appear in - * `getProperties()`. Only the second is observable. - * - * Properties can be deleted by using the unset method. E.g. - * object.unset('foo'). - * - * @constructor - * @extends {ol.Observable} - * @param {Object.<string, *>=} opt_values An object with key-value pairs. - * @fires ol.Object.Event - * @api - */ -ol.Object = function(opt_values) { - ol.Observable.call(this); - - // Call ol.getUid to ensure that the order of objects' ids is the same as - // the order in which they were created. This also helps to ensure that - // object properties are always added in the same order, which helps many - // JavaScript engines generate faster code. - ol.getUid(this); - - /** - * @private - * @type {!Object.<string, *>} - */ - this.values_ = {}; - - if (opt_values !== undefined) { - this.setProperties(opt_values); - } -}; -ol.inherits(ol.Object, ol.Observable); - - -/** - * @private - * @type {Object.<string, string>} - */ -ol.Object.changeEventTypeCache_ = {}; - - -/** - * @param {string} key Key name. - * @return {string} Change name. - */ -ol.Object.getChangeEventType = function(key) { - return ol.Object.changeEventTypeCache_.hasOwnProperty(key) ? - ol.Object.changeEventTypeCache_[key] : - (ol.Object.changeEventTypeCache_[key] = 'change:' + key); -}; - - -/** - * Gets a value. - * @param {string} key Key name. - * @return {*} Value. - * @api - */ -ol.Object.prototype.get = function(key) { - var value; - if (this.values_.hasOwnProperty(key)) { - value = this.values_[key]; - } - return value; -}; - - -/** - * Get a list of object property names. - * @return {Array.<string>} List of property names. - * @api - */ -ol.Object.prototype.getKeys = function() { - return Object.keys(this.values_); -}; - - -/** - * Get an object of all property names and values. - * @return {Object.<string, *>} Object. - * @api - */ -ol.Object.prototype.getProperties = function() { - return ol.obj.assign({}, this.values_); -}; - - -/** - * @param {string} key Key name. - * @param {*} oldValue Old value. - */ -ol.Object.prototype.notify = function(key, oldValue) { - var eventType; - eventType = ol.Object.getChangeEventType(key); - this.dispatchEvent(new ol.Object.Event(eventType, key, oldValue)); - eventType = ol.ObjectEventType.PROPERTYCHANGE; - this.dispatchEvent(new ol.Object.Event(eventType, key, oldValue)); -}; - - -/** - * Sets a value. - * @param {string} key Key name. - * @param {*} value Value. - * @param {boolean=} opt_silent Update without triggering an event. - * @api - */ -ol.Object.prototype.set = function(key, value, opt_silent) { - if (opt_silent) { - this.values_[key] = value; - } else { - var oldValue = this.values_[key]; - this.values_[key] = value; - if (oldValue !== value) { - this.notify(key, oldValue); - } - } -}; - - -/** - * Sets a collection of key-value pairs. Note that this changes any existing - * properties and adds new ones (it does not remove any existing properties). - * @param {Object.<string, *>} values Values. - * @param {boolean=} opt_silent Update without triggering an event. - * @api - */ -ol.Object.prototype.setProperties = function(values, opt_silent) { - var key; - for (key in values) { - this.set(key, values[key], opt_silent); - } -}; - - -/** - * Unsets a property. - * @param {string} key Key name. - * @param {boolean=} opt_silent Unset without triggering an event. - * @api - */ -ol.Object.prototype.unset = function(key, opt_silent) { - if (key in this.values_) { - var oldValue = this.values_[key]; - delete this.values_[key]; - if (!opt_silent) { - this.notify(key, oldValue); - } - } -}; - - -/** - * @classdesc - * Events emitted by {@link ol.Object} instances are instances of this type. - * - * @param {string} type The event type. - * @param {string} key The property name. - * @param {*} oldValue The old value for `key`. - * @extends {ol.events.Event} - * @implements {oli.Object.Event} - * @constructor - */ -ol.Object.Event = function(type, key, oldValue) { - ol.events.Event.call(this, type); - - /** - * The name of the property whose value is changing. - * @type {string} - * @api - */ - this.key = key; - - /** - * The old value. To get the new value use `e.target.get(e.key)` where - * `e` is the event object. - * @type {*} - * @api - */ - this.oldValue = oldValue; - -}; -ol.inherits(ol.Object.Event, ol.events.Event); - -/** - * An implementation of Google Maps' MVCArray. - * @see https://developers.google.com/maps/documentation/javascript/reference - */ - -goog.provide('ol.Collection'); - -goog.require('ol'); -goog.require('ol.AssertionError'); -goog.require('ol.CollectionEventType'); -goog.require('ol.Object'); -goog.require('ol.events.Event'); - - -/** - * @classdesc - * An expanded version of standard JS Array, adding convenience methods for - * manipulation. Add and remove changes to the Collection trigger a Collection - * event. Note that this does not cover changes to the objects _within_ the - * Collection; they trigger events on the appropriate object, not on the - * Collection as a whole. - * - * @constructor - * @extends {ol.Object} - * @fires ol.Collection.Event - * @param {Array.<T>=} opt_array Array. - * @param {olx.CollectionOptions=} opt_options Collection options. - * @template T - * @api - */ -ol.Collection = function(opt_array, opt_options) { - - ol.Object.call(this); - - var options = opt_options || {}; - - /** - * @private - * @type {boolean} - */ - this.unique_ = !!options.unique; - - /** - * @private - * @type {!Array.<T>} - */ - this.array_ = opt_array ? opt_array : []; - - if (this.unique_) { - for (var i = 0, ii = this.array_.length; i < ii; ++i) { - this.assertUnique_(this.array_[i], i); - } - } - - this.updateLength_(); - -}; -ol.inherits(ol.Collection, ol.Object); - - -/** - * Remove all elements from the collection. - * @api - */ -ol.Collection.prototype.clear = function() { - while (this.getLength() > 0) { - this.pop(); - } -}; - - -/** - * Add elements to the collection. This pushes each item in the provided array - * to the end of the collection. - * @param {!Array.<T>} arr Array. - * @return {ol.Collection.<T>} This collection. - * @api - */ -ol.Collection.prototype.extend = function(arr) { - var i, ii; - for (i = 0, ii = arr.length; i < ii; ++i) { - this.push(arr[i]); - } - return this; -}; - - -/** - * Iterate over each element, calling the provided callback. - * @param {function(this: S, T, number, Array.<T>): *} f The function to call - * for every element. This function takes 3 arguments (the element, the - * index and the array). The return value is ignored. - * @param {S=} opt_this The object to use as `this` in `f`. - * @template S - * @api - */ -ol.Collection.prototype.forEach = function(f, opt_this) { - var fn = (opt_this) ? f.bind(opt_this) : f; - var array = this.array_; - for (var i = 0, ii = array.length; i < ii; ++i) { - fn(array[i], i, array); - } -}; - - -/** - * Get a reference to the underlying Array object. Warning: if the array - * is mutated, no events will be dispatched by the collection, and the - * collection's "length" property won't be in sync with the actual length - * of the array. - * @return {!Array.<T>} Array. - * @api - */ -ol.Collection.prototype.getArray = function() { - return this.array_; -}; - - -/** - * Get the element at the provided index. - * @param {number} index Index. - * @return {T} Element. - * @api - */ -ol.Collection.prototype.item = function(index) { - return this.array_[index]; -}; - - -/** - * Get the length of this collection. - * @return {number} The length of the array. - * @observable - * @api - */ -ol.Collection.prototype.getLength = function() { - return /** @type {number} */ (this.get(ol.Collection.Property_.LENGTH)); -}; - - -/** - * Insert an element at the provided index. - * @param {number} index Index. - * @param {T} elem Element. - * @api - */ -ol.Collection.prototype.insertAt = function(index, elem) { - if (this.unique_) { - this.assertUnique_(elem); - } - this.array_.splice(index, 0, elem); - this.updateLength_(); - this.dispatchEvent( - new ol.Collection.Event(ol.CollectionEventType.ADD, elem)); -}; - - -/** - * Remove the last element of the collection and return it. - * Return `undefined` if the collection is empty. - * @return {T|undefined} Element. - * @api - */ -ol.Collection.prototype.pop = function() { - return this.removeAt(this.getLength() - 1); -}; - - -/** - * Insert the provided element at the end of the collection. - * @param {T} elem Element. - * @return {number} New length of the collection. - * @api - */ -ol.Collection.prototype.push = function(elem) { - if (this.unique_) { - this.assertUnique_(elem); - } - var n = this.getLength(); - this.insertAt(n, elem); - return this.getLength(); -}; - - -/** - * Remove the first occurrence of an element from the collection. - * @param {T} elem Element. - * @return {T|undefined} The removed element or undefined if none found. - * @api - */ -ol.Collection.prototype.remove = function(elem) { - var arr = this.array_; - var i, ii; - for (i = 0, ii = arr.length; i < ii; ++i) { - if (arr[i] === elem) { - return this.removeAt(i); - } - } - return undefined; -}; - - -/** - * Remove the element at the provided index and return it. - * Return `undefined` if the collection does not contain this index. - * @param {number} index Index. - * @return {T|undefined} Value. - * @api - */ -ol.Collection.prototype.removeAt = function(index) { - var prev = this.array_[index]; - this.array_.splice(index, 1); - this.updateLength_(); - this.dispatchEvent( - new ol.Collection.Event(ol.CollectionEventType.REMOVE, prev)); - return prev; -}; - - -/** - * Set the element at the provided index. - * @param {number} index Index. - * @param {T} elem Element. - * @api - */ -ol.Collection.prototype.setAt = function(index, elem) { - var n = this.getLength(); - if (index < n) { - if (this.unique_) { - this.assertUnique_(elem, index); - } - var prev = this.array_[index]; - this.array_[index] = elem; - this.dispatchEvent( - new ol.Collection.Event(ol.CollectionEventType.REMOVE, prev)); - this.dispatchEvent( - new ol.Collection.Event(ol.CollectionEventType.ADD, elem)); - } else { - var j; - for (j = n; j < index; ++j) { - this.insertAt(j, undefined); - } - this.insertAt(index, elem); - } -}; - - -/** - * @private - */ -ol.Collection.prototype.updateLength_ = function() { - this.set(ol.Collection.Property_.LENGTH, this.array_.length); -}; - - -/** - * @private - * @param {T} elem Element. - * @param {number=} opt_except Optional index to ignore. - */ -ol.Collection.prototype.assertUnique_ = function(elem, opt_except) { - for (var i = 0, ii = this.array_.length; i < ii; ++i) { - if (this.array_[i] === elem && i !== opt_except) { - throw new ol.AssertionError(58); - } - } -}; - - -/** - * @enum {string} - * @private - */ -ol.Collection.Property_ = { - LENGTH: 'length' -}; - - -/** - * @classdesc - * Events emitted by {@link ol.Collection} instances are instances of this - * type. - * - * @constructor - * @extends {ol.events.Event} - * @implements {oli.Collection.Event} - * @param {ol.CollectionEventType} type Type. - * @param {*=} opt_element Element. - */ -ol.Collection.Event = function(type, opt_element) { - - ol.events.Event.call(this, type); - - /** - * The element that is added to or removed from the collection. - * @type {*} - * @api - */ - this.element = opt_element; - -}; -ol.inherits(ol.Collection.Event, ol.events.Event); - -goog.provide('ol.MapEvent'); - -goog.require('ol'); -goog.require('ol.events.Event'); - - -/** - * @classdesc - * Events emitted as map events are instances of this type. - * See {@link ol.Map} for which events trigger a map event. - * - * @constructor - * @extends {ol.events.Event} - * @implements {oli.MapEvent} - * @param {string} type Event type. - * @param {ol.PluggableMap} map Map. - * @param {?olx.FrameState=} opt_frameState Frame state. - */ -ol.MapEvent = function(type, map, opt_frameState) { - - ol.events.Event.call(this, type); - - /** - * The map where the event occurred. - * @type {ol.PluggableMap} - * @api - */ - this.map = map; - - /** - * The frame state at the time of the event. - * @type {?olx.FrameState} - * @api - */ - this.frameState = opt_frameState !== undefined ? opt_frameState : null; - -}; -ol.inherits(ol.MapEvent, ol.events.Event); - -goog.provide('ol.MapBrowserEvent'); - -goog.require('ol'); -goog.require('ol.MapEvent'); - - -/** - * @classdesc - * Events emitted as map browser events are instances of this type. - * See {@link ol.Map} for which events trigger a map browser event. - * - * @constructor - * @extends {ol.MapEvent} - * @implements {oli.MapBrowserEvent} - * @param {string} type Event type. - * @param {ol.PluggableMap} map Map. - * @param {Event} browserEvent Browser event. - * @param {boolean=} opt_dragging Is the map currently being dragged? - * @param {?olx.FrameState=} opt_frameState Frame state. - */ -ol.MapBrowserEvent = function(type, map, browserEvent, opt_dragging, - opt_frameState) { - - ol.MapEvent.call(this, type, map, opt_frameState); - - /** - * The original browser event. - * @const - * @type {Event} - * @api - */ - this.originalEvent = browserEvent; - - /** - * The map pixel relative to the viewport corresponding to the original browser event. - * @type {ol.Pixel} - * @api - */ - this.pixel = map.getEventPixel(browserEvent); - - /** - * The coordinate in view projection corresponding to the original browser event. - * @type {ol.Coordinate} - * @api - */ - this.coordinate = map.getCoordinateFromPixel(this.pixel); - - /** - * Indicates if the map is currently being dragged. Only set for - * `POINTERDRAG` and `POINTERMOVE` events. Default is `false`. - * - * @type {boolean} - * @api - */ - this.dragging = opt_dragging !== undefined ? opt_dragging : false; - -}; -ol.inherits(ol.MapBrowserEvent, ol.MapEvent); - - -/** - * Prevents the default browser action. - * @see https://developer.mozilla.org/en-US/docs/Web/API/event.preventDefault - * @override - * @api - */ -ol.MapBrowserEvent.prototype.preventDefault = function() { - ol.MapEvent.prototype.preventDefault.call(this); - this.originalEvent.preventDefault(); -}; - - -/** - * Prevents further propagation of the current event. - * @see https://developer.mozilla.org/en-US/docs/Web/API/event.stopPropagation - * @override - * @api - */ -ol.MapBrowserEvent.prototype.stopPropagation = function() { - ol.MapEvent.prototype.stopPropagation.call(this); - this.originalEvent.stopPropagation(); -}; - -goog.provide('ol.webgl'); - -/** - * Constants taken from goog.webgl - */ - - -/** - * @const - * @type {number} - */ -ol.webgl.ONE = 1; - - -/** - * @const - * @type {number} - */ -ol.webgl.SRC_ALPHA = 0x0302; - - -/** - * @const - * @type {number} - */ -ol.webgl.COLOR_ATTACHMENT0 = 0x8CE0; - - -/** - * @const - * @type {number} - */ -ol.webgl.COLOR_BUFFER_BIT = 0x00004000; - - -/** - * @const - * @type {number} - */ -ol.webgl.TRIANGLES = 0x0004; - - -/** - * @const - * @type {number} - */ -ol.webgl.TRIANGLE_STRIP = 0x0005; - - -/** - * @const - * @type {number} - */ -ol.webgl.ONE_MINUS_SRC_ALPHA = 0x0303; - - -/** - * @const - * @type {number} - */ -ol.webgl.ARRAY_BUFFER = 0x8892; - - -/** - * @const - * @type {number} - */ -ol.webgl.ELEMENT_ARRAY_BUFFER = 0x8893; - - -/** - * @const - * @type {number} - */ -ol.webgl.STREAM_DRAW = 0x88E0; - - -/** - * @const - * @type {number} - */ -ol.webgl.STATIC_DRAW = 0x88E4; - - -/** - * @const - * @type {number} - */ -ol.webgl.DYNAMIC_DRAW = 0x88E8; - - -/** - * @const - * @type {number} - */ -ol.webgl.CULL_FACE = 0x0B44; - - -/** - * @const - * @type {number} - */ -ol.webgl.BLEND = 0x0BE2; - - -/** - * @const - * @type {number} - */ -ol.webgl.STENCIL_TEST = 0x0B90; - - -/** - * @const - * @type {number} - */ -ol.webgl.DEPTH_TEST = 0x0B71; - - -/** - * @const - * @type {number} - */ -ol.webgl.SCISSOR_TEST = 0x0C11; - - -/** - * @const - * @type {number} - */ -ol.webgl.UNSIGNED_BYTE = 0x1401; - - -/** - * @const - * @type {number} - */ -ol.webgl.UNSIGNED_SHORT = 0x1403; - - -/** - * @const - * @type {number} - */ -ol.webgl.UNSIGNED_INT = 0x1405; - - -/** - * @const - * @type {number} - */ -ol.webgl.FLOAT = 0x1406; - - -/** - * @const - * @type {number} - */ -ol.webgl.RGBA = 0x1908; - - -/** - * @const - * @type {number} - */ -ol.webgl.FRAGMENT_SHADER = 0x8B30; - - -/** - * @const - * @type {number} - */ -ol.webgl.VERTEX_SHADER = 0x8B31; - - -/** - * @const - * @type {number} - */ -ol.webgl.LINK_STATUS = 0x8B82; - - -/** - * @const - * @type {number} - */ -ol.webgl.LINEAR = 0x2601; - - -/** - * @const - * @type {number} - */ -ol.webgl.TEXTURE_MAG_FILTER = 0x2800; - - -/** - * @const - * @type {number} - */ -ol.webgl.TEXTURE_MIN_FILTER = 0x2801; - - -/** - * @const - * @type {number} - */ -ol.webgl.TEXTURE_WRAP_S = 0x2802; - - -/** - * @const - * @type {number} - */ -ol.webgl.TEXTURE_WRAP_T = 0x2803; - - -/** - * @const - * @type {number} - */ -ol.webgl.TEXTURE_2D = 0x0DE1; - - -/** - * @const - * @type {number} - */ -ol.webgl.TEXTURE0 = 0x84C0; - - -/** - * @const - * @type {number} - */ -ol.webgl.CLAMP_TO_EDGE = 0x812F; - - -/** - * @const - * @type {number} - */ -ol.webgl.COMPILE_STATUS = 0x8B81; - - -/** - * @const - * @type {number} - */ -ol.webgl.FRAMEBUFFER = 0x8D40; - - -/** end of goog.webgl constants - */ - - -/** - * @const - * @private - * @type {Array.<string>} - */ -ol.webgl.CONTEXT_IDS_ = [ - 'experimental-webgl', - 'webgl', - 'webkit-3d', - 'moz-webgl' -]; - - -/** - * @param {HTMLCanvasElement} canvas Canvas. - * @param {Object=} opt_attributes Attributes. - * @return {WebGLRenderingContext} WebGL rendering context. - */ -ol.webgl.getContext = function(canvas, opt_attributes) { - var context, i, ii = ol.webgl.CONTEXT_IDS_.length; - for (i = 0; i < ii; ++i) { - try { - context = canvas.getContext(ol.webgl.CONTEXT_IDS_[i], opt_attributes); - if (context) { - return /** @type {!WebGLRenderingContext} */ (context); - } - } catch (e) { - // pass - } - } - return null; -}; - -goog.provide('ol.has'); - -goog.require('ol'); -goog.require('ol.webgl'); - -var ua = typeof navigator !== 'undefined' ? - navigator.userAgent.toLowerCase() : ''; - -/** - * User agent string says we are dealing with Firefox as browser. - * @type {boolean} - */ -ol.has.FIREFOX = ua.indexOf('firefox') !== -1; - -/** - * User agent string says we are dealing with Safari as browser. - * @type {boolean} - */ -ol.has.SAFARI = ua.indexOf('safari') !== -1 && ua.indexOf('chrom') == -1; - -/** - * User agent string says we are dealing with a WebKit engine. - * @type {boolean} - */ -ol.has.WEBKIT = ua.indexOf('webkit') !== -1 && ua.indexOf('edge') == -1; - -/** - * User agent string says we are dealing with a Mac as platform. - * @type {boolean} - */ -ol.has.MAC = ua.indexOf('macintosh') !== -1; - - -/** - * The ratio between physical pixels and device-independent pixels - * (dips) on the device (`window.devicePixelRatio`). - * @const - * @type {number} - * @api - */ -ol.has.DEVICE_PIXEL_RATIO = window.devicePixelRatio || 1; - - -/** - * True if the browser's Canvas implementation implements {get,set}LineDash. - * @type {boolean} - */ -ol.has.CANVAS_LINE_DASH = false; - - -/** - * True if both the library and browser support Canvas. Always `false` - * if `ol.ENABLE_CANVAS` is set to `false` at compile time. - * @const - * @type {boolean} - * @api - */ -ol.has.CANVAS = ol.ENABLE_CANVAS && ( - /** - * @return {boolean} Canvas supported. - */ - function() { - if (!('HTMLCanvasElement' in window)) { - return false; - } - try { - var context = document.createElement('CANVAS').getContext('2d'); - if (!context) { - return false; - } else { - if (context.setLineDash !== undefined) { - ol.has.CANVAS_LINE_DASH = true; - } - return true; - } - } catch (e) { - return false; - } - })(); - - -/** - * Indicates if DeviceOrientation is supported in the user's browser. - * @const - * @type {boolean} - * @api - */ -ol.has.DEVICE_ORIENTATION = 'DeviceOrientationEvent' in window; - - -/** - * Is HTML5 geolocation supported in the current browser? - * @const - * @type {boolean} - * @api - */ -ol.has.GEOLOCATION = 'geolocation' in navigator; - - -/** - * True if browser supports touch events. - * @const - * @type {boolean} - * @api - */ -ol.has.TOUCH = ol.ASSUME_TOUCH || 'ontouchstart' in window; - - -/** - * True if browser supports pointer events. - * @const - * @type {boolean} - */ -ol.has.POINTER = 'PointerEvent' in window; - - -/** - * True if browser supports ms pointer events (IE 10). - * @const - * @type {boolean} - */ -ol.has.MSPOINTER = !!(navigator.msPointerEnabled); - - -/** - * True if both OpenLayers and browser support WebGL. Always `false` - * if `ol.ENABLE_WEBGL` is set to `false` at compile time. - * @const - * @type {boolean} - * @api - */ -ol.has.WEBGL; - - -(function() { - if (ol.ENABLE_WEBGL) { - var hasWebGL = false; - var textureSize; - var /** @type {Array.<string>} */ extensions = []; - - if ('WebGLRenderingContext' in window) { - try { - var canvas = /** @type {HTMLCanvasElement} */ - (document.createElement('CANVAS')); - var gl = ol.webgl.getContext(canvas, { - failIfMajorPerformanceCaveat: true - }); - if (gl) { - hasWebGL = true; - textureSize = /** @type {number} */ - (gl.getParameter(gl.MAX_TEXTURE_SIZE)); - extensions = gl.getSupportedExtensions(); - } - } catch (e) { - // pass - } - } - ol.has.WEBGL = hasWebGL; - ol.WEBGL_EXTENSIONS = extensions; - ol.WEBGL_MAX_TEXTURE_SIZE = textureSize; - } -})(); - -goog.provide('ol.MapBrowserEventType'); - -goog.require('ol.events.EventType'); - - -/** - * Constants for event names. - * @enum {string} - */ -ol.MapBrowserEventType = { - - /** - * A true single click with no dragging and no double click. Note that this - * event is delayed by 250 ms to ensure that it is not a double click. - * @event ol.MapBrowserEvent#singleclick - * @api - */ - SINGLECLICK: 'singleclick', - - /** - * A click with no dragging. A double click will fire two of this. - * @event ol.MapBrowserEvent#click - * @api - */ - CLICK: ol.events.EventType.CLICK, - - /** - * A true double click, with no dragging. - * @event ol.MapBrowserEvent#dblclick - * @api - */ - DBLCLICK: ol.events.EventType.DBLCLICK, - - /** - * Triggered when a pointer is dragged. - * @event ol.MapBrowserEvent#pointerdrag - * @api - */ - POINTERDRAG: 'pointerdrag', - - /** - * Triggered when a pointer is moved. Note that on touch devices this is - * triggered when the map is panned, so is not the same as mousemove. - * @event ol.MapBrowserEvent#pointermove - * @api - */ - POINTERMOVE: 'pointermove', - - POINTERDOWN: 'pointerdown', - POINTERUP: 'pointerup', - POINTEROVER: 'pointerover', - POINTEROUT: 'pointerout', - POINTERENTER: 'pointerenter', - POINTERLEAVE: 'pointerleave', - POINTERCANCEL: 'pointercancel' -}; - -goog.provide('ol.MapBrowserPointerEvent'); - -goog.require('ol'); -goog.require('ol.MapBrowserEvent'); - - -/** - * @constructor - * @extends {ol.MapBrowserEvent} - * @param {string} type Event type. - * @param {ol.PluggableMap} map Map. - * @param {ol.pointer.PointerEvent} pointerEvent Pointer event. - * @param {boolean=} opt_dragging Is the map currently being dragged? - * @param {?olx.FrameState=} opt_frameState Frame state. - */ -ol.MapBrowserPointerEvent = function(type, map, pointerEvent, opt_dragging, - opt_frameState) { - - ol.MapBrowserEvent.call(this, type, map, pointerEvent.originalEvent, opt_dragging, - opt_frameState); - - /** - * @const - * @type {ol.pointer.PointerEvent} - */ - this.pointerEvent = pointerEvent; - -}; -ol.inherits(ol.MapBrowserPointerEvent, ol.MapBrowserEvent); - -goog.provide('ol.pointer.EventType'); - - -/** - * Constants for event names. - * @enum {string} - */ -ol.pointer.EventType = { - POINTERMOVE: 'pointermove', - POINTERDOWN: 'pointerdown', - POINTERUP: 'pointerup', - POINTEROVER: 'pointerover', - POINTEROUT: 'pointerout', - POINTERENTER: 'pointerenter', - POINTERLEAVE: 'pointerleave', - POINTERCANCEL: 'pointercancel' -}; - -goog.provide('ol.pointer.EventSource'); - - -/** - * @param {ol.pointer.PointerEventHandler} dispatcher Event handler. - * @param {!Object.<string, function(Event)>} mapping Event - * mapping. - * @constructor - */ -ol.pointer.EventSource = function(dispatcher, mapping) { - /** - * @type {ol.pointer.PointerEventHandler} - */ - this.dispatcher = dispatcher; - - /** - * @private - * @const - * @type {!Object.<string, function(Event)>} - */ - this.mapping_ = mapping; -}; - - -/** - * List of events supported by this source. - * @return {Array.<string>} Event names - */ -ol.pointer.EventSource.prototype.getEvents = function() { - return Object.keys(this.mapping_); -}; - - -/** - * Returns the handler that should handle a given event type. - * @param {string} eventType The event type. - * @return {function(Event)} Handler - */ -ol.pointer.EventSource.prototype.getHandlerForEvent = function(eventType) { - return this.mapping_[eventType]; -}; - -// Based on https://github.com/Polymer/PointerEvents - -// Copyright (c) 2013 The Polymer Authors. All rights reserved. -// -// Redistribution and use in source and binary forms, with or without -// modification, are permitted provided that the following conditions are -// met: -// -// * Redistributions of source code must retain the above copyright -// notice, this list of conditions and the following disclaimer. -// * Redistributions in binary form must reproduce the above -// copyright notice, this list of conditions and the following disclaimer -// in the documentation and/or other materials provided with the -// distribution. -// * Neither the name of Google Inc. nor the names of its -// contributors may be used to endorse or promote products derived from -// this software without specific prior written permission. -// -// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT -// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, -// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT -// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, -// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY -// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE -// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - -goog.provide('ol.pointer.MouseSource'); - -goog.require('ol'); -goog.require('ol.pointer.EventSource'); - - -/** - * @param {ol.pointer.PointerEventHandler} dispatcher Event handler. - * @constructor - * @extends {ol.pointer.EventSource} - */ -ol.pointer.MouseSource = function(dispatcher) { - var mapping = { - 'mousedown': this.mousedown, - 'mousemove': this.mousemove, - 'mouseup': this.mouseup, - 'mouseover': this.mouseover, - 'mouseout': this.mouseout - }; - ol.pointer.EventSource.call(this, dispatcher, mapping); - - /** - * @const - * @type {!Object.<string, Event|Object>} - */ - this.pointerMap = dispatcher.pointerMap; - - /** - * @const - * @type {Array.<ol.Pixel>} - */ - this.lastTouches = []; -}; -ol.inherits(ol.pointer.MouseSource, ol.pointer.EventSource); - - -/** - * @const - * @type {number} - */ -ol.pointer.MouseSource.POINTER_ID = 1; - - -/** - * @const - * @type {string} - */ -ol.pointer.MouseSource.POINTER_TYPE = 'mouse'; - - -/** - * Radius around touchend that swallows mouse events. - * - * @const - * @type {number} - */ -ol.pointer.MouseSource.DEDUP_DIST = 25; - - -/** - * Detect if a mouse event was simulated from a touch by - * checking if previously there was a touch event at the - * same position. - * - * FIXME - Known problem with the native Android browser on - * Samsung GT-I9100 (Android 4.1.2): - * In case the page is scrolled, this function does not work - * correctly when a canvas is used (WebGL or canvas renderer). - * Mouse listeners on canvas elements (for this browser), create - * two mouse events: One 'good' and one 'bad' one (on other browsers or - * when a div is used, there is only one event). For the 'bad' one, - * clientX/clientY and also pageX/pageY are wrong when the page - * is scrolled. Because of that, this function can not detect if - * the events were simulated from a touch event. As result, a - * pointer event at a wrong position is dispatched, which confuses - * the map interactions. - * It is unclear, how one can get the correct position for the event - * or detect that the positions are invalid. - * - * @private - * @param {Event} inEvent The in event. - * @return {boolean} True, if the event was generated by a touch. - */ -ol.pointer.MouseSource.prototype.isEventSimulatedFromTouch_ = function(inEvent) { - var lts = this.lastTouches; - var x = inEvent.clientX, y = inEvent.clientY; - for (var i = 0, l = lts.length, t; i < l && (t = lts[i]); i++) { - // simulated mouse events will be swallowed near a primary touchend - var dx = Math.abs(x - t[0]), dy = Math.abs(y - t[1]); - if (dx <= ol.pointer.MouseSource.DEDUP_DIST && - dy <= ol.pointer.MouseSource.DEDUP_DIST) { - return true; - } - } - return false; -}; - - -/** - * Creates a copy of the original event that will be used - * for the fake pointer event. - * - * @param {Event} inEvent The in event. - * @param {ol.pointer.PointerEventHandler} dispatcher Event handler. - * @return {Object} The copied event. - */ -ol.pointer.MouseSource.prepareEvent = function(inEvent, dispatcher) { - var e = dispatcher.cloneEvent(inEvent, inEvent); - - // forward mouse preventDefault - var pd = e.preventDefault; - e.preventDefault = function() { - inEvent.preventDefault(); - pd(); - }; - - e.pointerId = ol.pointer.MouseSource.POINTER_ID; - e.isPrimary = true; - e.pointerType = ol.pointer.MouseSource.POINTER_TYPE; - - return e; -}; - - -/** - * Handler for `mousedown`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.MouseSource.prototype.mousedown = function(inEvent) { - if (!this.isEventSimulatedFromTouch_(inEvent)) { - // TODO(dfreedman) workaround for some elements not sending mouseup - // http://crbug/149091 - if (ol.pointer.MouseSource.POINTER_ID.toString() in this.pointerMap) { - this.cancel(inEvent); - } - var e = ol.pointer.MouseSource.prepareEvent(inEvent, this.dispatcher); - this.pointerMap[ol.pointer.MouseSource.POINTER_ID.toString()] = inEvent; - this.dispatcher.down(e, inEvent); - } -}; - - -/** - * Handler for `mousemove`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.MouseSource.prototype.mousemove = function(inEvent) { - if (!this.isEventSimulatedFromTouch_(inEvent)) { - var e = ol.pointer.MouseSource.prepareEvent(inEvent, this.dispatcher); - this.dispatcher.move(e, inEvent); - } -}; - - -/** - * Handler for `mouseup`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.MouseSource.prototype.mouseup = function(inEvent) { - if (!this.isEventSimulatedFromTouch_(inEvent)) { - var p = this.pointerMap[ol.pointer.MouseSource.POINTER_ID.toString()]; - - if (p && p.button === inEvent.button) { - var e = ol.pointer.MouseSource.prepareEvent(inEvent, this.dispatcher); - this.dispatcher.up(e, inEvent); - this.cleanupMouse(); - } - } -}; - - -/** - * Handler for `mouseover`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.MouseSource.prototype.mouseover = function(inEvent) { - if (!this.isEventSimulatedFromTouch_(inEvent)) { - var e = ol.pointer.MouseSource.prepareEvent(inEvent, this.dispatcher); - this.dispatcher.enterOver(e, inEvent); - } -}; - - -/** - * Handler for `mouseout`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.MouseSource.prototype.mouseout = function(inEvent) { - if (!this.isEventSimulatedFromTouch_(inEvent)) { - var e = ol.pointer.MouseSource.prepareEvent(inEvent, this.dispatcher); - this.dispatcher.leaveOut(e, inEvent); - } -}; - - -/** - * Dispatches a `pointercancel` event. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.MouseSource.prototype.cancel = function(inEvent) { - var e = ol.pointer.MouseSource.prepareEvent(inEvent, this.dispatcher); - this.dispatcher.cancel(e, inEvent); - this.cleanupMouse(); -}; - - -/** - * Remove the mouse from the list of active pointers. - */ -ol.pointer.MouseSource.prototype.cleanupMouse = function() { - delete this.pointerMap[ol.pointer.MouseSource.POINTER_ID.toString()]; -}; - -// Based on https://github.com/Polymer/PointerEvents - -// Copyright (c) 2013 The Polymer Authors. All rights reserved. -// -// Redistribution and use in source and binary forms, with or without -// modification, are permitted provided that the following conditions are -// met: -// -// * Redistributions of source code must retain the above copyright -// notice, this list of conditions and the following disclaimer. -// * Redistributions in binary form must reproduce the above -// copyright notice, this list of conditions and the following disclaimer -// in the documentation and/or other materials provided with the -// distribution. -// * Neither the name of Google Inc. nor the names of its -// contributors may be used to endorse or promote products derived from -// this software without specific prior written permission. -// -// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT -// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, -// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT -// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, -// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY -// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE -// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - -goog.provide('ol.pointer.MsSource'); - -goog.require('ol'); -goog.require('ol.pointer.EventSource'); - - -/** - * @param {ol.pointer.PointerEventHandler} dispatcher Event handler. - * @constructor - * @extends {ol.pointer.EventSource} - */ -ol.pointer.MsSource = function(dispatcher) { - var mapping = { - 'MSPointerDown': this.msPointerDown, - 'MSPointerMove': this.msPointerMove, - 'MSPointerUp': this.msPointerUp, - 'MSPointerOut': this.msPointerOut, - 'MSPointerOver': this.msPointerOver, - 'MSPointerCancel': this.msPointerCancel, - 'MSGotPointerCapture': this.msGotPointerCapture, - 'MSLostPointerCapture': this.msLostPointerCapture - }; - ol.pointer.EventSource.call(this, dispatcher, mapping); - - /** - * @const - * @type {!Object.<string, Event|Object>} - */ - this.pointerMap = dispatcher.pointerMap; - - /** - * @const - * @type {Array.<string>} - */ - this.POINTER_TYPES = [ - '', - 'unavailable', - 'touch', - 'pen', - 'mouse' - ]; -}; -ol.inherits(ol.pointer.MsSource, ol.pointer.EventSource); - - -/** - * Creates a copy of the original event that will be used - * for the fake pointer event. - * - * @private - * @param {Event} inEvent The in event. - * @return {Object} The copied event. - */ -ol.pointer.MsSource.prototype.prepareEvent_ = function(inEvent) { - var e = inEvent; - if (typeof inEvent.pointerType === 'number') { - e = this.dispatcher.cloneEvent(inEvent, inEvent); - e.pointerType = this.POINTER_TYPES[inEvent.pointerType]; - } - - return e; -}; - - -/** - * Remove this pointer from the list of active pointers. - * @param {number} pointerId Pointer identifier. - */ -ol.pointer.MsSource.prototype.cleanup = function(pointerId) { - delete this.pointerMap[pointerId.toString()]; -}; - - -/** - * Handler for `msPointerDown`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.MsSource.prototype.msPointerDown = function(inEvent) { - this.pointerMap[inEvent.pointerId.toString()] = inEvent; - var e = this.prepareEvent_(inEvent); - this.dispatcher.down(e, inEvent); -}; - - -/** - * Handler for `msPointerMove`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.MsSource.prototype.msPointerMove = function(inEvent) { - var e = this.prepareEvent_(inEvent); - this.dispatcher.move(e, inEvent); -}; - - -/** - * Handler for `msPointerUp`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.MsSource.prototype.msPointerUp = function(inEvent) { - var e = this.prepareEvent_(inEvent); - this.dispatcher.up(e, inEvent); - this.cleanup(inEvent.pointerId); -}; - - -/** - * Handler for `msPointerOut`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.MsSource.prototype.msPointerOut = function(inEvent) { - var e = this.prepareEvent_(inEvent); - this.dispatcher.leaveOut(e, inEvent); -}; - - -/** - * Handler for `msPointerOver`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.MsSource.prototype.msPointerOver = function(inEvent) { - var e = this.prepareEvent_(inEvent); - this.dispatcher.enterOver(e, inEvent); -}; - - -/** - * Handler for `msPointerCancel`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.MsSource.prototype.msPointerCancel = function(inEvent) { - var e = this.prepareEvent_(inEvent); - this.dispatcher.cancel(e, inEvent); - this.cleanup(inEvent.pointerId); -}; - - -/** - * Handler for `msLostPointerCapture`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.MsSource.prototype.msLostPointerCapture = function(inEvent) { - var e = this.dispatcher.makeEvent('lostpointercapture', - inEvent, inEvent); - this.dispatcher.dispatchEvent(e); -}; - - -/** - * Handler for `msGotPointerCapture`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.MsSource.prototype.msGotPointerCapture = function(inEvent) { - var e = this.dispatcher.makeEvent('gotpointercapture', - inEvent, inEvent); - this.dispatcher.dispatchEvent(e); -}; - -// Based on https://github.com/Polymer/PointerEvents - -// Copyright (c) 2013 The Polymer Authors. All rights reserved. -// -// Redistribution and use in source and binary forms, with or without -// modification, are permitted provided that the following conditions are -// met: -// -// * Redistributions of source code must retain the above copyright -// notice, this list of conditions and the following disclaimer. -// * Redistributions in binary form must reproduce the above -// copyright notice, this list of conditions and the following disclaimer -// in the documentation and/or other materials provided with the -// distribution. -// * Neither the name of Google Inc. nor the names of its -// contributors may be used to endorse or promote products derived from -// this software without specific prior written permission. -// -// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT -// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, -// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT -// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, -// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY -// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE -// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - -goog.provide('ol.pointer.NativeSource'); - -goog.require('ol'); -goog.require('ol.pointer.EventSource'); - - -/** - * @param {ol.pointer.PointerEventHandler} dispatcher Event handler. - * @constructor - * @extends {ol.pointer.EventSource} - */ -ol.pointer.NativeSource = function(dispatcher) { - var mapping = { - 'pointerdown': this.pointerDown, - 'pointermove': this.pointerMove, - 'pointerup': this.pointerUp, - 'pointerout': this.pointerOut, - 'pointerover': this.pointerOver, - 'pointercancel': this.pointerCancel, - 'gotpointercapture': this.gotPointerCapture, - 'lostpointercapture': this.lostPointerCapture - }; - ol.pointer.EventSource.call(this, dispatcher, mapping); -}; -ol.inherits(ol.pointer.NativeSource, ol.pointer.EventSource); - - -/** - * Handler for `pointerdown`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.NativeSource.prototype.pointerDown = function(inEvent) { - this.dispatcher.fireNativeEvent(inEvent); -}; - - -/** - * Handler for `pointermove`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.NativeSource.prototype.pointerMove = function(inEvent) { - this.dispatcher.fireNativeEvent(inEvent); -}; - - -/** - * Handler for `pointerup`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.NativeSource.prototype.pointerUp = function(inEvent) { - this.dispatcher.fireNativeEvent(inEvent); -}; - - -/** - * Handler for `pointerout`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.NativeSource.prototype.pointerOut = function(inEvent) { - this.dispatcher.fireNativeEvent(inEvent); -}; - - -/** - * Handler for `pointerover`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.NativeSource.prototype.pointerOver = function(inEvent) { - this.dispatcher.fireNativeEvent(inEvent); -}; - - -/** - * Handler for `pointercancel`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.NativeSource.prototype.pointerCancel = function(inEvent) { - this.dispatcher.fireNativeEvent(inEvent); -}; - - -/** - * Handler for `lostpointercapture`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.NativeSource.prototype.lostPointerCapture = function(inEvent) { - this.dispatcher.fireNativeEvent(inEvent); -}; - - -/** - * Handler for `gotpointercapture`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.NativeSource.prototype.gotPointerCapture = function(inEvent) { - this.dispatcher.fireNativeEvent(inEvent); -}; - -// Based on https://github.com/Polymer/PointerEvents - -// Copyright (c) 2013 The Polymer Authors. All rights reserved. -// -// Redistribution and use in source and binary forms, with or without -// modification, are permitted provided that the following conditions are -// met: -// -// * Redistributions of source code must retain the above copyright -// notice, this list of conditions and the following disclaimer. -// * Redistributions in binary form must reproduce the above -// copyright notice, this list of conditions and the following disclaimer -// in the documentation and/or other materials provided with the -// distribution. -// * Neither the name of Google Inc. nor the names of its -// contributors may be used to endorse or promote products derived from -// this software without specific prior written permission. -// -// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT -// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, -// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT -// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, -// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY -// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE -// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - -goog.provide('ol.pointer.PointerEvent'); - - -goog.require('ol'); -goog.require('ol.events.Event'); - - -/** - * A class for pointer events. - * - * This class is used as an abstraction for mouse events, - * touch events and even native pointer events. - * - * @constructor - * @extends {ol.events.Event} - * @param {string} type The type of the event to create. - * @param {Event} originalEvent The event. - * @param {Object.<string, ?>=} opt_eventDict An optional dictionary of - * initial event properties. - */ -ol.pointer.PointerEvent = function(type, originalEvent, opt_eventDict) { - ol.events.Event.call(this, type); - - /** - * @const - * @type {Event} - */ - this.originalEvent = originalEvent; - - var eventDict = opt_eventDict ? opt_eventDict : {}; - - /** - * @type {number} - */ - this.buttons = this.getButtons_(eventDict); - - /** - * @type {number} - */ - this.pressure = this.getPressure_(eventDict, this.buttons); - - // MouseEvent related properties - - /** - * @type {boolean} - */ - this.bubbles = 'bubbles' in eventDict ? eventDict['bubbles'] : false; - - /** - * @type {boolean} - */ - this.cancelable = 'cancelable' in eventDict ? eventDict['cancelable'] : false; - - /** - * @type {Object} - */ - this.view = 'view' in eventDict ? eventDict['view'] : null; - - /** - * @type {number} - */ - this.detail = 'detail' in eventDict ? eventDict['detail'] : null; - - /** - * @type {number} - */ - this.screenX = 'screenX' in eventDict ? eventDict['screenX'] : 0; - - /** - * @type {number} - */ - this.screenY = 'screenY' in eventDict ? eventDict['screenY'] : 0; - - /** - * @type {number} - */ - this.clientX = 'clientX' in eventDict ? eventDict['clientX'] : 0; - - /** - * @type {number} - */ - this.clientY = 'clientY' in eventDict ? eventDict['clientY'] : 0; - - /** - * @type {boolean} - */ - this.ctrlKey = 'ctrlKey' in eventDict ? eventDict['ctrlKey'] : false; - - /** - * @type {boolean} - */ - this.altKey = 'altKey' in eventDict ? eventDict['altKey'] : false; - - /** - * @type {boolean} - */ - this.shiftKey = 'shiftKey' in eventDict ? eventDict['shiftKey'] : false; - - /** - * @type {boolean} - */ - this.metaKey = 'metaKey' in eventDict ? eventDict['metaKey'] : false; - - /** - * @type {number} - */ - this.button = 'button' in eventDict ? eventDict['button'] : 0; - - /** - * @type {Node} - */ - this.relatedTarget = 'relatedTarget' in eventDict ? - eventDict['relatedTarget'] : null; - - // PointerEvent related properties - - /** - * @const - * @type {number} - */ - this.pointerId = 'pointerId' in eventDict ? eventDict['pointerId'] : 0; - - /** - * @type {number} - */ - this.width = 'width' in eventDict ? eventDict['width'] : 0; - - /** - * @type {number} - */ - this.height = 'height' in eventDict ? eventDict['height'] : 0; - - /** - * @type {number} - */ - this.tiltX = 'tiltX' in eventDict ? eventDict['tiltX'] : 0; - - /** - * @type {number} - */ - this.tiltY = 'tiltY' in eventDict ? eventDict['tiltY'] : 0; - - /** - * @type {string} - */ - this.pointerType = 'pointerType' in eventDict ? eventDict['pointerType'] : ''; - - /** - * @type {number} - */ - this.hwTimestamp = 'hwTimestamp' in eventDict ? eventDict['hwTimestamp'] : 0; - - /** - * @type {boolean} - */ - this.isPrimary = 'isPrimary' in eventDict ? eventDict['isPrimary'] : false; - - // keep the semantics of preventDefault - if (originalEvent.preventDefault) { - this.preventDefault = function() { - originalEvent.preventDefault(); - }; - } -}; -ol.inherits(ol.pointer.PointerEvent, ol.events.Event); - - -/** - * @private - * @param {Object.<string, ?>} eventDict The event dictionary. - * @return {number} Button indicator. - */ -ol.pointer.PointerEvent.prototype.getButtons_ = function(eventDict) { - // According to the w3c spec, - // http://www.w3.org/TR/DOM-Level-3-Events/#events-MouseEvent-button - // MouseEvent.button == 0 can mean either no mouse button depressed, or the - // left mouse button depressed. - // - // As of now, the only way to distinguish between the two states of - // MouseEvent.button is by using the deprecated MouseEvent.which property, as - // this maps mouse buttons to positive integers > 0, and uses 0 to mean that - // no mouse button is held. - // - // MouseEvent.which is derived from MouseEvent.button at MouseEvent creation, - // but initMouseEvent does not expose an argument with which to set - // MouseEvent.which. Calling initMouseEvent with a buttonArg of 0 will set - // MouseEvent.button == 0 and MouseEvent.which == 1, breaking the expectations - // of app developers. - // - // The only way to propagate the correct state of MouseEvent.which and - // MouseEvent.button to a new MouseEvent.button == 0 and MouseEvent.which == 0 - // is to call initMouseEvent with a buttonArg value of -1. - // - // This is fixed with DOM Level 4's use of buttons - var buttons; - if (eventDict.buttons || ol.pointer.PointerEvent.HAS_BUTTONS) { - buttons = eventDict.buttons; - } else { - switch (eventDict.which) { - case 1: buttons = 1; break; - case 2: buttons = 4; break; - case 3: buttons = 2; break; - default: buttons = 0; - } - } - return buttons; -}; - - -/** - * @private - * @param {Object.<string, ?>} eventDict The event dictionary. - * @param {number} buttons Button indicator. - * @return {number} The pressure. - */ -ol.pointer.PointerEvent.prototype.getPressure_ = function(eventDict, buttons) { - // Spec requires that pointers without pressure specified use 0.5 for down - // state and 0 for up state. - var pressure = 0; - if (eventDict.pressure) { - pressure = eventDict.pressure; - } else { - pressure = buttons ? 0.5 : 0; - } - return pressure; -}; - - -/** - * Is the `buttons` property supported? - * @type {boolean} - */ -ol.pointer.PointerEvent.HAS_BUTTONS = false; - - -/** - * Checks if the `buttons` property is supported. - */ -(function() { - try { - var ev = new MouseEvent('click', {buttons: 1}); - ol.pointer.PointerEvent.HAS_BUTTONS = ev.buttons === 1; - } catch (e) { - // pass - } -})(); - -// Based on https://github.com/Polymer/PointerEvents - -// Copyright (c) 2013 The Polymer Authors. All rights reserved. -// -// Redistribution and use in source and binary forms, with or without -// modification, are permitted provided that the following conditions are -// met: -// -// * Redistributions of source code must retain the above copyright -// notice, this list of conditions and the following disclaimer. -// * Redistributions in binary form must reproduce the above -// copyright notice, this list of conditions and the following disclaimer -// in the documentation and/or other materials provided with the -// distribution. -// * Neither the name of Google Inc. nor the names of its -// contributors may be used to endorse or promote products derived from -// this software without specific prior written permission. -// -// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT -// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, -// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT -// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, -// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY -// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE -// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - -goog.provide('ol.pointer.TouchSource'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.pointer.EventSource'); -goog.require('ol.pointer.MouseSource'); - - -/** - * @constructor - * @param {ol.pointer.PointerEventHandler} dispatcher The event handler. - * @param {ol.pointer.MouseSource} mouseSource Mouse source. - * @extends {ol.pointer.EventSource} - */ -ol.pointer.TouchSource = function(dispatcher, mouseSource) { - var mapping = { - 'touchstart': this.touchstart, - 'touchmove': this.touchmove, - 'touchend': this.touchend, - 'touchcancel': this.touchcancel - }; - ol.pointer.EventSource.call(this, dispatcher, mapping); - - /** - * @const - * @type {!Object.<string, Event|Object>} - */ - this.pointerMap = dispatcher.pointerMap; - - /** - * @const - * @type {ol.pointer.MouseSource} - */ - this.mouseSource = mouseSource; - - /** - * @private - * @type {number|undefined} - */ - this.firstTouchId_ = undefined; - - /** - * @private - * @type {number} - */ - this.clickCount_ = 0; - - /** - * @private - * @type {number|undefined} - */ - this.resetId_ = undefined; -}; -ol.inherits(ol.pointer.TouchSource, ol.pointer.EventSource); - - -/** - * Mouse event timeout: This should be long enough to - * ignore compat mouse events made by touch. - * @const - * @type {number} - */ -ol.pointer.TouchSource.DEDUP_TIMEOUT = 2500; - - -/** - * @const - * @type {number} - */ -ol.pointer.TouchSource.CLICK_COUNT_TIMEOUT = 200; - - -/** - * @const - * @type {string} - */ -ol.pointer.TouchSource.POINTER_TYPE = 'touch'; - - -/** - * @private - * @param {Touch} inTouch The in touch. - * @return {boolean} True, if this is the primary touch. - */ -ol.pointer.TouchSource.prototype.isPrimaryTouch_ = function(inTouch) { - return this.firstTouchId_ === inTouch.identifier; -}; - - -/** - * Set primary touch if there are no pointers, or the only pointer is the mouse. - * @param {Touch} inTouch The in touch. - * @private - */ -ol.pointer.TouchSource.prototype.setPrimaryTouch_ = function(inTouch) { - var count = Object.keys(this.pointerMap).length; - if (count === 0 || (count === 1 && - ol.pointer.MouseSource.POINTER_ID.toString() in this.pointerMap)) { - this.firstTouchId_ = inTouch.identifier; - this.cancelResetClickCount_(); - } -}; - - -/** - * @private - * @param {Object} inPointer The in pointer object. - */ -ol.pointer.TouchSource.prototype.removePrimaryPointer_ = function(inPointer) { - if (inPointer.isPrimary) { - this.firstTouchId_ = undefined; - this.resetClickCount_(); - } -}; - - -/** - * @private - */ -ol.pointer.TouchSource.prototype.resetClickCount_ = function() { - this.resetId_ = setTimeout( - this.resetClickCountHandler_.bind(this), - ol.pointer.TouchSource.CLICK_COUNT_TIMEOUT); -}; - - -/** - * @private - */ -ol.pointer.TouchSource.prototype.resetClickCountHandler_ = function() { - this.clickCount_ = 0; - this.resetId_ = undefined; -}; - - -/** - * @private - */ -ol.pointer.TouchSource.prototype.cancelResetClickCount_ = function() { - if (this.resetId_ !== undefined) { - clearTimeout(this.resetId_); - } -}; - - -/** - * @private - * @param {Event} browserEvent Browser event - * @param {Touch} inTouch Touch event - * @return {Object} A pointer object. - */ -ol.pointer.TouchSource.prototype.touchToPointer_ = function(browserEvent, inTouch) { - var e = this.dispatcher.cloneEvent(browserEvent, inTouch); - // Spec specifies that pointerId 1 is reserved for Mouse. - // Touch identifiers can start at 0. - // Add 2 to the touch identifier for compatibility. - e.pointerId = inTouch.identifier + 2; - // TODO: check if this is necessary? - //e.target = findTarget(e); - e.bubbles = true; - e.cancelable = true; - e.detail = this.clickCount_; - e.button = 0; - e.buttons = 1; - e.width = inTouch.webkitRadiusX || inTouch.radiusX || 0; - e.height = inTouch.webkitRadiusY || inTouch.radiusY || 0; - e.pressure = inTouch.webkitForce || inTouch.force || 0.5; - e.isPrimary = this.isPrimaryTouch_(inTouch); - e.pointerType = ol.pointer.TouchSource.POINTER_TYPE; - - // make sure that the properties that are different for - // each `Touch` object are not copied from the BrowserEvent object - e.clientX = inTouch.clientX; - e.clientY = inTouch.clientY; - e.screenX = inTouch.screenX; - e.screenY = inTouch.screenY; - - return e; -}; - - -/** - * @private - * @param {Event} inEvent Touch event - * @param {function(Event, Object)} inFunction In function. - */ -ol.pointer.TouchSource.prototype.processTouches_ = function(inEvent, inFunction) { - var touches = Array.prototype.slice.call( - inEvent.changedTouches); - var count = touches.length; - function preventDefault() { - inEvent.preventDefault(); - } - var i, pointer; - for (i = 0; i < count; ++i) { - pointer = this.touchToPointer_(inEvent, touches[i]); - // forward touch preventDefaults - pointer.preventDefault = preventDefault; - inFunction.call(this, inEvent, pointer); - } -}; - - -/** - * @private - * @param {TouchList} touchList The touch list. - * @param {number} searchId Search identifier. - * @return {boolean} True, if the `Touch` with the given id is in the list. - */ -ol.pointer.TouchSource.prototype.findTouch_ = function(touchList, searchId) { - var l = touchList.length; - var touch; - for (var i = 0; i < l; i++) { - touch = touchList[i]; - if (touch.identifier === searchId) { - return true; - } - } - return false; -}; - - -/** - * In some instances, a touchstart can happen without a touchend. This - * leaves the pointermap in a broken state. - * Therefore, on every touchstart, we remove the touches that did not fire a - * touchend event. - * To keep state globally consistent, we fire a pointercancel for - * this "abandoned" touch - * - * @private - * @param {Event} inEvent The in event. - */ -ol.pointer.TouchSource.prototype.vacuumTouches_ = function(inEvent) { - var touchList = inEvent.touches; - // pointerMap.getCount() should be < touchList.length here, - // as the touchstart has not been processed yet. - var keys = Object.keys(this.pointerMap); - var count = keys.length; - if (count >= touchList.length) { - var d = []; - var i, key, value; - for (i = 0; i < count; ++i) { - key = keys[i]; - value = this.pointerMap[key]; - // Never remove pointerId == 1, which is mouse. - // Touch identifiers are 2 smaller than their pointerId, which is the - // index in pointermap. - if (key != ol.pointer.MouseSource.POINTER_ID && - !this.findTouch_(touchList, key - 2)) { - d.push(value.out); - } - } - for (i = 0; i < d.length; ++i) { - this.cancelOut_(inEvent, d[i]); - } - } -}; - - -/** - * Handler for `touchstart`, triggers `pointerover`, - * `pointerenter` and `pointerdown` events. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.TouchSource.prototype.touchstart = function(inEvent) { - this.vacuumTouches_(inEvent); - this.setPrimaryTouch_(inEvent.changedTouches[0]); - this.dedupSynthMouse_(inEvent); - this.clickCount_++; - this.processTouches_(inEvent, this.overDown_); -}; - - -/** - * @private - * @param {Event} browserEvent The event. - * @param {Object} inPointer The in pointer object. - */ -ol.pointer.TouchSource.prototype.overDown_ = function(browserEvent, inPointer) { - this.pointerMap[inPointer.pointerId] = { - target: inPointer.target, - out: inPointer, - outTarget: inPointer.target - }; - this.dispatcher.over(inPointer, browserEvent); - this.dispatcher.enter(inPointer, browserEvent); - this.dispatcher.down(inPointer, browserEvent); -}; - - -/** - * Handler for `touchmove`. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.TouchSource.prototype.touchmove = function(inEvent) { - inEvent.preventDefault(); - this.processTouches_(inEvent, this.moveOverOut_); -}; - - -/** - * @private - * @param {Event} browserEvent The event. - * @param {Object} inPointer The in pointer. - */ -ol.pointer.TouchSource.prototype.moveOverOut_ = function(browserEvent, inPointer) { - var event = inPointer; - var pointer = this.pointerMap[event.pointerId]; - // a finger drifted off the screen, ignore it - if (!pointer) { - return; - } - var outEvent = pointer.out; - var outTarget = pointer.outTarget; - this.dispatcher.move(event, browserEvent); - if (outEvent && outTarget !== event.target) { - outEvent.relatedTarget = event.target; - event.relatedTarget = outTarget; - // recover from retargeting by shadow - outEvent.target = outTarget; - if (event.target) { - this.dispatcher.leaveOut(outEvent, browserEvent); - this.dispatcher.enterOver(event, browserEvent); - } else { - // clean up case when finger leaves the screen - event.target = outTarget; - event.relatedTarget = null; - this.cancelOut_(browserEvent, event); - } - } - pointer.out = event; - pointer.outTarget = event.target; -}; - - -/** - * Handler for `touchend`, triggers `pointerup`, - * `pointerout` and `pointerleave` events. - * - * @param {Event} inEvent The event. - */ -ol.pointer.TouchSource.prototype.touchend = function(inEvent) { - this.dedupSynthMouse_(inEvent); - this.processTouches_(inEvent, this.upOut_); -}; - - -/** - * @private - * @param {Event} browserEvent An event. - * @param {Object} inPointer The inPointer object. - */ -ol.pointer.TouchSource.prototype.upOut_ = function(browserEvent, inPointer) { - this.dispatcher.up(inPointer, browserEvent); - this.dispatcher.out(inPointer, browserEvent); - this.dispatcher.leave(inPointer, browserEvent); - this.cleanUpPointer_(inPointer); -}; - - -/** - * Handler for `touchcancel`, triggers `pointercancel`, - * `pointerout` and `pointerleave` events. - * - * @param {Event} inEvent The in event. - */ -ol.pointer.TouchSource.prototype.touchcancel = function(inEvent) { - this.processTouches_(inEvent, this.cancelOut_); -}; - - -/** - * @private - * @param {Event} browserEvent The event. - * @param {Object} inPointer The in pointer. - */ -ol.pointer.TouchSource.prototype.cancelOut_ = function(browserEvent, inPointer) { - this.dispatcher.cancel(inPointer, browserEvent); - this.dispatcher.out(inPointer, browserEvent); - this.dispatcher.leave(inPointer, browserEvent); - this.cleanUpPointer_(inPointer); -}; - - -/** - * @private - * @param {Object} inPointer The inPointer object. - */ -ol.pointer.TouchSource.prototype.cleanUpPointer_ = function(inPointer) { - delete this.pointerMap[inPointer.pointerId]; - this.removePrimaryPointer_(inPointer); -}; - - -/** - * Prevent synth mouse events from creating pointer events. - * - * @private - * @param {Event} inEvent The in event. - */ -ol.pointer.TouchSource.prototype.dedupSynthMouse_ = function(inEvent) { - var lts = this.mouseSource.lastTouches; - var t = inEvent.changedTouches[0]; - // only the primary finger will synth mouse events - if (this.isPrimaryTouch_(t)) { - // remember x/y of last touch - var lt = [t.clientX, t.clientY]; - lts.push(lt); - - setTimeout(function() { - // remove touch after timeout - ol.array.remove(lts, lt); - }, ol.pointer.TouchSource.DEDUP_TIMEOUT); - } -}; - -// Based on https://github.com/Polymer/PointerEvents - -// Copyright (c) 2013 The Polymer Authors. All rights reserved. -// -// Redistribution and use in source and binary forms, with or without -// modification, are permitted provided that the following conditions are -// met: -// -// * Redistributions of source code must retain the above copyright -// notice, this list of conditions and the following disclaimer. -// * Redistributions in binary form must reproduce the above -// copyright notice, this list of conditions and the following disclaimer -// in the documentation and/or other materials provided with the -// distribution. -// * Neither the name of Google Inc. nor the names of its -// contributors may be used to endorse or promote products derived from -// this software without specific prior written permission. -// -// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT -// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, -// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT -// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, -// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY -// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE -// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - -goog.provide('ol.pointer.PointerEventHandler'); - -goog.require('ol'); -goog.require('ol.events'); -goog.require('ol.events.EventTarget'); - -goog.require('ol.has'); -goog.require('ol.pointer.EventType'); -goog.require('ol.pointer.MouseSource'); -goog.require('ol.pointer.MsSource'); -goog.require('ol.pointer.NativeSource'); -goog.require('ol.pointer.PointerEvent'); -goog.require('ol.pointer.TouchSource'); - - -/** - * @constructor - * @extends {ol.events.EventTarget} - * @param {Element|HTMLDocument} element Viewport element. - */ -ol.pointer.PointerEventHandler = function(element) { - ol.events.EventTarget.call(this); - - /** - * @const - * @private - * @type {Element|HTMLDocument} - */ - this.element_ = element; - - /** - * @const - * @type {!Object.<string, Event|Object>} - */ - this.pointerMap = {}; - - /** - * @type {Object.<string, function(Event)>} - * @private - */ - this.eventMap_ = {}; - - /** - * @type {Array.<ol.pointer.EventSource>} - * @private - */ - this.eventSourceList_ = []; - - this.registerSources(); -}; -ol.inherits(ol.pointer.PointerEventHandler, ol.events.EventTarget); - - -/** - * Set up the event sources (mouse, touch and native pointers) - * that generate pointer events. - */ -ol.pointer.PointerEventHandler.prototype.registerSources = function() { - if (ol.has.POINTER) { - this.registerSource('native', new ol.pointer.NativeSource(this)); - } else if (ol.has.MSPOINTER) { - this.registerSource('ms', new ol.pointer.MsSource(this)); - } else { - var mouseSource = new ol.pointer.MouseSource(this); - this.registerSource('mouse', mouseSource); - - if (ol.has.TOUCH) { - this.registerSource('touch', - new ol.pointer.TouchSource(this, mouseSource)); - } - } - - // register events on the viewport element - this.register_(); -}; - - -/** - * Add a new event source that will generate pointer events. - * - * @param {string} name A name for the event source - * @param {ol.pointer.EventSource} source The source event. - */ -ol.pointer.PointerEventHandler.prototype.registerSource = function(name, source) { - var s = source; - var newEvents = s.getEvents(); - - if (newEvents) { - newEvents.forEach(function(e) { - var handler = s.getHandlerForEvent(e); - - if (handler) { - this.eventMap_[e] = handler.bind(s); - } - }, this); - this.eventSourceList_.push(s); - } -}; - - -/** - * Set up the events for all registered event sources. - * @private - */ -ol.pointer.PointerEventHandler.prototype.register_ = function() { - var l = this.eventSourceList_.length; - var eventSource; - for (var i = 0; i < l; i++) { - eventSource = this.eventSourceList_[i]; - this.addEvents_(eventSource.getEvents()); - } -}; - - -/** - * Remove all registered events. - * @private - */ -ol.pointer.PointerEventHandler.prototype.unregister_ = function() { - var l = this.eventSourceList_.length; - var eventSource; - for (var i = 0; i < l; i++) { - eventSource = this.eventSourceList_[i]; - this.removeEvents_(eventSource.getEvents()); - } -}; - - -/** - * Calls the right handler for a new event. - * @private - * @param {Event} inEvent Browser event. - */ -ol.pointer.PointerEventHandler.prototype.eventHandler_ = function(inEvent) { - var type = inEvent.type; - var handler = this.eventMap_[type]; - if (handler) { - handler(inEvent); - } -}; - - -/** - * Setup listeners for the given events. - * @private - * @param {Array.<string>} events List of events. - */ -ol.pointer.PointerEventHandler.prototype.addEvents_ = function(events) { - events.forEach(function(eventName) { - ol.events.listen(this.element_, eventName, this.eventHandler_, this); - }, this); -}; - - -/** - * Unregister listeners for the given events. - * @private - * @param {Array.<string>} events List of events. - */ -ol.pointer.PointerEventHandler.prototype.removeEvents_ = function(events) { - events.forEach(function(e) { - ol.events.unlisten(this.element_, e, this.eventHandler_, this); - }, this); -}; - - -/** - * Returns a snapshot of inEvent, with writable properties. - * - * @param {Event} event Browser event. - * @param {Event|Touch} inEvent An event that contains - * properties to copy. - * @return {Object} An object containing shallow copies of - * `inEvent`'s properties. - */ -ol.pointer.PointerEventHandler.prototype.cloneEvent = function(event, inEvent) { - var eventCopy = {}, p; - for (var i = 0, ii = ol.pointer.PointerEventHandler.CLONE_PROPS.length; i < ii; i++) { - p = ol.pointer.PointerEventHandler.CLONE_PROPS[i][0]; - eventCopy[p] = event[p] || inEvent[p] || ol.pointer.PointerEventHandler.CLONE_PROPS[i][1]; - } - - return eventCopy; -}; - - -// EVENTS - - -/** - * Triggers a 'pointerdown' event. - * @param {Object} data Pointer event data. - * @param {Event} event The event. - */ -ol.pointer.PointerEventHandler.prototype.down = function(data, event) { - this.fireEvent(ol.pointer.EventType.POINTERDOWN, data, event); -}; - - -/** - * Triggers a 'pointermove' event. - * @param {Object} data Pointer event data. - * @param {Event} event The event. - */ -ol.pointer.PointerEventHandler.prototype.move = function(data, event) { - this.fireEvent(ol.pointer.EventType.POINTERMOVE, data, event); -}; - - -/** - * Triggers a 'pointerup' event. - * @param {Object} data Pointer event data. - * @param {Event} event The event. - */ -ol.pointer.PointerEventHandler.prototype.up = function(data, event) { - this.fireEvent(ol.pointer.EventType.POINTERUP, data, event); -}; - - -/** - * Triggers a 'pointerenter' event. - * @param {Object} data Pointer event data. - * @param {Event} event The event. - */ -ol.pointer.PointerEventHandler.prototype.enter = function(data, event) { - data.bubbles = false; - this.fireEvent(ol.pointer.EventType.POINTERENTER, data, event); -}; - - -/** - * Triggers a 'pointerleave' event. - * @param {Object} data Pointer event data. - * @param {Event} event The event. - */ -ol.pointer.PointerEventHandler.prototype.leave = function(data, event) { - data.bubbles = false; - this.fireEvent(ol.pointer.EventType.POINTERLEAVE, data, event); -}; - - -/** - * Triggers a 'pointerover' event. - * @param {Object} data Pointer event data. - * @param {Event} event The event. - */ -ol.pointer.PointerEventHandler.prototype.over = function(data, event) { - data.bubbles = true; - this.fireEvent(ol.pointer.EventType.POINTEROVER, data, event); -}; - - -/** - * Triggers a 'pointerout' event. - * @param {Object} data Pointer event data. - * @param {Event} event The event. - */ -ol.pointer.PointerEventHandler.prototype.out = function(data, event) { - data.bubbles = true; - this.fireEvent(ol.pointer.EventType.POINTEROUT, data, event); -}; - - -/** - * Triggers a 'pointercancel' event. - * @param {Object} data Pointer event data. - * @param {Event} event The event. - */ -ol.pointer.PointerEventHandler.prototype.cancel = function(data, event) { - this.fireEvent(ol.pointer.EventType.POINTERCANCEL, data, event); -}; - - -/** - * Triggers a combination of 'pointerout' and 'pointerleave' events. - * @param {Object} data Pointer event data. - * @param {Event} event The event. - */ -ol.pointer.PointerEventHandler.prototype.leaveOut = function(data, event) { - this.out(data, event); - if (!this.contains_(data.target, data.relatedTarget)) { - this.leave(data, event); - } -}; - - -/** - * Triggers a combination of 'pointerover' and 'pointerevents' events. - * @param {Object} data Pointer event data. - * @param {Event} event The event. - */ -ol.pointer.PointerEventHandler.prototype.enterOver = function(data, event) { - this.over(data, event); - if (!this.contains_(data.target, data.relatedTarget)) { - this.enter(data, event); - } -}; - - -/** - * @private - * @param {Element} container The container element. - * @param {Element} contained The contained element. - * @return {boolean} Returns true if the container element - * contains the other element. - */ -ol.pointer.PointerEventHandler.prototype.contains_ = function(container, contained) { - if (!container || !contained) { - return false; - } - return container.contains(contained); -}; - - -// EVENT CREATION AND TRACKING -/** - * Creates a new Event of type `inType`, based on the information in - * `data`. - * - * @param {string} inType A string representing the type of event to create. - * @param {Object} data Pointer event data. - * @param {Event} event The event. - * @return {ol.pointer.PointerEvent} A PointerEvent of type `inType`. - */ -ol.pointer.PointerEventHandler.prototype.makeEvent = function(inType, data, event) { - return new ol.pointer.PointerEvent(inType, event, data); -}; - - -/** - * Make and dispatch an event in one call. - * @param {string} inType A string representing the type of event. - * @param {Object} data Pointer event data. - * @param {Event} event The event. - */ -ol.pointer.PointerEventHandler.prototype.fireEvent = function(inType, data, event) { - var e = this.makeEvent(inType, data, event); - this.dispatchEvent(e); -}; - - -/** - * Creates a pointer event from a native pointer event - * and dispatches this event. - * @param {Event} event A platform event with a target. - */ -ol.pointer.PointerEventHandler.prototype.fireNativeEvent = function(event) { - var e = this.makeEvent(event.type, event, event); - this.dispatchEvent(e); -}; - - -/** - * Wrap a native mouse event into a pointer event. - * This proxy method is required for the legacy IE support. - * @param {string} eventType The pointer event type. - * @param {Event} event The event. - * @return {ol.pointer.PointerEvent} The wrapped event. - */ -ol.pointer.PointerEventHandler.prototype.wrapMouseEvent = function(eventType, event) { - var pointerEvent = this.makeEvent( - eventType, ol.pointer.MouseSource.prepareEvent(event, this), event); - return pointerEvent; -}; - - -/** - * @inheritDoc - */ -ol.pointer.PointerEventHandler.prototype.disposeInternal = function() { - this.unregister_(); - ol.events.EventTarget.prototype.disposeInternal.call(this); -}; - - -/** - * Properties to copy when cloning an event, with default values. - * @type {Array.<Array>} - */ -ol.pointer.PointerEventHandler.CLONE_PROPS = [ - // MouseEvent - ['bubbles', false], - ['cancelable', false], - ['view', null], - ['detail', null], - ['screenX', 0], - ['screenY', 0], - ['clientX', 0], - ['clientY', 0], - ['ctrlKey', false], - ['altKey', false], - ['shiftKey', false], - ['metaKey', false], - ['button', 0], - ['relatedTarget', null], - // DOM Level 3 - ['buttons', 0], - // PointerEvent - ['pointerId', 0], - ['width', 0], - ['height', 0], - ['pressure', 0], - ['tiltX', 0], - ['tiltY', 0], - ['pointerType', ''], - ['hwTimestamp', 0], - ['isPrimary', false], - // event instance - ['type', ''], - ['target', null], - ['currentTarget', null], - ['which', 0] -]; - -goog.provide('ol.MapBrowserEventHandler'); - -goog.require('ol'); -goog.require('ol.has'); -goog.require('ol.MapBrowserEventType'); -goog.require('ol.MapBrowserPointerEvent'); -goog.require('ol.events'); -goog.require('ol.events.EventTarget'); -goog.require('ol.pointer.EventType'); -goog.require('ol.pointer.PointerEventHandler'); - - -/** - * @param {ol.PluggableMap} map The map with the viewport to listen to events on. - * @param {number|undefined} moveTolerance The minimal distance the pointer must travel to trigger a move. - * @constructor - * @extends {ol.events.EventTarget} - */ -ol.MapBrowserEventHandler = function(map, moveTolerance) { - - ol.events.EventTarget.call(this); - - /** - * This is the element that we will listen to the real events on. - * @type {ol.PluggableMap} - * @private - */ - this.map_ = map; - - /** - * @type {number} - * @private - */ - this.clickTimeoutId_ = 0; - - /** - * @type {boolean} - * @private - */ - this.dragging_ = false; - - /** - * @type {!Array.<ol.EventsKey>} - * @private - */ - this.dragListenerKeys_ = []; - - /** - * @type {number} - * @private - */ - this.moveTolerance_ = moveTolerance ? - moveTolerance * ol.has.DEVICE_PIXEL_RATIO : ol.has.DEVICE_PIXEL_RATIO; - - /** - * The most recent "down" type event (or null if none have occurred). - * Set on pointerdown. - * @type {ol.pointer.PointerEvent} - * @private - */ - this.down_ = null; - - var element = this.map_.getViewport(); - - /** - * @type {number} - * @private - */ - this.activePointers_ = 0; - - /** - * @type {!Object.<number, boolean>} - * @private - */ - this.trackedTouches_ = {}; - - /** - * Event handler which generates pointer events for - * the viewport element. - * - * @type {ol.pointer.PointerEventHandler} - * @private - */ - this.pointerEventHandler_ = new ol.pointer.PointerEventHandler(element); - - /** - * Event handler which generates pointer events for - * the document (used when dragging). - * - * @type {ol.pointer.PointerEventHandler} - * @private - */ - this.documentPointerEventHandler_ = null; - - /** - * @type {?ol.EventsKey} - * @private - */ - this.pointerdownListenerKey_ = ol.events.listen(this.pointerEventHandler_, - ol.pointer.EventType.POINTERDOWN, - this.handlePointerDown_, this); - - /** - * @type {?ol.EventsKey} - * @private - */ - this.relayedListenerKey_ = ol.events.listen(this.pointerEventHandler_, - ol.pointer.EventType.POINTERMOVE, - this.relayEvent_, this); - -}; -ol.inherits(ol.MapBrowserEventHandler, ol.events.EventTarget); - - -/** - * @param {ol.pointer.PointerEvent} pointerEvent Pointer event. - * @private - */ -ol.MapBrowserEventHandler.prototype.emulateClick_ = function(pointerEvent) { - var newEvent = new ol.MapBrowserPointerEvent( - ol.MapBrowserEventType.CLICK, this.map_, pointerEvent); - this.dispatchEvent(newEvent); - if (this.clickTimeoutId_ !== 0) { - // double-click - clearTimeout(this.clickTimeoutId_); - this.clickTimeoutId_ = 0; - newEvent = new ol.MapBrowserPointerEvent( - ol.MapBrowserEventType.DBLCLICK, this.map_, pointerEvent); - this.dispatchEvent(newEvent); - } else { - // click - this.clickTimeoutId_ = setTimeout(function() { - this.clickTimeoutId_ = 0; - var newEvent = new ol.MapBrowserPointerEvent( - ol.MapBrowserEventType.SINGLECLICK, this.map_, pointerEvent); - this.dispatchEvent(newEvent); - }.bind(this), 250); - } -}; - - -/** - * Keeps track on how many pointers are currently active. - * - * @param {ol.pointer.PointerEvent} pointerEvent Pointer event. - * @private - */ -ol.MapBrowserEventHandler.prototype.updateActivePointers_ = function(pointerEvent) { - var event = pointerEvent; - - if (event.type == ol.MapBrowserEventType.POINTERUP || - event.type == ol.MapBrowserEventType.POINTERCANCEL) { - delete this.trackedTouches_[event.pointerId]; - } else if (event.type == ol.MapBrowserEventType.POINTERDOWN) { - this.trackedTouches_[event.pointerId] = true; - } - this.activePointers_ = Object.keys(this.trackedTouches_).length; -}; - - -/** - * @param {ol.pointer.PointerEvent} pointerEvent Pointer event. - * @private - */ -ol.MapBrowserEventHandler.prototype.handlePointerUp_ = function(pointerEvent) { - this.updateActivePointers_(pointerEvent); - var newEvent = new ol.MapBrowserPointerEvent( - ol.MapBrowserEventType.POINTERUP, this.map_, pointerEvent); - this.dispatchEvent(newEvent); - - // We emulate click events on left mouse button click, touch contact, and pen - // contact. isMouseActionButton returns true in these cases (evt.button is set - // to 0). - // See http://www.w3.org/TR/pointerevents/#button-states - if (!this.dragging_ && this.isMouseActionButton_(pointerEvent)) { - this.emulateClick_(this.down_); - } - - if (this.activePointers_ === 0) { - this.dragListenerKeys_.forEach(ol.events.unlistenByKey); - this.dragListenerKeys_.length = 0; - this.dragging_ = false; - this.down_ = null; - this.documentPointerEventHandler_.dispose(); - this.documentPointerEventHandler_ = null; - } -}; - - -/** - * @param {ol.pointer.PointerEvent} pointerEvent Pointer event. - * @return {boolean} If the left mouse button was pressed. - * @private - */ -ol.MapBrowserEventHandler.prototype.isMouseActionButton_ = function(pointerEvent) { - return pointerEvent.button === 0; -}; - - -/** - * @param {ol.pointer.PointerEvent} pointerEvent Pointer event. - * @private - */ -ol.MapBrowserEventHandler.prototype.handlePointerDown_ = function(pointerEvent) { - this.updateActivePointers_(pointerEvent); - var newEvent = new ol.MapBrowserPointerEvent( - ol.MapBrowserEventType.POINTERDOWN, this.map_, pointerEvent); - this.dispatchEvent(newEvent); - - this.down_ = pointerEvent; - - if (this.dragListenerKeys_.length === 0) { - /* Set up a pointer event handler on the `document`, - * which is required when the pointer is moved outside - * the viewport when dragging. - */ - this.documentPointerEventHandler_ = - new ol.pointer.PointerEventHandler(document); - - this.dragListenerKeys_.push( - ol.events.listen(this.documentPointerEventHandler_, - ol.MapBrowserEventType.POINTERMOVE, - this.handlePointerMove_, this), - ol.events.listen(this.documentPointerEventHandler_, - ol.MapBrowserEventType.POINTERUP, - this.handlePointerUp_, this), - /* Note that the listener for `pointercancel is set up on - * `pointerEventHandler_` and not `documentPointerEventHandler_` like - * the `pointerup` and `pointermove` listeners. - * - * The reason for this is the following: `TouchSource.vacuumTouches_()` - * issues `pointercancel` events, when there was no `touchend` for a - * `touchstart`. Now, let's say a first `touchstart` is registered on - * `pointerEventHandler_`. The `documentPointerEventHandler_` is set up. - * But `documentPointerEventHandler_` doesn't know about the first - * `touchstart`. If there is no `touchend` for the `touchstart`, we can - * only receive a `touchcancel` from `pointerEventHandler_`, because it is - * only registered there. - */ - ol.events.listen(this.pointerEventHandler_, - ol.MapBrowserEventType.POINTERCANCEL, - this.handlePointerUp_, this) - ); - } -}; - - -/** - * @param {ol.pointer.PointerEvent} pointerEvent Pointer event. - * @private - */ -ol.MapBrowserEventHandler.prototype.handlePointerMove_ = function(pointerEvent) { - // Between pointerdown and pointerup, pointermove events are triggered. - // To avoid a 'false' touchmove event to be dispatched, we test if the pointer - // moved a significant distance. - if (this.isMoving_(pointerEvent)) { - this.dragging_ = true; - var newEvent = new ol.MapBrowserPointerEvent( - ol.MapBrowserEventType.POINTERDRAG, this.map_, pointerEvent, - this.dragging_); - this.dispatchEvent(newEvent); - } - - // Some native android browser triggers mousemove events during small period - // of time. See: https://code.google.com/p/android/issues/detail?id=5491 or - // https://code.google.com/p/android/issues/detail?id=19827 - // ex: Galaxy Tab P3110 + Android 4.1.1 - pointerEvent.preventDefault(); -}; - - -/** - * Wrap and relay a pointer event. Note that this requires that the type - * string for the MapBrowserPointerEvent matches the PointerEvent type. - * @param {ol.pointer.PointerEvent} pointerEvent Pointer event. - * @private - */ -ol.MapBrowserEventHandler.prototype.relayEvent_ = function(pointerEvent) { - var dragging = !!(this.down_ && this.isMoving_(pointerEvent)); - this.dispatchEvent(new ol.MapBrowserPointerEvent( - pointerEvent.type, this.map_, pointerEvent, dragging)); -}; - - -/** - * @param {ol.pointer.PointerEvent} pointerEvent Pointer event. - * @return {boolean} Is moving. - * @private - */ -ol.MapBrowserEventHandler.prototype.isMoving_ = function(pointerEvent) { - return Math.abs(pointerEvent.clientX - this.down_.clientX) > this.moveTolerance_ || - Math.abs(pointerEvent.clientY - this.down_.clientY) > this.moveTolerance_; -}; - - -/** - * @inheritDoc - */ -ol.MapBrowserEventHandler.prototype.disposeInternal = function() { - if (this.relayedListenerKey_) { - ol.events.unlistenByKey(this.relayedListenerKey_); - this.relayedListenerKey_ = null; - } - if (this.pointerdownListenerKey_) { - ol.events.unlistenByKey(this.pointerdownListenerKey_); - this.pointerdownListenerKey_ = null; - } - - this.dragListenerKeys_.forEach(ol.events.unlistenByKey); - this.dragListenerKeys_.length = 0; - - if (this.documentPointerEventHandler_) { - this.documentPointerEventHandler_.dispose(); - this.documentPointerEventHandler_ = null; - } - if (this.pointerEventHandler_) { - this.pointerEventHandler_.dispose(); - this.pointerEventHandler_ = null; - } - ol.events.EventTarget.prototype.disposeInternal.call(this); -}; - -goog.provide('ol.MapEventType'); - -/** - * @enum {string} - */ -ol.MapEventType = { - - /** - * Triggered after a map frame is rendered. - * @event ol.MapEvent#postrender - * @api - */ - POSTRENDER: 'postrender', - - /** - * Triggered when the map starts moving. - * @event ol.MapEvent#movestart - * @api - */ - MOVESTART: 'movestart', - - /** - * Triggered after the map is moved. - * @event ol.MapEvent#moveend - * @api - */ - MOVEEND: 'moveend' - -}; - -goog.provide('ol.MapProperty'); - -/** - * @enum {string} - */ -ol.MapProperty = { - LAYERGROUP: 'layergroup', - SIZE: 'size', - TARGET: 'target', - VIEW: 'view' -}; - -goog.provide('ol.TileState'); - -/** - * @enum {number} - */ -ol.TileState = { - IDLE: 0, - LOADING: 1, - LOADED: 2, - ERROR: 3, - EMPTY: 4, - ABORT: 5 -}; - -goog.provide('ol.structs.PriorityQueue'); - -goog.require('ol.asserts'); -goog.require('ol.obj'); - - -/** - * Priority queue. - * - * The implementation is inspired from the Closure Library's Heap class and - * Python's heapq module. - * - * @see http://closure-library.googlecode.com/svn/docs/closure_goog_structs_heap.js.source.html - * @see http://hg.python.org/cpython/file/2.7/Lib/heapq.py - * - * @constructor - * @param {function(T): number} priorityFunction Priority function. - * @param {function(T): string} keyFunction Key function. - * @struct - * @template T - */ -ol.structs.PriorityQueue = function(priorityFunction, keyFunction) { - - /** - * @type {function(T): number} - * @private - */ - this.priorityFunction_ = priorityFunction; - - /** - * @type {function(T): string} - * @private - */ - this.keyFunction_ = keyFunction; - - /** - * @type {Array.<T>} - * @private - */ - this.elements_ = []; - - /** - * @type {Array.<number>} - * @private - */ - this.priorities_ = []; - - /** - * @type {Object.<string, boolean>} - * @private - */ - this.queuedElements_ = {}; - -}; - - -/** - * @const - * @type {number} - */ -ol.structs.PriorityQueue.DROP = Infinity; - - -/** - * FIXME empty description for jsdoc - */ -ol.structs.PriorityQueue.prototype.clear = function() { - this.elements_.length = 0; - this.priorities_.length = 0; - ol.obj.clear(this.queuedElements_); -}; - - -/** - * Remove and return the highest-priority element. O(log N). - * @return {T} Element. - */ -ol.structs.PriorityQueue.prototype.dequeue = function() { - var elements = this.elements_; - var priorities = this.priorities_; - var element = elements[0]; - if (elements.length == 1) { - elements.length = 0; - priorities.length = 0; - } else { - elements[0] = elements.pop(); - priorities[0] = priorities.pop(); - this.siftUp_(0); - } - var elementKey = this.keyFunction_(element); - delete this.queuedElements_[elementKey]; - return element; -}; - - -/** - * Enqueue an element. O(log N). - * @param {T} element Element. - * @return {boolean} The element was added to the queue. - */ -ol.structs.PriorityQueue.prototype.enqueue = function(element) { - ol.asserts.assert(!(this.keyFunction_(element) in this.queuedElements_), - 31); // Tried to enqueue an `element` that was already added to the queue - var priority = this.priorityFunction_(element); - if (priority != ol.structs.PriorityQueue.DROP) { - this.elements_.push(element); - this.priorities_.push(priority); - this.queuedElements_[this.keyFunction_(element)] = true; - this.siftDown_(0, this.elements_.length - 1); - return true; - } - return false; -}; - - -/** - * @return {number} Count. - */ -ol.structs.PriorityQueue.prototype.getCount = function() { - return this.elements_.length; -}; - - -/** - * Gets the index of the left child of the node at the given index. - * @param {number} index The index of the node to get the left child for. - * @return {number} The index of the left child. - * @private - */ -ol.structs.PriorityQueue.prototype.getLeftChildIndex_ = function(index) { - return index * 2 + 1; -}; - - -/** - * Gets the index of the right child of the node at the given index. - * @param {number} index The index of the node to get the right child for. - * @return {number} The index of the right child. - * @private - */ -ol.structs.PriorityQueue.prototype.getRightChildIndex_ = function(index) { - return index * 2 + 2; -}; - - -/** - * Gets the index of the parent of the node at the given index. - * @param {number} index The index of the node to get the parent for. - * @return {number} The index of the parent. - * @private - */ -ol.structs.PriorityQueue.prototype.getParentIndex_ = function(index) { - return (index - 1) >> 1; -}; - - -/** - * Make this a heap. O(N). - * @private - */ -ol.structs.PriorityQueue.prototype.heapify_ = function() { - var i; - for (i = (this.elements_.length >> 1) - 1; i >= 0; i--) { - this.siftUp_(i); - } -}; - - -/** - * @return {boolean} Is empty. - */ -ol.structs.PriorityQueue.prototype.isEmpty = function() { - return this.elements_.length === 0; -}; - - -/** - * @param {string} key Key. - * @return {boolean} Is key queued. - */ -ol.structs.PriorityQueue.prototype.isKeyQueued = function(key) { - return key in this.queuedElements_; -}; - - -/** - * @param {T} element Element. - * @return {boolean} Is queued. - */ -ol.structs.PriorityQueue.prototype.isQueued = function(element) { - return this.isKeyQueued(this.keyFunction_(element)); -}; - - -/** - * @param {number} index The index of the node to move down. - * @private - */ -ol.structs.PriorityQueue.prototype.siftUp_ = function(index) { - var elements = this.elements_; - var priorities = this.priorities_; - var count = elements.length; - var element = elements[index]; - var priority = priorities[index]; - var startIndex = index; - - while (index < (count >> 1)) { - var lIndex = this.getLeftChildIndex_(index); - var rIndex = this.getRightChildIndex_(index); - - var smallerChildIndex = rIndex < count && - priorities[rIndex] < priorities[lIndex] ? - rIndex : lIndex; - - elements[index] = elements[smallerChildIndex]; - priorities[index] = priorities[smallerChildIndex]; - index = smallerChildIndex; - } - - elements[index] = element; - priorities[index] = priority; - this.siftDown_(startIndex, index); -}; - - -/** - * @param {number} startIndex The index of the root. - * @param {number} index The index of the node to move up. - * @private - */ -ol.structs.PriorityQueue.prototype.siftDown_ = function(startIndex, index) { - var elements = this.elements_; - var priorities = this.priorities_; - var element = elements[index]; - var priority = priorities[index]; - - while (index > startIndex) { - var parentIndex = this.getParentIndex_(index); - if (priorities[parentIndex] > priority) { - elements[index] = elements[parentIndex]; - priorities[index] = priorities[parentIndex]; - index = parentIndex; - } else { - break; - } - } - elements[index] = element; - priorities[index] = priority; -}; - - -/** - * FIXME empty description for jsdoc - */ -ol.structs.PriorityQueue.prototype.reprioritize = function() { - var priorityFunction = this.priorityFunction_; - var elements = this.elements_; - var priorities = this.priorities_; - var index = 0; - var n = elements.length; - var element, i, priority; - for (i = 0; i < n; ++i) { - element = elements[i]; - priority = priorityFunction(element); - if (priority == ol.structs.PriorityQueue.DROP) { - delete this.queuedElements_[this.keyFunction_(element)]; - } else { - priorities[index] = priority; - elements[index++] = element; - } - } - elements.length = index; - priorities.length = index; - this.heapify_(); -}; - -goog.provide('ol.TileQueue'); - -goog.require('ol'); -goog.require('ol.TileState'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.structs.PriorityQueue'); - - -/** - * @constructor - * @extends {ol.structs.PriorityQueue.<Array>} - * @param {ol.TilePriorityFunction} tilePriorityFunction - * Tile priority function. - * @param {function(): ?} tileChangeCallback - * Function called on each tile change event. - * @struct - */ -ol.TileQueue = function(tilePriorityFunction, tileChangeCallback) { - - ol.structs.PriorityQueue.call( - this, - /** - * @param {Array} element Element. - * @return {number} Priority. - */ - function(element) { - return tilePriorityFunction.apply(null, element); - }, - /** - * @param {Array} element Element. - * @return {string} Key. - */ - function(element) { - return /** @type {ol.Tile} */ (element[0]).getKey(); - }); - - /** - * @private - * @type {function(): ?} - */ - this.tileChangeCallback_ = tileChangeCallback; - - /** - * @private - * @type {number} - */ - this.tilesLoading_ = 0; - - /** - * @private - * @type {!Object.<string,boolean>} - */ - this.tilesLoadingKeys_ = {}; - -}; -ol.inherits(ol.TileQueue, ol.structs.PriorityQueue); - - -/** - * @inheritDoc - */ -ol.TileQueue.prototype.enqueue = function(element) { - var added = ol.structs.PriorityQueue.prototype.enqueue.call(this, element); - if (added) { - var tile = element[0]; - ol.events.listen(tile, ol.events.EventType.CHANGE, - this.handleTileChange, this); - } - return added; -}; - - -/** - * @return {number} Number of tiles loading. - */ -ol.TileQueue.prototype.getTilesLoading = function() { - return this.tilesLoading_; -}; - - -/** - * @param {ol.events.Event} event Event. - * @protected - */ -ol.TileQueue.prototype.handleTileChange = function(event) { - var tile = /** @type {ol.Tile} */ (event.target); - var state = tile.getState(); - if (state === ol.TileState.LOADED || state === ol.TileState.ERROR || - state === ol.TileState.EMPTY || state === ol.TileState.ABORT) { - ol.events.unlisten(tile, ol.events.EventType.CHANGE, - this.handleTileChange, this); - var tileKey = tile.getKey(); - if (tileKey in this.tilesLoadingKeys_) { - delete this.tilesLoadingKeys_[tileKey]; - --this.tilesLoading_; - } - this.tileChangeCallback_(); - } -}; - - -/** - * @param {number} maxTotalLoading Maximum number tiles to load simultaneously. - * @param {number} maxNewLoads Maximum number of new tiles to load. - */ -ol.TileQueue.prototype.loadMoreTiles = function(maxTotalLoading, maxNewLoads) { - var newLoads = 0; - var abortedTiles = false; - var state, tile, tileKey; - while (this.tilesLoading_ < maxTotalLoading && newLoads < maxNewLoads && - this.getCount() > 0) { - tile = /** @type {ol.Tile} */ (this.dequeue()[0]); - tileKey = tile.getKey(); - state = tile.getState(); - if (state === ol.TileState.ABORT) { - abortedTiles = true; - } else if (state === ol.TileState.IDLE && !(tileKey in this.tilesLoadingKeys_)) { - this.tilesLoadingKeys_[tileKey] = true; - ++this.tilesLoading_; - ++newLoads; - tile.load(); - } - } - if (newLoads === 0 && abortedTiles) { - // Do not stop the render loop when all wanted tiles were aborted due to - // a small, saturated tile cache. - this.tileChangeCallback_(); - } -}; - -goog.provide('ol.CenterConstraint'); - -goog.require('ol.math'); - - -/** - * @param {ol.Extent} extent Extent. - * @return {ol.CenterConstraintType} The constraint. - */ -ol.CenterConstraint.createExtent = function(extent) { - return ( - /** - * @param {ol.Coordinate|undefined} center Center. - * @return {ol.Coordinate|undefined} Center. - */ - function(center) { - if (center) { - return [ - ol.math.clamp(center[0], extent[0], extent[2]), - ol.math.clamp(center[1], extent[1], extent[3]) - ]; - } else { - return undefined; - } - }); -}; - - -/** - * @param {ol.Coordinate|undefined} center Center. - * @return {ol.Coordinate|undefined} Center. - */ -ol.CenterConstraint.none = function(center) { - return center; -}; - -goog.provide('ol.ResolutionConstraint'); - -goog.require('ol.array'); -goog.require('ol.math'); - - -/** - * @param {Array.<number>} resolutions Resolutions. - * @return {ol.ResolutionConstraintType} Zoom function. - */ -ol.ResolutionConstraint.createSnapToResolutions = function(resolutions) { - return ( - /** - * @param {number|undefined} resolution Resolution. - * @param {number} delta Delta. - * @param {number} direction Direction. - * @return {number|undefined} Resolution. - */ - function(resolution, delta, direction) { - if (resolution !== undefined) { - var z = - ol.array.linearFindNearest(resolutions, resolution, direction); - z = ol.math.clamp(z + delta, 0, resolutions.length - 1); - var index = Math.floor(z); - if (z != index && index < resolutions.length - 1) { - var power = resolutions[index] / resolutions[index + 1]; - return resolutions[index] / Math.pow(power, z - index); - } else { - return resolutions[index]; - } - } else { - return undefined; - } - }); -}; - - -/** - * @param {number} power Power. - * @param {number} maxResolution Maximum resolution. - * @param {number=} opt_maxLevel Maximum level. - * @return {ol.ResolutionConstraintType} Zoom function. - */ -ol.ResolutionConstraint.createSnapToPower = function(power, maxResolution, opt_maxLevel) { - return ( - /** - * @param {number|undefined} resolution Resolution. - * @param {number} delta Delta. - * @param {number} direction Direction. - * @return {number|undefined} Resolution. - */ - function(resolution, delta, direction) { - if (resolution !== undefined) { - var offset = -direction / 2 + 0.5; - var oldLevel = Math.floor( - Math.log(maxResolution / resolution) / Math.log(power) + offset); - var newLevel = Math.max(oldLevel + delta, 0); - if (opt_maxLevel !== undefined) { - newLevel = Math.min(newLevel, opt_maxLevel); - } - return maxResolution / Math.pow(power, newLevel); - } else { - return undefined; - } - }); -}; - -goog.provide('ol.RotationConstraint'); - -goog.require('ol.math'); - - -/** - * @param {number|undefined} rotation Rotation. - * @param {number} delta Delta. - * @return {number|undefined} Rotation. - */ -ol.RotationConstraint.disable = function(rotation, delta) { - if (rotation !== undefined) { - return 0; - } else { - return undefined; - } -}; - - -/** - * @param {number|undefined} rotation Rotation. - * @param {number} delta Delta. - * @return {number|undefined} Rotation. - */ -ol.RotationConstraint.none = function(rotation, delta) { - if (rotation !== undefined) { - return rotation + delta; - } else { - return undefined; - } -}; - - -/** - * @param {number} n N. - * @return {ol.RotationConstraintType} Rotation constraint. - */ -ol.RotationConstraint.createSnapToN = function(n) { - var theta = 2 * Math.PI / n; - return ( - /** - * @param {number|undefined} rotation Rotation. - * @param {number} delta Delta. - * @return {number|undefined} Rotation. - */ - function(rotation, delta) { - if (rotation !== undefined) { - rotation = Math.floor((rotation + delta) / theta + 0.5) * theta; - return rotation; - } else { - return undefined; - } - }); -}; - - -/** - * @param {number=} opt_tolerance Tolerance. - * @return {ol.RotationConstraintType} Rotation constraint. - */ -ol.RotationConstraint.createSnapToZero = function(opt_tolerance) { - var tolerance = opt_tolerance || ol.math.toRadians(5); - return ( - /** - * @param {number|undefined} rotation Rotation. - * @param {number} delta Delta. - * @return {number|undefined} Rotation. - */ - function(rotation, delta) { - if (rotation !== undefined) { - if (Math.abs(rotation + delta) <= tolerance) { - return 0; - } else { - return rotation + delta; - } - } else { - return undefined; - } - }); -}; - -goog.provide('ol.ViewHint'); - -/** - * @enum {number} - */ -ol.ViewHint = { - ANIMATING: 0, - INTERACTING: 1 -}; - -goog.provide('ol.ViewProperty'); - -/** - * @enum {string} - */ -ol.ViewProperty = { - CENTER: 'center', - RESOLUTION: 'resolution', - ROTATION: 'rotation' -}; - -goog.provide('ol.string'); - -/** - * @param {number} number Number to be formatted - * @param {number} width The desired width - * @param {number=} opt_precision Precision of the output string (i.e. number of decimal places) - * @returns {string} Formatted string -*/ -ol.string.padNumber = function(number, width, opt_precision) { - var numberString = opt_precision !== undefined ? number.toFixed(opt_precision) : '' + number; - var decimal = numberString.indexOf('.'); - decimal = decimal === -1 ? numberString.length : decimal; - return decimal > width ? numberString : new Array(1 + width - decimal).join('0') + numberString; -}; - -/** - * Adapted from https://github.com/omichelsen/compare-versions/blob/master/index.js - * @param {string|number} v1 First version - * @param {string|number} v2 Second version - * @returns {number} Value - */ -ol.string.compareVersions = function(v1, v2) { - var s1 = ('' + v1).split('.'); - var s2 = ('' + v2).split('.'); - - for (var i = 0; i < Math.max(s1.length, s2.length); i++) { - var n1 = parseInt(s1[i] || '0', 10); - var n2 = parseInt(s2[i] || '0', 10); - - if (n1 > n2) { - return 1; - } - if (n2 > n1) { - return -1; - } - } - - return 0; -}; - -goog.provide('ol.coordinate'); - -goog.require('ol.math'); -goog.require('ol.string'); - - -/** - * Add `delta` to `coordinate`. `coordinate` is modified in place and returned - * by the function. - * - * Example: - * - * var coord = [7.85, 47.983333]; - * ol.coordinate.add(coord, [-2, 4]); - * // coord is now [5.85, 51.983333] - * - * @param {ol.Coordinate} coordinate Coordinate. - * @param {ol.Coordinate} delta Delta. - * @return {ol.Coordinate} The input coordinate adjusted by the given delta. - * @api - */ -ol.coordinate.add = function(coordinate, delta) { - coordinate[0] += delta[0]; - coordinate[1] += delta[1]; - return coordinate; -}; - - -/** - * Calculates the point closest to the passed coordinate on the passed circle. - * - * @param {ol.Coordinate} coordinate The coordinate. - * @param {ol.geom.Circle} circle The circle. - * @return {ol.Coordinate} Closest point on the circumference - */ -ol.coordinate.closestOnCircle = function(coordinate, circle) { - var r = circle.getRadius(); - var center = circle.getCenter(); - var x0 = center[0]; - var y0 = center[1]; - var x1 = coordinate[0]; - var y1 = coordinate[1]; - - var dx = x1 - x0; - var dy = y1 - y0; - if (dx === 0 && dy === 0) { - dx = 1; - } - var d = Math.sqrt(dx * dx + dy * dy); - - var x, y; - - x = x0 + r * dx / d; - y = y0 + r * dy / d; - - return [x, y]; -}; - - -/** - * Calculates the point closest to the passed coordinate on the passed segment. - * This is the foot of the perpendicular of the coordinate to the segment when - * the foot is on the segment, or the closest segment coordinate when the foot - * is outside the segment. - * - * @param {ol.Coordinate} coordinate The coordinate. - * @param {Array.<ol.Coordinate>} segment The two coordinates of the segment. - * @return {ol.Coordinate} The foot of the perpendicular of the coordinate to - * the segment. - */ -ol.coordinate.closestOnSegment = function(coordinate, segment) { - var x0 = coordinate[0]; - var y0 = coordinate[1]; - var start = segment[0]; - var end = segment[1]; - var x1 = start[0]; - var y1 = start[1]; - var x2 = end[0]; - var y2 = end[1]; - var dx = x2 - x1; - var dy = y2 - y1; - var along = (dx === 0 && dy === 0) ? 0 : - ((dx * (x0 - x1)) + (dy * (y0 - y1))) / ((dx * dx + dy * dy) || 0); - var x, y; - if (along <= 0) { - x = x1; - y = y1; - } else if (along >= 1) { - x = x2; - y = y2; - } else { - x = x1 + along * dx; - y = y1 + along * dy; - } - return [x, y]; -}; - - -/** - * Returns a {@link ol.CoordinateFormatType} function that can be used to format - * a {ol.Coordinate} to a string. - * - * Example without specifying the fractional digits: - * - * var coord = [7.85, 47.983333]; - * var stringifyFunc = ol.coordinate.createStringXY(); - * var out = stringifyFunc(coord); - * // out is now '8, 48' - * - * Example with explicitly specifying 2 fractional digits: - * - * var coord = [7.85, 47.983333]; - * var stringifyFunc = ol.coordinate.createStringXY(2); - * var out = stringifyFunc(coord); - * // out is now '7.85, 47.98' - * - * @param {number=} opt_fractionDigits The number of digits to include - * after the decimal point. Default is `0`. - * @return {ol.CoordinateFormatType} Coordinate format. - * @api - */ -ol.coordinate.createStringXY = function(opt_fractionDigits) { - return ( - /** - * @param {ol.Coordinate|undefined} coordinate Coordinate. - * @return {string} String XY. - */ - function(coordinate) { - return ol.coordinate.toStringXY(coordinate, opt_fractionDigits); - }); -}; - - -/** - * @param {string} hemispheres Hemispheres. - * @param {number} degrees Degrees. - * @param {number=} opt_fractionDigits The number of digits to include - * after the decimal point. Default is `0`. - * @return {string} String. - */ -ol.coordinate.degreesToStringHDMS = function(hemispheres, degrees, opt_fractionDigits) { - var normalizedDegrees = ol.math.modulo(degrees + 180, 360) - 180; - var x = Math.abs(3600 * normalizedDegrees); - var dflPrecision = opt_fractionDigits || 0; - var precision = Math.pow(10, dflPrecision); - - var deg = Math.floor(x / 3600); - var min = Math.floor((x - deg * 3600) / 60); - var sec = x - (deg * 3600) - (min * 60); - sec = Math.ceil(sec * precision) / precision; - - if (sec >= 60) { - sec = 0; - min += 1; - } - - if (min >= 60) { - min = 0; - deg += 1; - } - - return deg + '\u00b0 ' + ol.string.padNumber(min, 2) + '\u2032 ' + - ol.string.padNumber(sec, 2, dflPrecision) + '\u2033' + - (normalizedDegrees == 0 ? '' : ' ' + hemispheres.charAt(normalizedDegrees < 0 ? 1 : 0)); -}; - - -/** - * Transforms the given {@link ol.Coordinate} to a string using the given string - * template. The strings `{x}` and `{y}` in the template will be replaced with - * the first and second coordinate values respectively. - * - * Example without specifying the fractional digits: - * - * var coord = [7.85, 47.983333]; - * var template = 'Coordinate is ({x}|{y}).'; - * var out = ol.coordinate.format(coord, template); - * // out is now 'Coordinate is (8|48).' - * - * Example explicitly specifying the fractional digits: - * - * var coord = [7.85, 47.983333]; - * var template = 'Coordinate is ({x}|{y}).'; - * var out = ol.coordinate.format(coord, template, 2); - * // out is now 'Coordinate is (7.85|47.98).' - * - * @param {ol.Coordinate|undefined} coordinate Coordinate. - * @param {string} template A template string with `{x}` and `{y}` placeholders - * that will be replaced by first and second coordinate values. - * @param {number=} opt_fractionDigits The number of digits to include - * after the decimal point. Default is `0`. - * @return {string} Formatted coordinate. - * @api - */ -ol.coordinate.format = function(coordinate, template, opt_fractionDigits) { - if (coordinate) { - return template - .replace('{x}', coordinate[0].toFixed(opt_fractionDigits)) - .replace('{y}', coordinate[1].toFixed(opt_fractionDigits)); - } else { - return ''; - } -}; - - -/** - * @param {ol.Coordinate} coordinate1 First coordinate. - * @param {ol.Coordinate} coordinate2 Second coordinate. - * @return {boolean} Whether the passed coordinates are equal. - */ -ol.coordinate.equals = function(coordinate1, coordinate2) { - var equals = true; - for (var i = coordinate1.length - 1; i >= 0; --i) { - if (coordinate1[i] != coordinate2[i]) { - equals = false; - break; - } - } - return equals; -}; - - -/** - * Rotate `coordinate` by `angle`. `coordinate` is modified in place and - * returned by the function. - * - * Example: - * - * var coord = [7.85, 47.983333]; - * var rotateRadians = Math.PI / 2; // 90 degrees - * ol.coordinate.rotate(coord, rotateRadians); - * // coord is now [-47.983333, 7.85] - * - * @param {ol.Coordinate} coordinate Coordinate. - * @param {number} angle Angle in radian. - * @return {ol.Coordinate} Coordinate. - * @api - */ -ol.coordinate.rotate = function(coordinate, angle) { - var cosAngle = Math.cos(angle); - var sinAngle = Math.sin(angle); - var x = coordinate[0] * cosAngle - coordinate[1] * sinAngle; - var y = coordinate[1] * cosAngle + coordinate[0] * sinAngle; - coordinate[0] = x; - coordinate[1] = y; - return coordinate; -}; - - -/** - * Scale `coordinate` by `scale`. `coordinate` is modified in place and returned - * by the function. - * - * Example: - * - * var coord = [7.85, 47.983333]; - * var scale = 1.2; - * ol.coordinate.scale(coord, scale); - * // coord is now [9.42, 57.5799996] - * - * @param {ol.Coordinate} coordinate Coordinate. - * @param {number} scale Scale factor. - * @return {ol.Coordinate} Coordinate. - */ -ol.coordinate.scale = function(coordinate, scale) { - coordinate[0] *= scale; - coordinate[1] *= scale; - return coordinate; -}; - - -/** - * Subtract `delta` to `coordinate`. `coordinate` is modified in place and - * returned by the function. - * - * @param {ol.Coordinate} coordinate Coordinate. - * @param {ol.Coordinate} delta Delta. - * @return {ol.Coordinate} Coordinate. - */ -ol.coordinate.sub = function(coordinate, delta) { - coordinate[0] -= delta[0]; - coordinate[1] -= delta[1]; - return coordinate; -}; - - -/** - * @param {ol.Coordinate} coord1 First coordinate. - * @param {ol.Coordinate} coord2 Second coordinate. - * @return {number} Squared distance between coord1 and coord2. - */ -ol.coordinate.squaredDistance = function(coord1, coord2) { - var dx = coord1[0] - coord2[0]; - var dy = coord1[1] - coord2[1]; - return dx * dx + dy * dy; -}; - - -/** - * @param {ol.Coordinate} coord1 First coordinate. - * @param {ol.Coordinate} coord2 Second coordinate. - * @return {number} Distance between coord1 and coord2. - */ -ol.coordinate.distance = function(coord1, coord2) { - return Math.sqrt(ol.coordinate.squaredDistance(coord1, coord2)); -}; - - -/** - * Calculate the squared distance from a coordinate to a line segment. - * - * @param {ol.Coordinate} coordinate Coordinate of the point. - * @param {Array.<ol.Coordinate>} segment Line segment (2 coordinates). - * @return {number} Squared distance from the point to the line segment. - */ -ol.coordinate.squaredDistanceToSegment = function(coordinate, segment) { - return ol.coordinate.squaredDistance(coordinate, - ol.coordinate.closestOnSegment(coordinate, segment)); -}; - - -/** - * Format a geographic coordinate with the hemisphere, degrees, minutes, and - * seconds. - * - * Example without specifying fractional digits: - * - * var coord = [7.85, 47.983333]; - * var out = ol.coordinate.toStringHDMS(coord); - * // out is now '47° 58′ 60″ N 7° 50′ 60″ E' - * - * Example explicitly specifying 1 fractional digit: - * - * var coord = [7.85, 47.983333]; - * var out = ol.coordinate.toStringHDMS(coord, 1); - * // out is now '47° 58′ 60.0″ N 7° 50′ 60.0″ E' - * - * @param {ol.Coordinate|undefined} coordinate Coordinate. - * @param {number=} opt_fractionDigits The number of digits to include - * after the decimal point. Default is `0`. - * @return {string} Hemisphere, degrees, minutes and seconds. - * @api - */ -ol.coordinate.toStringHDMS = function(coordinate, opt_fractionDigits) { - if (coordinate) { - return ol.coordinate.degreesToStringHDMS('NS', coordinate[1], opt_fractionDigits) + ' ' + - ol.coordinate.degreesToStringHDMS('EW', coordinate[0], opt_fractionDigits); - } else { - return ''; - } -}; - - -/** - * Format a coordinate as a comma delimited string. - * - * Example without specifying fractional digits: - * - * var coord = [7.85, 47.983333]; - * var out = ol.coordinate.toStringXY(coord); - * // out is now '8, 48' - * - * Example explicitly specifying 1 fractional digit: - * - * var coord = [7.85, 47.983333]; - * var out = ol.coordinate.toStringXY(coord, 1); - * // out is now '7.8, 48.0' - * - * @param {ol.Coordinate|undefined} coordinate Coordinate. - * @param {number=} opt_fractionDigits The number of digits to include - * after the decimal point. Default is `0`. - * @return {string} XY. - * @api - */ -ol.coordinate.toStringXY = function(coordinate, opt_fractionDigits) { - return ol.coordinate.format(coordinate, '{x}, {y}', opt_fractionDigits); -}; - -goog.provide('ol.easing'); - - -/** - * Start slow and speed up. - * @param {number} t Input between 0 and 1. - * @return {number} Output between 0 and 1. - * @api - */ -ol.easing.easeIn = function(t) { - return Math.pow(t, 3); -}; - - -/** - * Start fast and slow down. - * @param {number} t Input between 0 and 1. - * @return {number} Output between 0 and 1. - * @api - */ -ol.easing.easeOut = function(t) { - return 1 - ol.easing.easeIn(1 - t); -}; - - -/** - * Start slow, speed up, and then slow down again. - * @param {number} t Input between 0 and 1. - * @return {number} Output between 0 and 1. - * @api - */ -ol.easing.inAndOut = function(t) { - return 3 * t * t - 2 * t * t * t; -}; - - -/** - * Maintain a constant speed over time. - * @param {number} t Input between 0 and 1. - * @return {number} Output between 0 and 1. - * @api - */ -ol.easing.linear = function(t) { - return t; -}; - - -/** - * Start slow, speed up, and at the very end slow down again. This has the - * same general behavior as {@link ol.easing.inAndOut}, but the final slowdown - * is delayed. - * @param {number} t Input between 0 and 1. - * @return {number} Output between 0 and 1. - * @api - */ -ol.easing.upAndDown = function(t) { - if (t < 0.5) { - return ol.easing.inAndOut(2 * t); - } else { - return 1 - ol.easing.inAndOut(2 * (t - 0.5)); - } -}; - -goog.provide('ol.geom.GeometryLayout'); - - -/** - * The coordinate layout for geometries, indicating whether a 3rd or 4th z ('Z') - * or measure ('M') coordinate is available. Supported values are `'XY'`, - * `'XYZ'`, `'XYM'`, `'XYZM'`. - * @enum {string} - */ -ol.geom.GeometryLayout = { - XY: 'XY', - XYZ: 'XYZ', - XYM: 'XYM', - XYZM: 'XYZM' -}; - -goog.provide('ol.functions'); - -/** - * Always returns true. - * @returns {boolean} true. - */ -ol.functions.TRUE = function() { - return true; -}; - -/** - * Always returns false. - * @returns {boolean} false. - */ -ol.functions.FALSE = function() { - return false; -}; - -goog.provide('ol.geom.flat.transform'); - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {ol.Transform} transform Transform. - * @param {Array.<number>=} opt_dest Destination. - * @return {Array.<number>} Transformed coordinates. - */ -ol.geom.flat.transform.transform2D = function(flatCoordinates, offset, end, stride, transform, opt_dest) { - var dest = opt_dest ? opt_dest : []; - var i = 0; - var j; - for (j = offset; j < end; j += stride) { - var x = flatCoordinates[j]; - var y = flatCoordinates[j + 1]; - dest[i++] = transform[0] * x + transform[2] * y + transform[4]; - dest[i++] = transform[1] * x + transform[3] * y + transform[5]; - } - if (opt_dest && dest.length != i) { - dest.length = i; - } - return dest; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {number} angle Angle. - * @param {Array.<number>} anchor Rotation anchor point. - * @param {Array.<number>=} opt_dest Destination. - * @return {Array.<number>} Transformed coordinates. - */ -ol.geom.flat.transform.rotate = function(flatCoordinates, offset, end, stride, angle, anchor, opt_dest) { - var dest = opt_dest ? opt_dest : []; - var cos = Math.cos(angle); - var sin = Math.sin(angle); - var anchorX = anchor[0]; - var anchorY = anchor[1]; - var i = 0; - for (var j = offset; j < end; j += stride) { - var deltaX = flatCoordinates[j] - anchorX; - var deltaY = flatCoordinates[j + 1] - anchorY; - dest[i++] = anchorX + deltaX * cos - deltaY * sin; - dest[i++] = anchorY + deltaX * sin + deltaY * cos; - for (var k = j + 2; k < j + stride; ++k) { - dest[i++] = flatCoordinates[k]; - } - } - if (opt_dest && dest.length != i) { - dest.length = i; - } - return dest; -}; - - -/** - * Scale the coordinates. - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {number} sx Scale factor in the x-direction. - * @param {number} sy Scale factor in the y-direction. - * @param {Array.<number>} anchor Scale anchor point. - * @param {Array.<number>=} opt_dest Destination. - * @return {Array.<number>} Transformed coordinates. - */ -ol.geom.flat.transform.scale = function(flatCoordinates, offset, end, stride, sx, sy, anchor, opt_dest) { - var dest = opt_dest ? opt_dest : []; - var anchorX = anchor[0]; - var anchorY = anchor[1]; - var i = 0; - for (var j = offset; j < end; j += stride) { - var deltaX = flatCoordinates[j] - anchorX; - var deltaY = flatCoordinates[j + 1] - anchorY; - dest[i++] = anchorX + sx * deltaX; - dest[i++] = anchorY + sy * deltaY; - for (var k = j + 2; k < j + stride; ++k) { - dest[i++] = flatCoordinates[k]; - } - } - if (opt_dest && dest.length != i) { - dest.length = i; - } - return dest; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {number} deltaX Delta X. - * @param {number} deltaY Delta Y. - * @param {Array.<number>=} opt_dest Destination. - * @return {Array.<number>} Transformed coordinates. - */ -ol.geom.flat.transform.translate = function(flatCoordinates, offset, end, stride, deltaX, deltaY, opt_dest) { - var dest = opt_dest ? opt_dest : []; - var i = 0; - var j, k; - for (j = offset; j < end; j += stride) { - dest[i++] = flatCoordinates[j] + deltaX; - dest[i++] = flatCoordinates[j + 1] + deltaY; - for (k = j + 2; k < j + stride; ++k) { - dest[i++] = flatCoordinates[k]; - } - } - if (opt_dest && dest.length != i) { - dest.length = i; - } - return dest; -}; - -goog.provide('ol.transform'); - -goog.require('ol.asserts'); - - -/** - * Collection of affine 2d transformation functions. The functions work on an - * array of 6 elements. The element order is compatible with the [SVGMatrix - * interface](https://developer.mozilla.org/en-US/docs/Web/API/SVGMatrix) and is - * a subset (elements a to f) of a 3x3 martrix: - * ``` - * [ a c e ] - * [ b d f ] - * [ 0 0 1 ] - * ``` - */ - - -/** - * @private - * @type {ol.Transform} - */ -ol.transform.tmp_ = new Array(6); - - -/** - * Create an identity transform. - * @return {!ol.Transform} Identity transform. - */ -ol.transform.create = function() { - return [1, 0, 0, 1, 0, 0]; -}; - - -/** - * Resets the given transform to an identity transform. - * @param {!ol.Transform} transform Transform. - * @return {!ol.Transform} Transform. - */ -ol.transform.reset = function(transform) { - return ol.transform.set(transform, 1, 0, 0, 1, 0, 0); -}; - - -/** - * Multiply the underlying matrices of two transforms and return the result in - * the first transform. - * @param {!ol.Transform} transform1 Transform parameters of matrix 1. - * @param {!ol.Transform} transform2 Transform parameters of matrix 2. - * @return {!ol.Transform} transform1 multiplied with transform2. - */ -ol.transform.multiply = function(transform1, transform2) { - var a1 = transform1[0]; - var b1 = transform1[1]; - var c1 = transform1[2]; - var d1 = transform1[3]; - var e1 = transform1[4]; - var f1 = transform1[5]; - var a2 = transform2[0]; - var b2 = transform2[1]; - var c2 = transform2[2]; - var d2 = transform2[3]; - var e2 = transform2[4]; - var f2 = transform2[5]; - - transform1[0] = a1 * a2 + c1 * b2; - transform1[1] = b1 * a2 + d1 * b2; - transform1[2] = a1 * c2 + c1 * d2; - transform1[3] = b1 * c2 + d1 * d2; - transform1[4] = a1 * e2 + c1 * f2 + e1; - transform1[5] = b1 * e2 + d1 * f2 + f1; - - return transform1; -}; - -/** - * Set the transform components a-f on a given transform. - * @param {!ol.Transform} transform Transform. - * @param {number} a The a component of the transform. - * @param {number} b The b component of the transform. - * @param {number} c The c component of the transform. - * @param {number} d The d component of the transform. - * @param {number} e The e component of the transform. - * @param {number} f The f component of the transform. - * @return {!ol.Transform} Matrix with transform applied. - */ -ol.transform.set = function(transform, a, b, c, d, e, f) { - transform[0] = a; - transform[1] = b; - transform[2] = c; - transform[3] = d; - transform[4] = e; - transform[5] = f; - return transform; -}; - - -/** - * Set transform on one matrix from another matrix. - * @param {!ol.Transform} transform1 Matrix to set transform to. - * @param {!ol.Transform} transform2 Matrix to set transform from. - * @return {!ol.Transform} transform1 with transform from transform2 applied. - */ -ol.transform.setFromArray = function(transform1, transform2) { - transform1[0] = transform2[0]; - transform1[1] = transform2[1]; - transform1[2] = transform2[2]; - transform1[3] = transform2[3]; - transform1[4] = transform2[4]; - transform1[5] = transform2[5]; - return transform1; -}; - - -/** - * Transforms the given coordinate with the given transform returning the - * resulting, transformed coordinate. The coordinate will be modified in-place. - * - * @param {ol.Transform} transform The transformation. - * @param {ol.Coordinate|ol.Pixel} coordinate The coordinate to transform. - * @return {ol.Coordinate|ol.Pixel} return coordinate so that operations can be - * chained together. - */ -ol.transform.apply = function(transform, coordinate) { - var x = coordinate[0], y = coordinate[1]; - coordinate[0] = transform[0] * x + transform[2] * y + transform[4]; - coordinate[1] = transform[1] * x + transform[3] * y + transform[5]; - return coordinate; -}; - - -/** - * Applies rotation to the given transform. - * @param {!ol.Transform} transform Transform. - * @param {number} angle Angle in radians. - * @return {!ol.Transform} The rotated transform. - */ -ol.transform.rotate = function(transform, angle) { - var cos = Math.cos(angle); - var sin = Math.sin(angle); - return ol.transform.multiply(transform, - ol.transform.set(ol.transform.tmp_, cos, sin, -sin, cos, 0, 0)); -}; - - -/** - * Applies scale to a given transform. - * @param {!ol.Transform} transform Transform. - * @param {number} x Scale factor x. - * @param {number} y Scale factor y. - * @return {!ol.Transform} The scaled transform. - */ -ol.transform.scale = function(transform, x, y) { - return ol.transform.multiply(transform, - ol.transform.set(ol.transform.tmp_, x, 0, 0, y, 0, 0)); -}; - - -/** - * Applies translation to the given transform. - * @param {!ol.Transform} transform Transform. - * @param {number} dx Translation x. - * @param {number} dy Translation y. - * @return {!ol.Transform} The translated transform. - */ -ol.transform.translate = function(transform, dx, dy) { - return ol.transform.multiply(transform, - ol.transform.set(ol.transform.tmp_, 1, 0, 0, 1, dx, dy)); -}; - - -/** - * Creates a composite transform given an initial translation, scale, rotation, and - * final translation (in that order only, not commutative). - * @param {!ol.Transform} transform The transform (will be modified in place). - * @param {number} dx1 Initial translation x. - * @param {number} dy1 Initial translation y. - * @param {number} sx Scale factor x. - * @param {number} sy Scale factor y. - * @param {number} angle Rotation (in counter-clockwise radians). - * @param {number} dx2 Final translation x. - * @param {number} dy2 Final translation y. - * @return {!ol.Transform} The composite transform. - */ -ol.transform.compose = function(transform, dx1, dy1, sx, sy, angle, dx2, dy2) { - var sin = Math.sin(angle); - var cos = Math.cos(angle); - transform[0] = sx * cos; - transform[1] = sy * sin; - transform[2] = -sx * sin; - transform[3] = sy * cos; - transform[4] = dx2 * sx * cos - dy2 * sx * sin + dx1; - transform[5] = dx2 * sy * sin + dy2 * sy * cos + dy1; - return transform; -}; - - -/** - * Invert the given transform. - * @param {!ol.Transform} transform Transform. - * @return {!ol.Transform} Inverse of the transform. - */ -ol.transform.invert = function(transform) { - var det = ol.transform.determinant(transform); - ol.asserts.assert(det !== 0, 32); // Transformation matrix cannot be inverted - - var a = transform[0]; - var b = transform[1]; - var c = transform[2]; - var d = transform[3]; - var e = transform[4]; - var f = transform[5]; - - transform[0] = d / det; - transform[1] = -b / det; - transform[2] = -c / det; - transform[3] = a / det; - transform[4] = (c * f - d * e) / det; - transform[5] = -(a * f - b * e) / det; - - return transform; -}; - - -/** - * Returns the determinant of the given matrix. - * @param {!ol.Transform} mat Matrix. - * @return {number} Determinant. - */ -ol.transform.determinant = function(mat) { - return mat[0] * mat[3] - mat[1] * mat[2]; -}; - -goog.provide('ol.geom.Geometry'); - -goog.require('ol'); -goog.require('ol.Object'); -goog.require('ol.extent'); -goog.require('ol.functions'); -goog.require('ol.geom.flat.transform'); -goog.require('ol.proj'); -goog.require('ol.proj.Units'); -goog.require('ol.transform'); - - -/** - * @classdesc - * Abstract base class; normally only used for creating subclasses and not - * instantiated in apps. - * Base class for vector geometries. - * - * To get notified of changes to the geometry, register a listener for the - * generic `change` event on your geometry instance. - * - * @constructor - * @abstract - * @extends {ol.Object} - * @api - */ -ol.geom.Geometry = function() { - - ol.Object.call(this); - - /** - * @private - * @type {ol.Extent} - */ - this.extent_ = ol.extent.createEmpty(); - - /** - * @private - * @type {number} - */ - this.extentRevision_ = -1; - - /** - * @protected - * @type {Object.<string, ol.geom.Geometry>} - */ - this.simplifiedGeometryCache = {}; - - /** - * @protected - * @type {number} - */ - this.simplifiedGeometryMaxMinSquaredTolerance = 0; - - /** - * @protected - * @type {number} - */ - this.simplifiedGeometryRevision = 0; - - /** - * @private - * @type {ol.Transform} - */ - this.tmpTransform_ = ol.transform.create(); - -}; -ol.inherits(ol.geom.Geometry, ol.Object); - - -/** - * Make a complete copy of the geometry. - * @abstract - * @return {!ol.geom.Geometry} Clone. - */ -ol.geom.Geometry.prototype.clone = function() {}; - - -/** - * @abstract - * @param {number} x X. - * @param {number} y Y. - * @param {ol.Coordinate} closestPoint Closest point. - * @param {number} minSquaredDistance Minimum squared distance. - * @return {number} Minimum squared distance. - */ -ol.geom.Geometry.prototype.closestPointXY = function(x, y, closestPoint, minSquaredDistance) {}; - - -/** - * Return the closest point of the geometry to the passed point as - * {@link ol.Coordinate coordinate}. - * @param {ol.Coordinate} point Point. - * @param {ol.Coordinate=} opt_closestPoint Closest point. - * @return {ol.Coordinate} Closest point. - * @api - */ -ol.geom.Geometry.prototype.getClosestPoint = function(point, opt_closestPoint) { - var closestPoint = opt_closestPoint ? opt_closestPoint : [NaN, NaN]; - this.closestPointXY(point[0], point[1], closestPoint, Infinity); - return closestPoint; -}; - - -/** - * Returns true if this geometry includes the specified coordinate. If the - * coordinate is on the boundary of the geometry, returns false. - * @param {ol.Coordinate} coordinate Coordinate. - * @return {boolean} Contains coordinate. - * @api - */ -ol.geom.Geometry.prototype.intersectsCoordinate = function(coordinate) { - return this.containsXY(coordinate[0], coordinate[1]); -}; - - -/** - * @abstract - * @param {ol.Extent} extent Extent. - * @protected - * @return {ol.Extent} extent Extent. - */ -ol.geom.Geometry.prototype.computeExtent = function(extent) {}; - - -/** - * @param {number} x X. - * @param {number} y Y. - * @return {boolean} Contains (x, y). - */ -ol.geom.Geometry.prototype.containsXY = ol.functions.FALSE; - - -/** - * Get the extent of the geometry. - * @param {ol.Extent=} opt_extent Extent. - * @return {ol.Extent} extent Extent. - * @api - */ -ol.geom.Geometry.prototype.getExtent = function(opt_extent) { - if (this.extentRevision_ != this.getRevision()) { - this.extent_ = this.computeExtent(this.extent_); - this.extentRevision_ = this.getRevision(); - } - return ol.extent.returnOrUpdate(this.extent_, opt_extent); -}; - - -/** - * Rotate the geometry around a given coordinate. This modifies the geometry - * coordinates in place. - * @abstract - * @param {number} angle Rotation angle in radians. - * @param {ol.Coordinate} anchor The rotation center. - * @api - */ -ol.geom.Geometry.prototype.rotate = function(angle, anchor) {}; - - -/** - * Scale the geometry (with an optional origin). This modifies the geometry - * coordinates in place. - * @abstract - * @param {number} sx The scaling factor in the x-direction. - * @param {number=} opt_sy The scaling factor in the y-direction (defaults to - * sx). - * @param {ol.Coordinate=} opt_anchor The scale origin (defaults to the center - * of the geometry extent). - * @api - */ -ol.geom.Geometry.prototype.scale = function(sx, opt_sy, opt_anchor) {}; - - -/** - * Create a simplified version of this geometry. For linestrings, this uses - * the the {@link - * https://en.wikipedia.org/wiki/Ramer-Douglas-Peucker_algorithm - * Douglas Peucker} algorithm. For polygons, a quantization-based - * simplification is used to preserve topology. - * @function - * @param {number} tolerance The tolerance distance for simplification. - * @return {ol.geom.Geometry} A new, simplified version of the original - * geometry. - * @api - */ -ol.geom.Geometry.prototype.simplify = function(tolerance) { - return this.getSimplifiedGeometry(tolerance * tolerance); -}; - - -/** - * Create a simplified version of this geometry using the Douglas Peucker - * algorithm. - * @see https://en.wikipedia.org/wiki/Ramer-Douglas-Peucker_algorithm - * @abstract - * @param {number} squaredTolerance Squared tolerance. - * @return {ol.geom.Geometry} Simplified geometry. - */ -ol.geom.Geometry.prototype.getSimplifiedGeometry = function(squaredTolerance) {}; - - -/** - * Get the type of this geometry. - * @abstract - * @return {ol.geom.GeometryType} Geometry type. - */ -ol.geom.Geometry.prototype.getType = function() {}; - - -/** - * Apply a transform function to each coordinate of the geometry. - * The geometry is modified in place. - * If you do not want the geometry modified in place, first `clone()` it and - * then use this function on the clone. - * @abstract - * @param {ol.TransformFunction} transformFn Transform. - */ -ol.geom.Geometry.prototype.applyTransform = function(transformFn) {}; - - -/** - * Test if the geometry and the passed extent intersect. - * @abstract - * @param {ol.Extent} extent Extent. - * @return {boolean} `true` if the geometry and the extent intersect. - */ -ol.geom.Geometry.prototype.intersectsExtent = function(extent) {}; - - -/** - * Translate the geometry. This modifies the geometry coordinates in place. If - * instead you want a new geometry, first `clone()` this geometry. - * @abstract - * @param {number} deltaX Delta X. - * @param {number} deltaY Delta Y. - */ -ol.geom.Geometry.prototype.translate = function(deltaX, deltaY) {}; - - -/** - * Transform each coordinate of the geometry from one coordinate reference - * system to another. The geometry is modified in place. - * For example, a line will be transformed to a line and a circle to a circle. - * If you do not want the geometry modified in place, first `clone()` it and - * then use this function on the clone. - * - * @param {ol.ProjectionLike} source The current projection. Can be a - * string identifier or a {@link ol.proj.Projection} object. - * @param {ol.ProjectionLike} destination The desired projection. Can be a - * string identifier or a {@link ol.proj.Projection} object. - * @return {ol.geom.Geometry} This geometry. Note that original geometry is - * modified in place. - * @api - */ -ol.geom.Geometry.prototype.transform = function(source, destination) { - var tmpTransform = this.tmpTransform_; - source = ol.proj.get(source); - var transformFn = source.getUnits() == ol.proj.Units.TILE_PIXELS ? - function(inCoordinates, outCoordinates, stride) { - var pixelExtent = source.getExtent(); - var projectedExtent = source.getWorldExtent(); - var scale = ol.extent.getHeight(projectedExtent) / ol.extent.getHeight(pixelExtent); - ol.transform.compose(tmpTransform, - projectedExtent[0], projectedExtent[3], - scale, -scale, 0, - 0, 0); - ol.geom.flat.transform.transform2D(inCoordinates, 0, inCoordinates.length, stride, - tmpTransform, outCoordinates); - return ol.proj.getTransform(source, destination)(inCoordinates, outCoordinates, stride); - } : - ol.proj.getTransform(source, destination); - this.applyTransform(transformFn); - return this; -}; - -goog.provide('ol.geom.SimpleGeometry'); - -goog.require('ol'); -goog.require('ol.functions'); -goog.require('ol.extent'); -goog.require('ol.geom.Geometry'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.flat.transform'); -goog.require('ol.obj'); - - -/** - * @classdesc - * Abstract base class; only used for creating subclasses; do not instantiate - * in apps, as cannot be rendered. - * - * @constructor - * @abstract - * @extends {ol.geom.Geometry} - * @api - */ -ol.geom.SimpleGeometry = function() { - - ol.geom.Geometry.call(this); - - /** - * @protected - * @type {ol.geom.GeometryLayout} - */ - this.layout = ol.geom.GeometryLayout.XY; - - /** - * @protected - * @type {number} - */ - this.stride = 2; - - /** - * @protected - * @type {Array.<number>} - */ - this.flatCoordinates = null; - -}; -ol.inherits(ol.geom.SimpleGeometry, ol.geom.Geometry); - - -/** - * @param {number} stride Stride. - * @private - * @return {ol.geom.GeometryLayout} layout Layout. - */ -ol.geom.SimpleGeometry.getLayoutForStride_ = function(stride) { - var layout; - if (stride == 2) { - layout = ol.geom.GeometryLayout.XY; - } else if (stride == 3) { - layout = ol.geom.GeometryLayout.XYZ; - } else if (stride == 4) { - layout = ol.geom.GeometryLayout.XYZM; - } - return /** @type {ol.geom.GeometryLayout} */ (layout); -}; - - -/** - * @param {ol.geom.GeometryLayout} layout Layout. - * @return {number} Stride. - */ -ol.geom.SimpleGeometry.getStrideForLayout = function(layout) { - var stride; - if (layout == ol.geom.GeometryLayout.XY) { - stride = 2; - } else if (layout == ol.geom.GeometryLayout.XYZ || layout == ol.geom.GeometryLayout.XYM) { - stride = 3; - } else if (layout == ol.geom.GeometryLayout.XYZM) { - stride = 4; - } - return /** @type {number} */ (stride); -}; - - -/** - * @inheritDoc - */ -ol.geom.SimpleGeometry.prototype.containsXY = ol.functions.FALSE; - - -/** - * @inheritDoc - */ -ol.geom.SimpleGeometry.prototype.computeExtent = function(extent) { - return ol.extent.createOrUpdateFromFlatCoordinates( - this.flatCoordinates, 0, this.flatCoordinates.length, this.stride, - extent); -}; - - -/** - * @abstract - * @return {Array} Coordinates. - */ -ol.geom.SimpleGeometry.prototype.getCoordinates = function() {}; - - -/** - * Return the first coordinate of the geometry. - * @return {ol.Coordinate} First coordinate. - * @api - */ -ol.geom.SimpleGeometry.prototype.getFirstCoordinate = function() { - return this.flatCoordinates.slice(0, this.stride); -}; - - -/** - * @return {Array.<number>} Flat coordinates. - */ -ol.geom.SimpleGeometry.prototype.getFlatCoordinates = function() { - return this.flatCoordinates; -}; - - -/** - * Return the last coordinate of the geometry. - * @return {ol.Coordinate} Last point. - * @api - */ -ol.geom.SimpleGeometry.prototype.getLastCoordinate = function() { - return this.flatCoordinates.slice(this.flatCoordinates.length - this.stride); -}; - - -/** - * Return the {@link ol.geom.GeometryLayout layout} of the geometry. - * @return {ol.geom.GeometryLayout} Layout. - * @api - */ -ol.geom.SimpleGeometry.prototype.getLayout = function() { - return this.layout; -}; - - -/** - * @inheritDoc - */ -ol.geom.SimpleGeometry.prototype.getSimplifiedGeometry = function(squaredTolerance) { - if (this.simplifiedGeometryRevision != this.getRevision()) { - ol.obj.clear(this.simplifiedGeometryCache); - this.simplifiedGeometryMaxMinSquaredTolerance = 0; - this.simplifiedGeometryRevision = this.getRevision(); - } - // If squaredTolerance is negative or if we know that simplification will not - // have any effect then just return this. - if (squaredTolerance < 0 || - (this.simplifiedGeometryMaxMinSquaredTolerance !== 0 && - squaredTolerance <= this.simplifiedGeometryMaxMinSquaredTolerance)) { - return this; - } - var key = squaredTolerance.toString(); - if (this.simplifiedGeometryCache.hasOwnProperty(key)) { - return this.simplifiedGeometryCache[key]; - } else { - var simplifiedGeometry = - this.getSimplifiedGeometryInternal(squaredTolerance); - var simplifiedFlatCoordinates = simplifiedGeometry.getFlatCoordinates(); - if (simplifiedFlatCoordinates.length < this.flatCoordinates.length) { - this.simplifiedGeometryCache[key] = simplifiedGeometry; - return simplifiedGeometry; - } else { - // Simplification did not actually remove any coordinates. We now know - // that any calls to getSimplifiedGeometry with a squaredTolerance less - // than or equal to the current squaredTolerance will also not have any - // effect. This allows us to short circuit simplification (saving CPU - // cycles) and prevents the cache of simplified geometries from filling - // up with useless identical copies of this geometry (saving memory). - this.simplifiedGeometryMaxMinSquaredTolerance = squaredTolerance; - return this; - } - } -}; - - -/** - * @param {number} squaredTolerance Squared tolerance. - * @return {ol.geom.SimpleGeometry} Simplified geometry. - * @protected - */ -ol.geom.SimpleGeometry.prototype.getSimplifiedGeometryInternal = function(squaredTolerance) { - return this; -}; - - -/** - * @return {number} Stride. - */ -ol.geom.SimpleGeometry.prototype.getStride = function() { - return this.stride; -}; - - -/** - * @param {ol.geom.GeometryLayout} layout Layout. - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @protected - */ -ol.geom.SimpleGeometry.prototype.setFlatCoordinatesInternal = function(layout, flatCoordinates) { - this.stride = ol.geom.SimpleGeometry.getStrideForLayout(layout); - this.layout = layout; - this.flatCoordinates = flatCoordinates; -}; - - -/** - * @abstract - * @param {Array} coordinates Coordinates. - * @param {ol.geom.GeometryLayout=} opt_layout Layout. - */ -ol.geom.SimpleGeometry.prototype.setCoordinates = function(coordinates, opt_layout) {}; - - -/** - * @param {ol.geom.GeometryLayout|undefined} layout Layout. - * @param {Array} coordinates Coordinates. - * @param {number} nesting Nesting. - * @protected - */ -ol.geom.SimpleGeometry.prototype.setLayout = function(layout, coordinates, nesting) { - /** @type {number} */ - var stride; - if (layout) { - stride = ol.geom.SimpleGeometry.getStrideForLayout(layout); - } else { - var i; - for (i = 0; i < nesting; ++i) { - if (coordinates.length === 0) { - this.layout = ol.geom.GeometryLayout.XY; - this.stride = 2; - return; - } else { - coordinates = /** @type {Array} */ (coordinates[0]); - } - } - stride = coordinates.length; - layout = ol.geom.SimpleGeometry.getLayoutForStride_(stride); - } - this.layout = layout; - this.stride = stride; -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.SimpleGeometry.prototype.applyTransform = function(transformFn) { - if (this.flatCoordinates) { - transformFn(this.flatCoordinates, this.flatCoordinates, this.stride); - this.changed(); - } -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.SimpleGeometry.prototype.rotate = function(angle, anchor) { - var flatCoordinates = this.getFlatCoordinates(); - if (flatCoordinates) { - var stride = this.getStride(); - ol.geom.flat.transform.rotate( - flatCoordinates, 0, flatCoordinates.length, - stride, angle, anchor, flatCoordinates); - this.changed(); - } -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.SimpleGeometry.prototype.scale = function(sx, opt_sy, opt_anchor) { - var sy = opt_sy; - if (sy === undefined) { - sy = sx; - } - var anchor = opt_anchor; - if (!anchor) { - anchor = ol.extent.getCenter(this.getExtent()); - } - var flatCoordinates = this.getFlatCoordinates(); - if (flatCoordinates) { - var stride = this.getStride(); - ol.geom.flat.transform.scale( - flatCoordinates, 0, flatCoordinates.length, - stride, sx, sy, anchor, flatCoordinates); - this.changed(); - } -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.SimpleGeometry.prototype.translate = function(deltaX, deltaY) { - var flatCoordinates = this.getFlatCoordinates(); - if (flatCoordinates) { - var stride = this.getStride(); - ol.geom.flat.transform.translate( - flatCoordinates, 0, flatCoordinates.length, stride, - deltaX, deltaY, flatCoordinates); - this.changed(); - } -}; - - -/** - * @param {ol.geom.SimpleGeometry} simpleGeometry Simple geometry. - * @param {ol.Transform} transform Transform. - * @param {Array.<number>=} opt_dest Destination. - * @return {Array.<number>} Transformed flat coordinates. - */ -ol.geom.SimpleGeometry.transform2D = function(simpleGeometry, transform, opt_dest) { - var flatCoordinates = simpleGeometry.getFlatCoordinates(); - if (!flatCoordinates) { - return null; - } else { - var stride = simpleGeometry.getStride(); - return ol.geom.flat.transform.transform2D( - flatCoordinates, 0, flatCoordinates.length, stride, - transform, opt_dest); - } -}; - -goog.provide('ol.geom.flat.area'); - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @return {number} Area. - */ -ol.geom.flat.area.linearRing = function(flatCoordinates, offset, end, stride) { - var twiceArea = 0; - var x1 = flatCoordinates[end - stride]; - var y1 = flatCoordinates[end - stride + 1]; - for (; offset < end; offset += stride) { - var x2 = flatCoordinates[offset]; - var y2 = flatCoordinates[offset + 1]; - twiceArea += y1 * x2 - x1 * y2; - x1 = x2; - y1 = y2; - } - return twiceArea / 2; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<number>} ends Ends. - * @param {number} stride Stride. - * @return {number} Area. - */ -ol.geom.flat.area.linearRings = function(flatCoordinates, offset, ends, stride) { - var area = 0; - var i, ii; - for (i = 0, ii = ends.length; i < ii; ++i) { - var end = ends[i]; - area += ol.geom.flat.area.linearRing(flatCoordinates, offset, end, stride); - offset = end; - } - return area; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<Array.<number>>} endss Endss. - * @param {number} stride Stride. - * @return {number} Area. - */ -ol.geom.flat.area.linearRingss = function(flatCoordinates, offset, endss, stride) { - var area = 0; - var i, ii; - for (i = 0, ii = endss.length; i < ii; ++i) { - var ends = endss[i]; - area += - ol.geom.flat.area.linearRings(flatCoordinates, offset, ends, stride); - offset = ends[ends.length - 1]; - } - return area; -}; - -goog.provide('ol.geom.flat.closest'); - -goog.require('ol.math'); - - -/** - * Returns the point on the 2D line segment flatCoordinates[offset1] to - * flatCoordinates[offset2] that is closest to the point (x, y). Extra - * dimensions are linearly interpolated. - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset1 Offset 1. - * @param {number} offset2 Offset 2. - * @param {number} stride Stride. - * @param {number} x X. - * @param {number} y Y. - * @param {Array.<number>} closestPoint Closest point. - */ -ol.geom.flat.closest.point = function(flatCoordinates, offset1, offset2, stride, x, y, closestPoint) { - var x1 = flatCoordinates[offset1]; - var y1 = flatCoordinates[offset1 + 1]; - var dx = flatCoordinates[offset2] - x1; - var dy = flatCoordinates[offset2 + 1] - y1; - var i, offset; - if (dx === 0 && dy === 0) { - offset = offset1; - } else { - var t = ((x - x1) * dx + (y - y1) * dy) / (dx * dx + dy * dy); - if (t > 1) { - offset = offset2; - } else if (t > 0) { - for (i = 0; i < stride; ++i) { - closestPoint[i] = ol.math.lerp(flatCoordinates[offset1 + i], - flatCoordinates[offset2 + i], t); - } - closestPoint.length = stride; - return; - } else { - offset = offset1; - } - } - for (i = 0; i < stride; ++i) { - closestPoint[i] = flatCoordinates[offset + i]; - } - closestPoint.length = stride; -}; - - -/** - * Return the squared of the largest distance between any pair of consecutive - * coordinates. - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {number} maxSquaredDelta Max squared delta. - * @return {number} Max squared delta. - */ -ol.geom.flat.closest.getMaxSquaredDelta = function(flatCoordinates, offset, end, stride, maxSquaredDelta) { - var x1 = flatCoordinates[offset]; - var y1 = flatCoordinates[offset + 1]; - for (offset += stride; offset < end; offset += stride) { - var x2 = flatCoordinates[offset]; - var y2 = flatCoordinates[offset + 1]; - var squaredDelta = ol.math.squaredDistance(x1, y1, x2, y2); - if (squaredDelta > maxSquaredDelta) { - maxSquaredDelta = squaredDelta; - } - x1 = x2; - y1 = y2; - } - return maxSquaredDelta; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<number>} ends Ends. - * @param {number} stride Stride. - * @param {number} maxSquaredDelta Max squared delta. - * @return {number} Max squared delta. - */ -ol.geom.flat.closest.getsMaxSquaredDelta = function(flatCoordinates, offset, ends, stride, maxSquaredDelta) { - var i, ii; - for (i = 0, ii = ends.length; i < ii; ++i) { - var end = ends[i]; - maxSquaredDelta = ol.geom.flat.closest.getMaxSquaredDelta( - flatCoordinates, offset, end, stride, maxSquaredDelta); - offset = end; - } - return maxSquaredDelta; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<Array.<number>>} endss Endss. - * @param {number} stride Stride. - * @param {number} maxSquaredDelta Max squared delta. - * @return {number} Max squared delta. - */ -ol.geom.flat.closest.getssMaxSquaredDelta = function(flatCoordinates, offset, endss, stride, maxSquaredDelta) { - var i, ii; - for (i = 0, ii = endss.length; i < ii; ++i) { - var ends = endss[i]; - maxSquaredDelta = ol.geom.flat.closest.getsMaxSquaredDelta( - flatCoordinates, offset, ends, stride, maxSquaredDelta); - offset = ends[ends.length - 1]; - } - return maxSquaredDelta; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {number} maxDelta Max delta. - * @param {boolean} isRing Is ring. - * @param {number} x X. - * @param {number} y Y. - * @param {Array.<number>} closestPoint Closest point. - * @param {number} minSquaredDistance Minimum squared distance. - * @param {Array.<number>=} opt_tmpPoint Temporary point object. - * @return {number} Minimum squared distance. - */ -ol.geom.flat.closest.getClosestPoint = function(flatCoordinates, offset, end, - stride, maxDelta, isRing, x, y, closestPoint, minSquaredDistance, - opt_tmpPoint) { - if (offset == end) { - return minSquaredDistance; - } - var i, squaredDistance; - if (maxDelta === 0) { - // All points are identical, so just test the first point. - squaredDistance = ol.math.squaredDistance( - x, y, flatCoordinates[offset], flatCoordinates[offset + 1]); - if (squaredDistance < minSquaredDistance) { - for (i = 0; i < stride; ++i) { - closestPoint[i] = flatCoordinates[offset + i]; - } - closestPoint.length = stride; - return squaredDistance; - } else { - return minSquaredDistance; - } - } - var tmpPoint = opt_tmpPoint ? opt_tmpPoint : [NaN, NaN]; - var index = offset + stride; - while (index < end) { - ol.geom.flat.closest.point( - flatCoordinates, index - stride, index, stride, x, y, tmpPoint); - squaredDistance = ol.math.squaredDistance(x, y, tmpPoint[0], tmpPoint[1]); - if (squaredDistance < minSquaredDistance) { - minSquaredDistance = squaredDistance; - for (i = 0; i < stride; ++i) { - closestPoint[i] = tmpPoint[i]; - } - closestPoint.length = stride; - index += stride; - } else { - // Skip ahead multiple points, because we know that all the skipped - // points cannot be any closer than the closest point we have found so - // far. We know this because we know how close the current point is, how - // close the closest point we have found so far is, and the maximum - // distance between consecutive points. For example, if we're currently - // at distance 10, the best we've found so far is 3, and that the maximum - // distance between consecutive points is 2, then we'll need to skip at - // least (10 - 3) / 2 == 3 (rounded down) points to have any chance of - // finding a closer point. We use Math.max(..., 1) to ensure that we - // always advance at least one point, to avoid an infinite loop. - index += stride * Math.max( - ((Math.sqrt(squaredDistance) - - Math.sqrt(minSquaredDistance)) / maxDelta) | 0, 1); - } - } - if (isRing) { - // Check the closing segment. - ol.geom.flat.closest.point( - flatCoordinates, end - stride, offset, stride, x, y, tmpPoint); - squaredDistance = ol.math.squaredDistance(x, y, tmpPoint[0], tmpPoint[1]); - if (squaredDistance < minSquaredDistance) { - minSquaredDistance = squaredDistance; - for (i = 0; i < stride; ++i) { - closestPoint[i] = tmpPoint[i]; - } - closestPoint.length = stride; - } - } - return minSquaredDistance; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<number>} ends Ends. - * @param {number} stride Stride. - * @param {number} maxDelta Max delta. - * @param {boolean} isRing Is ring. - * @param {number} x X. - * @param {number} y Y. - * @param {Array.<number>} closestPoint Closest point. - * @param {number} minSquaredDistance Minimum squared distance. - * @param {Array.<number>=} opt_tmpPoint Temporary point object. - * @return {number} Minimum squared distance. - */ -ol.geom.flat.closest.getsClosestPoint = function(flatCoordinates, offset, ends, - stride, maxDelta, isRing, x, y, closestPoint, minSquaredDistance, - opt_tmpPoint) { - var tmpPoint = opt_tmpPoint ? opt_tmpPoint : [NaN, NaN]; - var i, ii; - for (i = 0, ii = ends.length; i < ii; ++i) { - var end = ends[i]; - minSquaredDistance = ol.geom.flat.closest.getClosestPoint( - flatCoordinates, offset, end, stride, - maxDelta, isRing, x, y, closestPoint, minSquaredDistance, tmpPoint); - offset = end; - } - return minSquaredDistance; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<Array.<number>>} endss Endss. - * @param {number} stride Stride. - * @param {number} maxDelta Max delta. - * @param {boolean} isRing Is ring. - * @param {number} x X. - * @param {number} y Y. - * @param {Array.<number>} closestPoint Closest point. - * @param {number} minSquaredDistance Minimum squared distance. - * @param {Array.<number>=} opt_tmpPoint Temporary point object. - * @return {number} Minimum squared distance. - */ -ol.geom.flat.closest.getssClosestPoint = function(flatCoordinates, offset, - endss, stride, maxDelta, isRing, x, y, closestPoint, minSquaredDistance, - opt_tmpPoint) { - var tmpPoint = opt_tmpPoint ? opt_tmpPoint : [NaN, NaN]; - var i, ii; - for (i = 0, ii = endss.length; i < ii; ++i) { - var ends = endss[i]; - minSquaredDistance = ol.geom.flat.closest.getsClosestPoint( - flatCoordinates, offset, ends, stride, - maxDelta, isRing, x, y, closestPoint, minSquaredDistance, tmpPoint); - offset = ends[ends.length - 1]; - } - return minSquaredDistance; -}; - -goog.provide('ol.geom.flat.deflate'); - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {ol.Coordinate} coordinate Coordinate. - * @param {number} stride Stride. - * @return {number} offset Offset. - */ -ol.geom.flat.deflate.coordinate = function(flatCoordinates, offset, coordinate, stride) { - var i, ii; - for (i = 0, ii = coordinate.length; i < ii; ++i) { - flatCoordinates[offset++] = coordinate[i]; - } - return offset; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<ol.Coordinate>} coordinates Coordinates. - * @param {number} stride Stride. - * @return {number} offset Offset. - */ -ol.geom.flat.deflate.coordinates = function(flatCoordinates, offset, coordinates, stride) { - var i, ii; - for (i = 0, ii = coordinates.length; i < ii; ++i) { - var coordinate = coordinates[i]; - var j; - for (j = 0; j < stride; ++j) { - flatCoordinates[offset++] = coordinate[j]; - } - } - return offset; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<Array.<ol.Coordinate>>} coordinatess Coordinatess. - * @param {number} stride Stride. - * @param {Array.<number>=} opt_ends Ends. - * @return {Array.<number>} Ends. - */ -ol.geom.flat.deflate.coordinatess = function(flatCoordinates, offset, coordinatess, stride, opt_ends) { - var ends = opt_ends ? opt_ends : []; - var i = 0; - var j, jj; - for (j = 0, jj = coordinatess.length; j < jj; ++j) { - var end = ol.geom.flat.deflate.coordinates( - flatCoordinates, offset, coordinatess[j], stride); - ends[i++] = end; - offset = end; - } - ends.length = i; - return ends; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<Array.<Array.<ol.Coordinate>>>} coordinatesss Coordinatesss. - * @param {number} stride Stride. - * @param {Array.<Array.<number>>=} opt_endss Endss. - * @return {Array.<Array.<number>>} Endss. - */ -ol.geom.flat.deflate.coordinatesss = function(flatCoordinates, offset, coordinatesss, stride, opt_endss) { - var endss = opt_endss ? opt_endss : []; - var i = 0; - var j, jj; - for (j = 0, jj = coordinatesss.length; j < jj; ++j) { - var ends = ol.geom.flat.deflate.coordinatess( - flatCoordinates, offset, coordinatesss[j], stride, endss[i]); - endss[i++] = ends; - offset = ends[ends.length - 1]; - } - endss.length = i; - return endss; -}; - -goog.provide('ol.geom.flat.inflate'); - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {Array.<ol.Coordinate>=} opt_coordinates Coordinates. - * @return {Array.<ol.Coordinate>} Coordinates. - */ -ol.geom.flat.inflate.coordinates = function(flatCoordinates, offset, end, stride, opt_coordinates) { - var coordinates = opt_coordinates !== undefined ? opt_coordinates : []; - var i = 0; - var j; - for (j = offset; j < end; j += stride) { - coordinates[i++] = flatCoordinates.slice(j, j + stride); - } - coordinates.length = i; - return coordinates; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<number>} ends Ends. - * @param {number} stride Stride. - * @param {Array.<Array.<ol.Coordinate>>=} opt_coordinatess Coordinatess. - * @return {Array.<Array.<ol.Coordinate>>} Coordinatess. - */ -ol.geom.flat.inflate.coordinatess = function(flatCoordinates, offset, ends, stride, opt_coordinatess) { - var coordinatess = opt_coordinatess !== undefined ? opt_coordinatess : []; - var i = 0; - var j, jj; - for (j = 0, jj = ends.length; j < jj; ++j) { - var end = ends[j]; - coordinatess[i++] = ol.geom.flat.inflate.coordinates( - flatCoordinates, offset, end, stride, coordinatess[i]); - offset = end; - } - coordinatess.length = i; - return coordinatess; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<Array.<number>>} endss Endss. - * @param {number} stride Stride. - * @param {Array.<Array.<Array.<ol.Coordinate>>>=} opt_coordinatesss - * Coordinatesss. - * @return {Array.<Array.<Array.<ol.Coordinate>>>} Coordinatesss. - */ -ol.geom.flat.inflate.coordinatesss = function(flatCoordinates, offset, endss, stride, opt_coordinatesss) { - var coordinatesss = opt_coordinatesss !== undefined ? opt_coordinatesss : []; - var i = 0; - var j, jj; - for (j = 0, jj = endss.length; j < jj; ++j) { - var ends = endss[j]; - coordinatesss[i++] = ol.geom.flat.inflate.coordinatess( - flatCoordinates, offset, ends, stride, coordinatesss[i]); - offset = ends[ends.length - 1]; - } - coordinatesss.length = i; - return coordinatesss; -}; - -// Based on simplify-js https://github.com/mourner/simplify-js -// Copyright (c) 2012, Vladimir Agafonkin -// All rights reserved. -// -// Redistribution and use in source and binary forms, with or without -// modification, are permitted provided that the following conditions are met: -// -// 1. Redistributions of source code must retain the above copyright notice, -// this list of conditions and the following disclaimer. -// -// 2. Redistributions in binary form must reproduce the above copyright -// notice, this list of conditions and the following disclaimer in the -// documentation and/or other materials provided with the distribution. -// -// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" -// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -// ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE -// LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR -// CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF -// SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS -// INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN -// CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) -// ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE -// POSSIBILITY OF SUCH DAMAGE. - -goog.provide('ol.geom.flat.simplify'); - -goog.require('ol.math'); - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {number} squaredTolerance Squared tolerance. - * @param {boolean} highQuality Highest quality. - * @param {Array.<number>=} opt_simplifiedFlatCoordinates Simplified flat - * coordinates. - * @return {Array.<number>} Simplified line string. - */ -ol.geom.flat.simplify.lineString = function(flatCoordinates, offset, end, - stride, squaredTolerance, highQuality, opt_simplifiedFlatCoordinates) { - var simplifiedFlatCoordinates = opt_simplifiedFlatCoordinates !== undefined ? - opt_simplifiedFlatCoordinates : []; - if (!highQuality) { - end = ol.geom.flat.simplify.radialDistance(flatCoordinates, offset, end, - stride, squaredTolerance, - simplifiedFlatCoordinates, 0); - flatCoordinates = simplifiedFlatCoordinates; - offset = 0; - stride = 2; - } - simplifiedFlatCoordinates.length = ol.geom.flat.simplify.douglasPeucker( - flatCoordinates, offset, end, stride, squaredTolerance, - simplifiedFlatCoordinates, 0); - return simplifiedFlatCoordinates; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {number} squaredTolerance Squared tolerance. - * @param {Array.<number>} simplifiedFlatCoordinates Simplified flat - * coordinates. - * @param {number} simplifiedOffset Simplified offset. - * @return {number} Simplified offset. - */ -ol.geom.flat.simplify.douglasPeucker = function(flatCoordinates, offset, end, - stride, squaredTolerance, simplifiedFlatCoordinates, simplifiedOffset) { - var n = (end - offset) / stride; - if (n < 3) { - for (; offset < end; offset += stride) { - simplifiedFlatCoordinates[simplifiedOffset++] = - flatCoordinates[offset]; - simplifiedFlatCoordinates[simplifiedOffset++] = - flatCoordinates[offset + 1]; - } - return simplifiedOffset; - } - /** @type {Array.<number>} */ - var markers = new Array(n); - markers[0] = 1; - markers[n - 1] = 1; - /** @type {Array.<number>} */ - var stack = [offset, end - stride]; - var index = 0; - var i; - while (stack.length > 0) { - var last = stack.pop(); - var first = stack.pop(); - var maxSquaredDistance = 0; - var x1 = flatCoordinates[first]; - var y1 = flatCoordinates[first + 1]; - var x2 = flatCoordinates[last]; - var y2 = flatCoordinates[last + 1]; - for (i = first + stride; i < last; i += stride) { - var x = flatCoordinates[i]; - var y = flatCoordinates[i + 1]; - var squaredDistance = ol.math.squaredSegmentDistance( - x, y, x1, y1, x2, y2); - if (squaredDistance > maxSquaredDistance) { - index = i; - maxSquaredDistance = squaredDistance; - } - } - if (maxSquaredDistance > squaredTolerance) { - markers[(index - offset) / stride] = 1; - if (first + stride < index) { - stack.push(first, index); - } - if (index + stride < last) { - stack.push(index, last); - } - } - } - for (i = 0; i < n; ++i) { - if (markers[i]) { - simplifiedFlatCoordinates[simplifiedOffset++] = - flatCoordinates[offset + i * stride]; - simplifiedFlatCoordinates[simplifiedOffset++] = - flatCoordinates[offset + i * stride + 1]; - } - } - return simplifiedOffset; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<number>} ends Ends. - * @param {number} stride Stride. - * @param {number} squaredTolerance Squared tolerance. - * @param {Array.<number>} simplifiedFlatCoordinates Simplified flat - * coordinates. - * @param {number} simplifiedOffset Simplified offset. - * @param {Array.<number>} simplifiedEnds Simplified ends. - * @return {number} Simplified offset. - */ -ol.geom.flat.simplify.douglasPeuckers = function(flatCoordinates, offset, - ends, stride, squaredTolerance, simplifiedFlatCoordinates, - simplifiedOffset, simplifiedEnds) { - var i, ii; - for (i = 0, ii = ends.length; i < ii; ++i) { - var end = ends[i]; - simplifiedOffset = ol.geom.flat.simplify.douglasPeucker( - flatCoordinates, offset, end, stride, squaredTolerance, - simplifiedFlatCoordinates, simplifiedOffset); - simplifiedEnds.push(simplifiedOffset); - offset = end; - } - return simplifiedOffset; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<Array.<number>>} endss Endss. - * @param {number} stride Stride. - * @param {number} squaredTolerance Squared tolerance. - * @param {Array.<number>} simplifiedFlatCoordinates Simplified flat - * coordinates. - * @param {number} simplifiedOffset Simplified offset. - * @param {Array.<Array.<number>>} simplifiedEndss Simplified endss. - * @return {number} Simplified offset. - */ -ol.geom.flat.simplify.douglasPeuckerss = function( - flatCoordinates, offset, endss, stride, squaredTolerance, - simplifiedFlatCoordinates, simplifiedOffset, simplifiedEndss) { - var i, ii; - for (i = 0, ii = endss.length; i < ii; ++i) { - var ends = endss[i]; - var simplifiedEnds = []; - simplifiedOffset = ol.geom.flat.simplify.douglasPeuckers( - flatCoordinates, offset, ends, stride, squaredTolerance, - simplifiedFlatCoordinates, simplifiedOffset, simplifiedEnds); - simplifiedEndss.push(simplifiedEnds); - offset = ends[ends.length - 1]; - } - return simplifiedOffset; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {number} squaredTolerance Squared tolerance. - * @param {Array.<number>} simplifiedFlatCoordinates Simplified flat - * coordinates. - * @param {number} simplifiedOffset Simplified offset. - * @return {number} Simplified offset. - */ -ol.geom.flat.simplify.radialDistance = function(flatCoordinates, offset, end, - stride, squaredTolerance, simplifiedFlatCoordinates, simplifiedOffset) { - if (end <= offset + stride) { - // zero or one point, no simplification possible, so copy and return - for (; offset < end; offset += stride) { - simplifiedFlatCoordinates[simplifiedOffset++] = flatCoordinates[offset]; - simplifiedFlatCoordinates[simplifiedOffset++] = - flatCoordinates[offset + 1]; - } - return simplifiedOffset; - } - var x1 = flatCoordinates[offset]; - var y1 = flatCoordinates[offset + 1]; - // copy first point - simplifiedFlatCoordinates[simplifiedOffset++] = x1; - simplifiedFlatCoordinates[simplifiedOffset++] = y1; - var x2 = x1; - var y2 = y1; - for (offset += stride; offset < end; offset += stride) { - x2 = flatCoordinates[offset]; - y2 = flatCoordinates[offset + 1]; - if (ol.math.squaredDistance(x1, y1, x2, y2) > squaredTolerance) { - // copy point at offset - simplifiedFlatCoordinates[simplifiedOffset++] = x2; - simplifiedFlatCoordinates[simplifiedOffset++] = y2; - x1 = x2; - y1 = y2; - } - } - if (x2 != x1 || y2 != y1) { - // copy last point - simplifiedFlatCoordinates[simplifiedOffset++] = x2; - simplifiedFlatCoordinates[simplifiedOffset++] = y2; - } - return simplifiedOffset; -}; - - -/** - * @param {number} value Value. - * @param {number} tolerance Tolerance. - * @return {number} Rounded value. - */ -ol.geom.flat.simplify.snap = function(value, tolerance) { - return tolerance * Math.round(value / tolerance); -}; - - -/** - * Simplifies a line string using an algorithm designed by Tim Schaub. - * Coordinates are snapped to the nearest value in a virtual grid and - * consecutive duplicate coordinates are discarded. This effectively preserves - * topology as the simplification of any subsection of a line string is - * independent of the rest of the line string. This means that, for examples, - * the common edge between two polygons will be simplified to the same line - * string independently in both polygons. This implementation uses a single - * pass over the coordinates and eliminates intermediate collinear points. - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {number} tolerance Tolerance. - * @param {Array.<number>} simplifiedFlatCoordinates Simplified flat - * coordinates. - * @param {number} simplifiedOffset Simplified offset. - * @return {number} Simplified offset. - */ -ol.geom.flat.simplify.quantize = function(flatCoordinates, offset, end, stride, - tolerance, simplifiedFlatCoordinates, simplifiedOffset) { - // do nothing if the line is empty - if (offset == end) { - return simplifiedOffset; - } - // snap the first coordinate (P1) - var x1 = ol.geom.flat.simplify.snap(flatCoordinates[offset], tolerance); - var y1 = ol.geom.flat.simplify.snap(flatCoordinates[offset + 1], tolerance); - offset += stride; - // add the first coordinate to the output - simplifiedFlatCoordinates[simplifiedOffset++] = x1; - simplifiedFlatCoordinates[simplifiedOffset++] = y1; - // find the next coordinate that does not snap to the same value as the first - // coordinate (P2) - var x2, y2; - do { - x2 = ol.geom.flat.simplify.snap(flatCoordinates[offset], tolerance); - y2 = ol.geom.flat.simplify.snap(flatCoordinates[offset + 1], tolerance); - offset += stride; - if (offset == end) { - // all coordinates snap to the same value, the line collapses to a point - // push the last snapped value anyway to ensure that the output contains - // at least two points - // FIXME should we really return at least two points anyway? - simplifiedFlatCoordinates[simplifiedOffset++] = x2; - simplifiedFlatCoordinates[simplifiedOffset++] = y2; - return simplifiedOffset; - } - } while (x2 == x1 && y2 == y1); - while (offset < end) { - var x3, y3; - // snap the next coordinate (P3) - x3 = ol.geom.flat.simplify.snap(flatCoordinates[offset], tolerance); - y3 = ol.geom.flat.simplify.snap(flatCoordinates[offset + 1], tolerance); - offset += stride; - // skip P3 if it is equal to P2 - if (x3 == x2 && y3 == y2) { - continue; - } - // calculate the delta between P1 and P2 - var dx1 = x2 - x1; - var dy1 = y2 - y1; - // calculate the delta between P3 and P1 - var dx2 = x3 - x1; - var dy2 = y3 - y1; - // if P1, P2, and P3 are colinear and P3 is further from P1 than P2 is from - // P1 in the same direction then P2 is on the straight line between P1 and - // P3 - if ((dx1 * dy2 == dy1 * dx2) && - ((dx1 < 0 && dx2 < dx1) || dx1 == dx2 || (dx1 > 0 && dx2 > dx1)) && - ((dy1 < 0 && dy2 < dy1) || dy1 == dy2 || (dy1 > 0 && dy2 > dy1))) { - // discard P2 and set P2 = P3 - x2 = x3; - y2 = y3; - continue; - } - // either P1, P2, and P3 are not colinear, or they are colinear but P3 is - // between P3 and P1 or on the opposite half of the line to P2. add P2, - // and continue with P1 = P2 and P2 = P3 - simplifiedFlatCoordinates[simplifiedOffset++] = x2; - simplifiedFlatCoordinates[simplifiedOffset++] = y2; - x1 = x2; - y1 = y2; - x2 = x3; - y2 = y3; - } - // add the last point (P2) - simplifiedFlatCoordinates[simplifiedOffset++] = x2; - simplifiedFlatCoordinates[simplifiedOffset++] = y2; - return simplifiedOffset; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<number>} ends Ends. - * @param {number} stride Stride. - * @param {number} tolerance Tolerance. - * @param {Array.<number>} simplifiedFlatCoordinates Simplified flat - * coordinates. - * @param {number} simplifiedOffset Simplified offset. - * @param {Array.<number>} simplifiedEnds Simplified ends. - * @return {number} Simplified offset. - */ -ol.geom.flat.simplify.quantizes = function( - flatCoordinates, offset, ends, stride, - tolerance, - simplifiedFlatCoordinates, simplifiedOffset, simplifiedEnds) { - var i, ii; - for (i = 0, ii = ends.length; i < ii; ++i) { - var end = ends[i]; - simplifiedOffset = ol.geom.flat.simplify.quantize( - flatCoordinates, offset, end, stride, - tolerance, - simplifiedFlatCoordinates, simplifiedOffset); - simplifiedEnds.push(simplifiedOffset); - offset = end; - } - return simplifiedOffset; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<Array.<number>>} endss Endss. - * @param {number} stride Stride. - * @param {number} tolerance Tolerance. - * @param {Array.<number>} simplifiedFlatCoordinates Simplified flat - * coordinates. - * @param {number} simplifiedOffset Simplified offset. - * @param {Array.<Array.<number>>} simplifiedEndss Simplified endss. - * @return {number} Simplified offset. - */ -ol.geom.flat.simplify.quantizess = function( - flatCoordinates, offset, endss, stride, - tolerance, - simplifiedFlatCoordinates, simplifiedOffset, simplifiedEndss) { - var i, ii; - for (i = 0, ii = endss.length; i < ii; ++i) { - var ends = endss[i]; - var simplifiedEnds = []; - simplifiedOffset = ol.geom.flat.simplify.quantizes( - flatCoordinates, offset, ends, stride, - tolerance, - simplifiedFlatCoordinates, simplifiedOffset, simplifiedEnds); - simplifiedEndss.push(simplifiedEnds); - offset = ends[ends.length - 1]; - } - return simplifiedOffset; -}; - -goog.provide('ol.geom.LinearRing'); - -goog.require('ol'); -goog.require('ol.extent'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.SimpleGeometry'); -goog.require('ol.geom.flat.area'); -goog.require('ol.geom.flat.closest'); -goog.require('ol.geom.flat.deflate'); -goog.require('ol.geom.flat.inflate'); -goog.require('ol.geom.flat.simplify'); - - -/** - * @classdesc - * Linear ring geometry. Only used as part of polygon; cannot be rendered - * on its own. - * - * @constructor - * @extends {ol.geom.SimpleGeometry} - * @param {Array.<ol.Coordinate>} coordinates Coordinates. - * @param {ol.geom.GeometryLayout=} opt_layout Layout. - * @api - */ -ol.geom.LinearRing = function(coordinates, opt_layout) { - - ol.geom.SimpleGeometry.call(this); - - /** - * @private - * @type {number} - */ - this.maxDelta_ = -1; - - /** - * @private - * @type {number} - */ - this.maxDeltaRevision_ = -1; - - this.setCoordinates(coordinates, opt_layout); - -}; -ol.inherits(ol.geom.LinearRing, ol.geom.SimpleGeometry); - - -/** - * Make a complete copy of the geometry. - * @return {!ol.geom.LinearRing} Clone. - * @override - * @api - */ -ol.geom.LinearRing.prototype.clone = function() { - var linearRing = new ol.geom.LinearRing(null); - linearRing.setFlatCoordinates(this.layout, this.flatCoordinates.slice()); - return linearRing; -}; - - -/** - * @inheritDoc - */ -ol.geom.LinearRing.prototype.closestPointXY = function(x, y, closestPoint, minSquaredDistance) { - if (minSquaredDistance < - ol.extent.closestSquaredDistanceXY(this.getExtent(), x, y)) { - return minSquaredDistance; - } - if (this.maxDeltaRevision_ != this.getRevision()) { - this.maxDelta_ = Math.sqrt(ol.geom.flat.closest.getMaxSquaredDelta( - this.flatCoordinates, 0, this.flatCoordinates.length, this.stride, 0)); - this.maxDeltaRevision_ = this.getRevision(); - } - return ol.geom.flat.closest.getClosestPoint( - this.flatCoordinates, 0, this.flatCoordinates.length, this.stride, - this.maxDelta_, true, x, y, closestPoint, minSquaredDistance); -}; - - -/** - * Return the area of the linear ring on projected plane. - * @return {number} Area (on projected plane). - * @api - */ -ol.geom.LinearRing.prototype.getArea = function() { - return ol.geom.flat.area.linearRing( - this.flatCoordinates, 0, this.flatCoordinates.length, this.stride); -}; - - -/** - * Return the coordinates of the linear ring. - * @return {Array.<ol.Coordinate>} Coordinates. - * @override - * @api - */ -ol.geom.LinearRing.prototype.getCoordinates = function() { - return ol.geom.flat.inflate.coordinates( - this.flatCoordinates, 0, this.flatCoordinates.length, this.stride); -}; - - -/** - * @inheritDoc - */ -ol.geom.LinearRing.prototype.getSimplifiedGeometryInternal = function(squaredTolerance) { - var simplifiedFlatCoordinates = []; - simplifiedFlatCoordinates.length = ol.geom.flat.simplify.douglasPeucker( - this.flatCoordinates, 0, this.flatCoordinates.length, this.stride, - squaredTolerance, simplifiedFlatCoordinates, 0); - var simplifiedLinearRing = new ol.geom.LinearRing(null); - simplifiedLinearRing.setFlatCoordinates( - ol.geom.GeometryLayout.XY, simplifiedFlatCoordinates); - return simplifiedLinearRing; -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.LinearRing.prototype.getType = function() { - return ol.geom.GeometryType.LINEAR_RING; -}; - - -/** - * @inheritDoc - */ -ol.geom.LinearRing.prototype.intersectsExtent = function(extent) {}; - - -/** - * Set the coordinates of the linear ring. - * @param {Array.<ol.Coordinate>} coordinates Coordinates. - * @param {ol.geom.GeometryLayout=} opt_layout Layout. - * @override - * @api - */ -ol.geom.LinearRing.prototype.setCoordinates = function(coordinates, opt_layout) { - if (!coordinates) { - this.setFlatCoordinates(ol.geom.GeometryLayout.XY, null); - } else { - this.setLayout(opt_layout, coordinates, 1); - if (!this.flatCoordinates) { - this.flatCoordinates = []; - } - this.flatCoordinates.length = ol.geom.flat.deflate.coordinates( - this.flatCoordinates, 0, coordinates, this.stride); - this.changed(); - } -}; - - -/** - * @param {ol.geom.GeometryLayout} layout Layout. - * @param {Array.<number>} flatCoordinates Flat coordinates. - */ -ol.geom.LinearRing.prototype.setFlatCoordinates = function(layout, flatCoordinates) { - this.setFlatCoordinatesInternal(layout, flatCoordinates); - this.changed(); -}; - -goog.provide('ol.geom.Point'); - -goog.require('ol'); -goog.require('ol.extent'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.SimpleGeometry'); -goog.require('ol.geom.flat.deflate'); -goog.require('ol.math'); - - -/** - * @classdesc - * Point geometry. - * - * @constructor - * @extends {ol.geom.SimpleGeometry} - * @param {ol.Coordinate} coordinates Coordinates. - * @param {ol.geom.GeometryLayout=} opt_layout Layout. - * @api - */ -ol.geom.Point = function(coordinates, opt_layout) { - ol.geom.SimpleGeometry.call(this); - this.setCoordinates(coordinates, opt_layout); -}; -ol.inherits(ol.geom.Point, ol.geom.SimpleGeometry); - - -/** - * Make a complete copy of the geometry. - * @return {!ol.geom.Point} Clone. - * @override - * @api - */ -ol.geom.Point.prototype.clone = function() { - var point = new ol.geom.Point(null); - point.setFlatCoordinates(this.layout, this.flatCoordinates.slice()); - return point; -}; - - -/** - * @inheritDoc - */ -ol.geom.Point.prototype.closestPointXY = function(x, y, closestPoint, minSquaredDistance) { - var flatCoordinates = this.flatCoordinates; - var squaredDistance = ol.math.squaredDistance( - x, y, flatCoordinates[0], flatCoordinates[1]); - if (squaredDistance < minSquaredDistance) { - var stride = this.stride; - var i; - for (i = 0; i < stride; ++i) { - closestPoint[i] = flatCoordinates[i]; - } - closestPoint.length = stride; - return squaredDistance; - } else { - return minSquaredDistance; - } -}; - - -/** - * Return the coordinate of the point. - * @return {ol.Coordinate} Coordinates. - * @override - * @api - */ -ol.geom.Point.prototype.getCoordinates = function() { - return !this.flatCoordinates ? [] : this.flatCoordinates.slice(); -}; - - -/** - * @inheritDoc - */ -ol.geom.Point.prototype.computeExtent = function(extent) { - return ol.extent.createOrUpdateFromCoordinate(this.flatCoordinates, extent); -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.Point.prototype.getType = function() { - return ol.geom.GeometryType.POINT; -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.Point.prototype.intersectsExtent = function(extent) { - return ol.extent.containsXY(extent, - this.flatCoordinates[0], this.flatCoordinates[1]); -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.Point.prototype.setCoordinates = function(coordinates, opt_layout) { - if (!coordinates) { - this.setFlatCoordinates(ol.geom.GeometryLayout.XY, null); - } else { - this.setLayout(opt_layout, coordinates, 0); - if (!this.flatCoordinates) { - this.flatCoordinates = []; - } - this.flatCoordinates.length = ol.geom.flat.deflate.coordinate( - this.flatCoordinates, 0, coordinates, this.stride); - this.changed(); - } -}; - - -/** - * @param {ol.geom.GeometryLayout} layout Layout. - * @param {Array.<number>} flatCoordinates Flat coordinates. - */ -ol.geom.Point.prototype.setFlatCoordinates = function(layout, flatCoordinates) { - this.setFlatCoordinatesInternal(layout, flatCoordinates); - this.changed(); -}; - -goog.provide('ol.geom.flat.contains'); - -goog.require('ol.extent'); - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {ol.Extent} extent Extent. - * @return {boolean} Contains extent. - */ -ol.geom.flat.contains.linearRingContainsExtent = function(flatCoordinates, offset, end, stride, extent) { - var outside = ol.extent.forEachCorner(extent, - /** - * @param {ol.Coordinate} coordinate Coordinate. - * @return {boolean} Contains (x, y). - */ - function(coordinate) { - return !ol.geom.flat.contains.linearRingContainsXY(flatCoordinates, - offset, end, stride, coordinate[0], coordinate[1]); - }); - return !outside; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {number} x X. - * @param {number} y Y. - * @return {boolean} Contains (x, y). - */ -ol.geom.flat.contains.linearRingContainsXY = function(flatCoordinates, offset, end, stride, x, y) { - // http://geomalgorithms.com/a03-_inclusion.html - // Copyright 2000 softSurfer, 2012 Dan Sunday - // This code may be freely used and modified for any purpose - // providing that this copyright notice is included with it. - // SoftSurfer makes no warranty for this code, and cannot be held - // liable for any real or imagined damage resulting from its use. - // Users of this code must verify correctness for their application. - var wn = 0; - var x1 = flatCoordinates[end - stride]; - var y1 = flatCoordinates[end - stride + 1]; - for (; offset < end; offset += stride) { - var x2 = flatCoordinates[offset]; - var y2 = flatCoordinates[offset + 1]; - if (y1 <= y) { - if (y2 > y && ((x2 - x1) * (y - y1)) - ((x - x1) * (y2 - y1)) > 0) { - wn++; - } - } else if (y2 <= y && ((x2 - x1) * (y - y1)) - ((x - x1) * (y2 - y1)) < 0) { - wn--; - } - x1 = x2; - y1 = y2; - } - return wn !== 0; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<number>} ends Ends. - * @param {number} stride Stride. - * @param {number} x X. - * @param {number} y Y. - * @return {boolean} Contains (x, y). - */ -ol.geom.flat.contains.linearRingsContainsXY = function(flatCoordinates, offset, ends, stride, x, y) { - if (ends.length === 0) { - return false; - } - if (!ol.geom.flat.contains.linearRingContainsXY( - flatCoordinates, offset, ends[0], stride, x, y)) { - return false; - } - var i, ii; - for (i = 1, ii = ends.length; i < ii; ++i) { - if (ol.geom.flat.contains.linearRingContainsXY( - flatCoordinates, ends[i - 1], ends[i], stride, x, y)) { - return false; - } - } - return true; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<Array.<number>>} endss Endss. - * @param {number} stride Stride. - * @param {number} x X. - * @param {number} y Y. - * @return {boolean} Contains (x, y). - */ -ol.geom.flat.contains.linearRingssContainsXY = function(flatCoordinates, offset, endss, stride, x, y) { - if (endss.length === 0) { - return false; - } - var i, ii; - for (i = 0, ii = endss.length; i < ii; ++i) { - var ends = endss[i]; - if (ol.geom.flat.contains.linearRingsContainsXY( - flatCoordinates, offset, ends, stride, x, y)) { - return true; - } - offset = ends[ends.length - 1]; - } - return false; -}; - -goog.provide('ol.geom.flat.interiorpoint'); - -goog.require('ol.array'); -goog.require('ol.geom.flat.contains'); - - -/** - * Calculates a point that is likely to lie in the interior of the linear rings. - * Inspired by JTS's com.vividsolutions.jts.geom.Geometry#getInteriorPoint. - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<number>} ends Ends. - * @param {number} stride Stride. - * @param {Array.<number>} flatCenters Flat centers. - * @param {number} flatCentersOffset Flat center offset. - * @param {Array.<number>=} opt_dest Destination. - * @return {Array.<number>} Destination point as XYM coordinate, where M is the - * length of the horizontal intersection that the point belongs to. - */ -ol.geom.flat.interiorpoint.linearRings = function(flatCoordinates, offset, - ends, stride, flatCenters, flatCentersOffset, opt_dest) { - var i, ii, x, x1, x2, y1, y2; - var y = flatCenters[flatCentersOffset + 1]; - /** @type {Array.<number>} */ - var intersections = []; - // Calculate intersections with the horizontal line - var end = ends[0]; - x1 = flatCoordinates[end - stride]; - y1 = flatCoordinates[end - stride + 1]; - for (i = offset; i < end; i += stride) { - x2 = flatCoordinates[i]; - y2 = flatCoordinates[i + 1]; - if ((y <= y1 && y2 <= y) || (y1 <= y && y <= y2)) { - x = (y - y1) / (y2 - y1) * (x2 - x1) + x1; - intersections.push(x); - } - x1 = x2; - y1 = y2; - } - // Find the longest segment of the horizontal line that has its center point - // inside the linear ring. - var pointX = NaN; - var maxSegmentLength = -Infinity; - intersections.sort(ol.array.numberSafeCompareFunction); - x1 = intersections[0]; - for (i = 1, ii = intersections.length; i < ii; ++i) { - x2 = intersections[i]; - var segmentLength = Math.abs(x2 - x1); - if (segmentLength > maxSegmentLength) { - x = (x1 + x2) / 2; - if (ol.geom.flat.contains.linearRingsContainsXY( - flatCoordinates, offset, ends, stride, x, y)) { - pointX = x; - maxSegmentLength = segmentLength; - } - } - x1 = x2; - } - if (isNaN(pointX)) { - // There is no horizontal line that has its center point inside the linear - // ring. Use the center of the the linear ring's extent. - pointX = flatCenters[flatCentersOffset]; - } - if (opt_dest) { - opt_dest.push(pointX, y, maxSegmentLength); - return opt_dest; - } else { - return [pointX, y, maxSegmentLength]; - } -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<Array.<number>>} endss Endss. - * @param {number} stride Stride. - * @param {Array.<number>} flatCenters Flat centers. - * @return {Array.<number>} Interior points as XYM coordinates, where M is the - * length of the horizontal intersection that the point belongs to. - */ -ol.geom.flat.interiorpoint.linearRingss = function(flatCoordinates, offset, endss, stride, flatCenters) { - var interiorPoints = []; - var i, ii; - for (i = 0, ii = endss.length; i < ii; ++i) { - var ends = endss[i]; - interiorPoints = ol.geom.flat.interiorpoint.linearRings(flatCoordinates, - offset, ends, stride, flatCenters, 2 * i, interiorPoints); - offset = ends[ends.length - 1]; - } - return interiorPoints; -}; - -goog.provide('ol.geom.flat.segments'); - - -/** - * This function calls `callback` for each segment of the flat coordinates - * array. If the callback returns a truthy value the function returns that - * value immediately. Otherwise the function returns `false`. - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {function(this: S, ol.Coordinate, ol.Coordinate): T} callback Function - * called for each segment. - * @param {S=} opt_this The object to be used as the value of 'this' - * within callback. - * @return {T|boolean} Value. - * @template T,S - */ -ol.geom.flat.segments.forEach = function(flatCoordinates, offset, end, stride, callback, opt_this) { - var point1 = [flatCoordinates[offset], flatCoordinates[offset + 1]]; - var point2 = []; - var ret; - for (; (offset + stride) < end; offset += stride) { - point2[0] = flatCoordinates[offset + stride]; - point2[1] = flatCoordinates[offset + stride + 1]; - ret = callback.call(opt_this, point1, point2); - if (ret) { - return ret; - } - point1[0] = point2[0]; - point1[1] = point2[1]; - } - return false; -}; - -goog.provide('ol.geom.flat.intersectsextent'); - -goog.require('ol.extent'); -goog.require('ol.geom.flat.contains'); -goog.require('ol.geom.flat.segments'); - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {ol.Extent} extent Extent. - * @return {boolean} True if the geometry and the extent intersect. - */ -ol.geom.flat.intersectsextent.lineString = function(flatCoordinates, offset, end, stride, extent) { - var coordinatesExtent = ol.extent.extendFlatCoordinates( - ol.extent.createEmpty(), flatCoordinates, offset, end, stride); - if (!ol.extent.intersects(extent, coordinatesExtent)) { - return false; - } - if (ol.extent.containsExtent(extent, coordinatesExtent)) { - return true; - } - if (coordinatesExtent[0] >= extent[0] && - coordinatesExtent[2] <= extent[2]) { - return true; - } - if (coordinatesExtent[1] >= extent[1] && - coordinatesExtent[3] <= extent[3]) { - return true; - } - return ol.geom.flat.segments.forEach(flatCoordinates, offset, end, stride, - /** - * @param {ol.Coordinate} point1 Start point. - * @param {ol.Coordinate} point2 End point. - * @return {boolean} `true` if the segment and the extent intersect, - * `false` otherwise. - */ - function(point1, point2) { - return ol.extent.intersectsSegment(extent, point1, point2); - }); -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<number>} ends Ends. - * @param {number} stride Stride. - * @param {ol.Extent} extent Extent. - * @return {boolean} True if the geometry and the extent intersect. - */ -ol.geom.flat.intersectsextent.lineStrings = function(flatCoordinates, offset, ends, stride, extent) { - var i, ii; - for (i = 0, ii = ends.length; i < ii; ++i) { - if (ol.geom.flat.intersectsextent.lineString( - flatCoordinates, offset, ends[i], stride, extent)) { - return true; - } - offset = ends[i]; - } - return false; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {ol.Extent} extent Extent. - * @return {boolean} True if the geometry and the extent intersect. - */ -ol.geom.flat.intersectsextent.linearRing = function(flatCoordinates, offset, end, stride, extent) { - if (ol.geom.flat.intersectsextent.lineString( - flatCoordinates, offset, end, stride, extent)) { - return true; - } - if (ol.geom.flat.contains.linearRingContainsXY( - flatCoordinates, offset, end, stride, extent[0], extent[1])) { - return true; - } - if (ol.geom.flat.contains.linearRingContainsXY( - flatCoordinates, offset, end, stride, extent[0], extent[3])) { - return true; - } - if (ol.geom.flat.contains.linearRingContainsXY( - flatCoordinates, offset, end, stride, extent[2], extent[1])) { - return true; - } - if (ol.geom.flat.contains.linearRingContainsXY( - flatCoordinates, offset, end, stride, extent[2], extent[3])) { - return true; - } - return false; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<number>} ends Ends. - * @param {number} stride Stride. - * @param {ol.Extent} extent Extent. - * @return {boolean} True if the geometry and the extent intersect. - */ -ol.geom.flat.intersectsextent.linearRings = function(flatCoordinates, offset, ends, stride, extent) { - if (!ol.geom.flat.intersectsextent.linearRing( - flatCoordinates, offset, ends[0], stride, extent)) { - return false; - } - if (ends.length === 1) { - return true; - } - var i, ii; - for (i = 1, ii = ends.length; i < ii; ++i) { - if (ol.geom.flat.contains.linearRingContainsExtent( - flatCoordinates, ends[i - 1], ends[i], stride, extent)) { - return false; - } - } - return true; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<Array.<number>>} endss Endss. - * @param {number} stride Stride. - * @param {ol.Extent} extent Extent. - * @return {boolean} True if the geometry and the extent intersect. - */ -ol.geom.flat.intersectsextent.linearRingss = function(flatCoordinates, offset, endss, stride, extent) { - var i, ii; - for (i = 0, ii = endss.length; i < ii; ++i) { - var ends = endss[i]; - if (ol.geom.flat.intersectsextent.linearRings( - flatCoordinates, offset, ends, stride, extent)) { - return true; - } - offset = ends[ends.length - 1]; - } - return false; -}; - -goog.provide('ol.geom.flat.reverse'); - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - */ -ol.geom.flat.reverse.coordinates = function(flatCoordinates, offset, end, stride) { - while (offset < end - stride) { - var i; - for (i = 0; i < stride; ++i) { - var tmp = flatCoordinates[offset + i]; - flatCoordinates[offset + i] = flatCoordinates[end - stride + i]; - flatCoordinates[end - stride + i] = tmp; - } - offset += stride; - end -= stride; - } -}; - -goog.provide('ol.geom.flat.orient'); - -goog.require('ol.geom.flat.reverse'); - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @return {boolean} Is clockwise. - */ -ol.geom.flat.orient.linearRingIsClockwise = function(flatCoordinates, offset, end, stride) { - // http://tinyurl.com/clockwise-method - // https://github.com/OSGeo/gdal/blob/trunk/gdal/ogr/ogrlinearring.cpp - var edge = 0; - var x1 = flatCoordinates[end - stride]; - var y1 = flatCoordinates[end - stride + 1]; - for (; offset < end; offset += stride) { - var x2 = flatCoordinates[offset]; - var y2 = flatCoordinates[offset + 1]; - edge += (x2 - x1) * (y2 + y1); - x1 = x2; - y1 = y2; - } - return edge > 0; -}; - - -/** - * Determines if linear rings are oriented. By default, left-hand orientation - * is tested (first ring must be clockwise, remaining rings counter-clockwise). - * To test for right-hand orientation, use the `opt_right` argument. - * - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<number>} ends Array of end indexes. - * @param {number} stride Stride. - * @param {boolean=} opt_right Test for right-hand orientation - * (counter-clockwise exterior ring and clockwise interior rings). - * @return {boolean} Rings are correctly oriented. - */ -ol.geom.flat.orient.linearRingsAreOriented = function(flatCoordinates, offset, ends, stride, opt_right) { - var right = opt_right !== undefined ? opt_right : false; - var i, ii; - for (i = 0, ii = ends.length; i < ii; ++i) { - var end = ends[i]; - var isClockwise = ol.geom.flat.orient.linearRingIsClockwise( - flatCoordinates, offset, end, stride); - if (i === 0) { - if ((right && isClockwise) || (!right && !isClockwise)) { - return false; - } - } else { - if ((right && !isClockwise) || (!right && isClockwise)) { - return false; - } - } - offset = end; - } - return true; -}; - - -/** - * Determines if linear rings are oriented. By default, left-hand orientation - * is tested (first ring must be clockwise, remaining rings counter-clockwise). - * To test for right-hand orientation, use the `opt_right` argument. - * - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<Array.<number>>} endss Array of array of end indexes. - * @param {number} stride Stride. - * @param {boolean=} opt_right Test for right-hand orientation - * (counter-clockwise exterior ring and clockwise interior rings). - * @return {boolean} Rings are correctly oriented. - */ -ol.geom.flat.orient.linearRingssAreOriented = function(flatCoordinates, offset, endss, stride, opt_right) { - var i, ii; - for (i = 0, ii = endss.length; i < ii; ++i) { - if (!ol.geom.flat.orient.linearRingsAreOriented( - flatCoordinates, offset, endss[i], stride, opt_right)) { - return false; - } - } - return true; -}; - - -/** - * Orient coordinates in a flat array of linear rings. By default, rings - * are oriented following the left-hand rule (clockwise for exterior and - * counter-clockwise for interior rings). To orient according to the - * right-hand rule, use the `opt_right` argument. - * - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<number>} ends Ends. - * @param {number} stride Stride. - * @param {boolean=} opt_right Follow the right-hand rule for orientation. - * @return {number} End. - */ -ol.geom.flat.orient.orientLinearRings = function(flatCoordinates, offset, ends, stride, opt_right) { - var right = opt_right !== undefined ? opt_right : false; - var i, ii; - for (i = 0, ii = ends.length; i < ii; ++i) { - var end = ends[i]; - var isClockwise = ol.geom.flat.orient.linearRingIsClockwise( - flatCoordinates, offset, end, stride); - var reverse = i === 0 ? - (right && isClockwise) || (!right && !isClockwise) : - (right && !isClockwise) || (!right && isClockwise); - if (reverse) { - ol.geom.flat.reverse.coordinates(flatCoordinates, offset, end, stride); - } - offset = end; - } - return offset; -}; - - -/** - * Orient coordinates in a flat array of linear rings. By default, rings - * are oriented following the left-hand rule (clockwise for exterior and - * counter-clockwise for interior rings). To orient according to the - * right-hand rule, use the `opt_right` argument. - * - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<Array.<number>>} endss Array of array of end indexes. - * @param {number} stride Stride. - * @param {boolean=} opt_right Follow the right-hand rule for orientation. - * @return {number} End. - */ -ol.geom.flat.orient.orientLinearRingss = function(flatCoordinates, offset, endss, stride, opt_right) { - var i, ii; - for (i = 0, ii = endss.length; i < ii; ++i) { - offset = ol.geom.flat.orient.orientLinearRings( - flatCoordinates, offset, endss[i], stride, opt_right); - } - return offset; -}; - -goog.provide('ol.geom.Polygon'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.extent'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.LinearRing'); -goog.require('ol.geom.Point'); -goog.require('ol.geom.SimpleGeometry'); -goog.require('ol.geom.flat.area'); -goog.require('ol.geom.flat.closest'); -goog.require('ol.geom.flat.contains'); -goog.require('ol.geom.flat.deflate'); -goog.require('ol.geom.flat.inflate'); -goog.require('ol.geom.flat.interiorpoint'); -goog.require('ol.geom.flat.intersectsextent'); -goog.require('ol.geom.flat.orient'); -goog.require('ol.geom.flat.simplify'); -goog.require('ol.math'); - - -/** - * @classdesc - * Polygon geometry. - * - * @constructor - * @extends {ol.geom.SimpleGeometry} - * @param {Array.<Array.<ol.Coordinate>>} coordinates Array of linear - * rings that define the polygon. The first linear ring of the array - * defines the outer-boundary or surface of the polygon. Each subsequent - * linear ring defines a hole in the surface of the polygon. A linear ring - * is an array of vertices' coordinates where the first coordinate and the - * last are equivalent. - * @param {ol.geom.GeometryLayout=} opt_layout Layout. - * @api - */ -ol.geom.Polygon = function(coordinates, opt_layout) { - - ol.geom.SimpleGeometry.call(this); - - /** - * @type {Array.<number>} - * @private - */ - this.ends_ = []; - - /** - * @private - * @type {number} - */ - this.flatInteriorPointRevision_ = -1; - - /** - * @private - * @type {ol.Coordinate} - */ - this.flatInteriorPoint_ = null; - - /** - * @private - * @type {number} - */ - this.maxDelta_ = -1; - - /** - * @private - * @type {number} - */ - this.maxDeltaRevision_ = -1; - - /** - * @private - * @type {number} - */ - this.orientedRevision_ = -1; - - /** - * @private - * @type {Array.<number>} - */ - this.orientedFlatCoordinates_ = null; - - this.setCoordinates(coordinates, opt_layout); - -}; -ol.inherits(ol.geom.Polygon, ol.geom.SimpleGeometry); - - -/** - * Append the passed linear ring to this polygon. - * @param {ol.geom.LinearRing} linearRing Linear ring. - * @api - */ -ol.geom.Polygon.prototype.appendLinearRing = function(linearRing) { - if (!this.flatCoordinates) { - this.flatCoordinates = linearRing.getFlatCoordinates().slice(); - } else { - ol.array.extend(this.flatCoordinates, linearRing.getFlatCoordinates()); - } - this.ends_.push(this.flatCoordinates.length); - this.changed(); -}; - - -/** - * Make a complete copy of the geometry. - * @return {!ol.geom.Polygon} Clone. - * @override - * @api - */ -ol.geom.Polygon.prototype.clone = function() { - var polygon = new ol.geom.Polygon(null); - polygon.setFlatCoordinates( - this.layout, this.flatCoordinates.slice(), this.ends_.slice()); - return polygon; -}; - - -/** - * @inheritDoc - */ -ol.geom.Polygon.prototype.closestPointXY = function(x, y, closestPoint, minSquaredDistance) { - if (minSquaredDistance < - ol.extent.closestSquaredDistanceXY(this.getExtent(), x, y)) { - return minSquaredDistance; - } - if (this.maxDeltaRevision_ != this.getRevision()) { - this.maxDelta_ = Math.sqrt(ol.geom.flat.closest.getsMaxSquaredDelta( - this.flatCoordinates, 0, this.ends_, this.stride, 0)); - this.maxDeltaRevision_ = this.getRevision(); - } - return ol.geom.flat.closest.getsClosestPoint( - this.flatCoordinates, 0, this.ends_, this.stride, - this.maxDelta_, true, x, y, closestPoint, minSquaredDistance); -}; - - -/** - * @inheritDoc - */ -ol.geom.Polygon.prototype.containsXY = function(x, y) { - return ol.geom.flat.contains.linearRingsContainsXY( - this.getOrientedFlatCoordinates(), 0, this.ends_, this.stride, x, y); -}; - - -/** - * Return the area of the polygon on projected plane. - * @return {number} Area (on projected plane). - * @api - */ -ol.geom.Polygon.prototype.getArea = function() { - return ol.geom.flat.area.linearRings( - this.getOrientedFlatCoordinates(), 0, this.ends_, this.stride); -}; - - -/** - * Get the coordinate array for this geometry. This array has the structure - * of a GeoJSON coordinate array for polygons. - * - * @param {boolean=} opt_right Orient coordinates according to the right-hand - * rule (counter-clockwise for exterior and clockwise for interior rings). - * If `false`, coordinates will be oriented according to the left-hand rule - * (clockwise for exterior and counter-clockwise for interior rings). - * By default, coordinate orientation will depend on how the geometry was - * constructed. - * @return {Array.<Array.<ol.Coordinate>>} Coordinates. - * @override - * @api - */ -ol.geom.Polygon.prototype.getCoordinates = function(opt_right) { - var flatCoordinates; - if (opt_right !== undefined) { - flatCoordinates = this.getOrientedFlatCoordinates().slice(); - ol.geom.flat.orient.orientLinearRings( - flatCoordinates, 0, this.ends_, this.stride, opt_right); - } else { - flatCoordinates = this.flatCoordinates; - } - - return ol.geom.flat.inflate.coordinatess( - flatCoordinates, 0, this.ends_, this.stride); -}; - - -/** - * @return {Array.<number>} Ends. - */ -ol.geom.Polygon.prototype.getEnds = function() { - return this.ends_; -}; - - -/** - * @return {Array.<number>} Interior point. - */ -ol.geom.Polygon.prototype.getFlatInteriorPoint = function() { - if (this.flatInteriorPointRevision_ != this.getRevision()) { - var flatCenter = ol.extent.getCenter(this.getExtent()); - this.flatInteriorPoint_ = ol.geom.flat.interiorpoint.linearRings( - this.getOrientedFlatCoordinates(), 0, this.ends_, this.stride, - flatCenter, 0); - this.flatInteriorPointRevision_ = this.getRevision(); - } - return this.flatInteriorPoint_; -}; - - -/** - * Return an interior point of the polygon. - * @return {ol.geom.Point} Interior point as XYM coordinate, where M is the - * length of the horizontal intersection that the point belongs to. - * @api - */ -ol.geom.Polygon.prototype.getInteriorPoint = function() { - return new ol.geom.Point(this.getFlatInteriorPoint(), ol.geom.GeometryLayout.XYM); -}; - - -/** - * Return the number of rings of the polygon, this includes the exterior - * ring and any interior rings. - * - * @return {number} Number of rings. - * @api - */ -ol.geom.Polygon.prototype.getLinearRingCount = function() { - return this.ends_.length; -}; - - -/** - * Return the Nth linear ring of the polygon geometry. Return `null` if the - * given index is out of range. - * The exterior linear ring is available at index `0` and the interior rings - * at index `1` and beyond. - * - * @param {number} index Index. - * @return {ol.geom.LinearRing} Linear ring. - * @api - */ -ol.geom.Polygon.prototype.getLinearRing = function(index) { - if (index < 0 || this.ends_.length <= index) { - return null; - } - var linearRing = new ol.geom.LinearRing(null); - linearRing.setFlatCoordinates(this.layout, this.flatCoordinates.slice( - index === 0 ? 0 : this.ends_[index - 1], this.ends_[index])); - return linearRing; -}; - - -/** - * Return the linear rings of the polygon. - * @return {Array.<ol.geom.LinearRing>} Linear rings. - * @api - */ -ol.geom.Polygon.prototype.getLinearRings = function() { - var layout = this.layout; - var flatCoordinates = this.flatCoordinates; - var ends = this.ends_; - var linearRings = []; - var offset = 0; - var i, ii; - for (i = 0, ii = ends.length; i < ii; ++i) { - var end = ends[i]; - var linearRing = new ol.geom.LinearRing(null); - linearRing.setFlatCoordinates(layout, flatCoordinates.slice(offset, end)); - linearRings.push(linearRing); - offset = end; - } - return linearRings; -}; - - -/** - * @return {Array.<number>} Oriented flat coordinates. - */ -ol.geom.Polygon.prototype.getOrientedFlatCoordinates = function() { - if (this.orientedRevision_ != this.getRevision()) { - var flatCoordinates = this.flatCoordinates; - if (ol.geom.flat.orient.linearRingsAreOriented( - flatCoordinates, 0, this.ends_, this.stride)) { - this.orientedFlatCoordinates_ = flatCoordinates; - } else { - this.orientedFlatCoordinates_ = flatCoordinates.slice(); - this.orientedFlatCoordinates_.length = - ol.geom.flat.orient.orientLinearRings( - this.orientedFlatCoordinates_, 0, this.ends_, this.stride); - } - this.orientedRevision_ = this.getRevision(); - } - return this.orientedFlatCoordinates_; -}; - - -/** - * @inheritDoc - */ -ol.geom.Polygon.prototype.getSimplifiedGeometryInternal = function(squaredTolerance) { - var simplifiedFlatCoordinates = []; - var simplifiedEnds = []; - simplifiedFlatCoordinates.length = ol.geom.flat.simplify.quantizes( - this.flatCoordinates, 0, this.ends_, this.stride, - Math.sqrt(squaredTolerance), - simplifiedFlatCoordinates, 0, simplifiedEnds); - var simplifiedPolygon = new ol.geom.Polygon(null); - simplifiedPolygon.setFlatCoordinates( - ol.geom.GeometryLayout.XY, simplifiedFlatCoordinates, simplifiedEnds); - return simplifiedPolygon; -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.Polygon.prototype.getType = function() { - return ol.geom.GeometryType.POLYGON; -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.Polygon.prototype.intersectsExtent = function(extent) { - return ol.geom.flat.intersectsextent.linearRings( - this.getOrientedFlatCoordinates(), 0, this.ends_, this.stride, extent); -}; - - -/** - * Set the coordinates of the polygon. - * @param {Array.<Array.<ol.Coordinate>>} coordinates Coordinates. - * @param {ol.geom.GeometryLayout=} opt_layout Layout. - * @override - * @api - */ -ol.geom.Polygon.prototype.setCoordinates = function(coordinates, opt_layout) { - if (!coordinates) { - this.setFlatCoordinates(ol.geom.GeometryLayout.XY, null, this.ends_); - } else { - this.setLayout(opt_layout, coordinates, 2); - if (!this.flatCoordinates) { - this.flatCoordinates = []; - } - var ends = ol.geom.flat.deflate.coordinatess( - this.flatCoordinates, 0, coordinates, this.stride, this.ends_); - this.flatCoordinates.length = ends.length === 0 ? 0 : ends[ends.length - 1]; - this.changed(); - } -}; - - -/** - * @param {ol.geom.GeometryLayout} layout Layout. - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {Array.<number>} ends Ends. - */ -ol.geom.Polygon.prototype.setFlatCoordinates = function(layout, flatCoordinates, ends) { - this.setFlatCoordinatesInternal(layout, flatCoordinates); - this.ends_ = ends; - this.changed(); -}; - - -/** - * Create an approximation of a circle on the surface of a sphere. - * @param {ol.Sphere} sphere The sphere. - * @param {ol.Coordinate} center Center (`[lon, lat]` in degrees). - * @param {number} radius The great-circle distance from the center to - * the polygon vertices. - * @param {number=} opt_n Optional number of vertices for the resulting - * polygon. Default is `32`. - * @return {ol.geom.Polygon} The "circular" polygon. - * @api - */ -ol.geom.Polygon.circular = function(sphere, center, radius, opt_n) { - var n = opt_n ? opt_n : 32; - /** @type {Array.<number>} */ - var flatCoordinates = []; - var i; - for (i = 0; i < n; ++i) { - ol.array.extend( - flatCoordinates, sphere.offset(center, radius, 2 * Math.PI * i / n)); - } - flatCoordinates.push(flatCoordinates[0], flatCoordinates[1]); - var polygon = new ol.geom.Polygon(null); - polygon.setFlatCoordinates( - ol.geom.GeometryLayout.XY, flatCoordinates, [flatCoordinates.length]); - return polygon; -}; - - -/** - * Create a polygon from an extent. The layout used is `XY`. - * @param {ol.Extent} extent The extent. - * @return {ol.geom.Polygon} The polygon. - * @api - */ -ol.geom.Polygon.fromExtent = function(extent) { - var minX = extent[0]; - var minY = extent[1]; - var maxX = extent[2]; - var maxY = extent[3]; - var flatCoordinates = - [minX, minY, minX, maxY, maxX, maxY, maxX, minY, minX, minY]; - var polygon = new ol.geom.Polygon(null); - polygon.setFlatCoordinates( - ol.geom.GeometryLayout.XY, flatCoordinates, [flatCoordinates.length]); - return polygon; -}; - - -/** - * Create a regular polygon from a circle. - * @param {ol.geom.Circle} circle Circle geometry. - * @param {number=} opt_sides Number of sides of the polygon. Default is 32. - * @param {number=} opt_angle Start angle for the first vertex of the polygon in - * radians. Default is 0. - * @return {ol.geom.Polygon} Polygon geometry. - * @api - */ -ol.geom.Polygon.fromCircle = function(circle, opt_sides, opt_angle) { - var sides = opt_sides ? opt_sides : 32; - var stride = circle.getStride(); - var layout = circle.getLayout(); - var polygon = new ol.geom.Polygon(null, layout); - var arrayLength = stride * (sides + 1); - var flatCoordinates = new Array(arrayLength); - for (var i = 0; i < arrayLength; i++) { - flatCoordinates[i] = 0; - } - var ends = [flatCoordinates.length]; - polygon.setFlatCoordinates(layout, flatCoordinates, ends); - ol.geom.Polygon.makeRegular( - polygon, circle.getCenter(), circle.getRadius(), opt_angle); - return polygon; -}; - - -/** - * Modify the coordinates of a polygon to make it a regular polygon. - * @param {ol.geom.Polygon} polygon Polygon geometry. - * @param {ol.Coordinate} center Center of the regular polygon. - * @param {number} radius Radius of the regular polygon. - * @param {number=} opt_angle Start angle for the first vertex of the polygon in - * radians. Default is 0. - */ -ol.geom.Polygon.makeRegular = function(polygon, center, radius, opt_angle) { - var flatCoordinates = polygon.getFlatCoordinates(); - var layout = polygon.getLayout(); - var stride = polygon.getStride(); - var ends = polygon.getEnds(); - var sides = flatCoordinates.length / stride - 1; - var startAngle = opt_angle ? opt_angle : 0; - var angle, offset; - for (var i = 0; i <= sides; ++i) { - offset = i * stride; - angle = startAngle + (ol.math.modulo(i, sides) * 2 * Math.PI / sides); - flatCoordinates[offset] = center[0] + (radius * Math.cos(angle)); - flatCoordinates[offset + 1] = center[1] + (radius * Math.sin(angle)); - } - polygon.setFlatCoordinates(layout, flatCoordinates, ends); -}; - -goog.provide('ol.View'); - -goog.require('ol'); -goog.require('ol.CenterConstraint'); -goog.require('ol.Object'); -goog.require('ol.ResolutionConstraint'); -goog.require('ol.RotationConstraint'); -goog.require('ol.ViewHint'); -goog.require('ol.ViewProperty'); -goog.require('ol.array'); -goog.require('ol.asserts'); -goog.require('ol.coordinate'); -goog.require('ol.easing'); -goog.require('ol.extent'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.Polygon'); -goog.require('ol.geom.SimpleGeometry'); -goog.require('ol.math'); -goog.require('ol.obj'); -goog.require('ol.proj'); -goog.require('ol.proj.Units'); - - -/** - * @classdesc - * An ol.View object represents a simple 2D view of the map. - * - * This is the object to act upon to change the center, resolution, - * and rotation of the map. - * - * ### The view states - * - * An `ol.View` is determined by three states: `center`, `resolution`, - * and `rotation`. Each state has a corresponding getter and setter, e.g. - * `getCenter` and `setCenter` for the `center` state. - * - * An `ol.View` has a `projection`. The projection determines the - * coordinate system of the center, and its units determine the units of the - * resolution (projection units per pixel). The default projection is - * Spherical Mercator (EPSG:3857). - * - * ### The constraints - * - * `setCenter`, `setResolution` and `setRotation` can be used to change the - * states of the view. Any value can be passed to the setters. And the value - * that is passed to a setter will effectively be the value set in the view, - * and returned by the corresponding getter. - * - * But an `ol.View` object also has a *resolution constraint*, a - * *rotation constraint* and a *center constraint*. - * - * As said above, no constraints are applied when the setters are used to set - * new states for the view. Applying constraints is done explicitly through - * the use of the `constrain*` functions (`constrainResolution` and - * `constrainRotation` and `constrainCenter`). - * - * The main users of the constraints are the interactions and the - * controls. For example, double-clicking on the map changes the view to - * the "next" resolution. And releasing the fingers after pinch-zooming - * snaps to the closest resolution (with an animation). - * - * The *resolution constraint* snaps to specific resolutions. It is - * determined by the following options: `resolutions`, `maxResolution`, - * `maxZoom`, and `zoomFactor`. If `resolutions` is set, the other three - * options are ignored. See documentation for each option for more - * information. - * - * The *rotation constraint* snaps to specific angles. It is determined - * by the following options: `enableRotation` and `constrainRotation`. - * By default the rotation value is snapped to zero when approaching the - * horizontal. - * - * The *center constraint* is determined by the `extent` option. By - * default the center is not constrained at all. - * - * @constructor - * @extends {ol.Object} - * @param {olx.ViewOptions=} opt_options View options. - * @api - */ -ol.View = function(opt_options) { - ol.Object.call(this); - - var options = ol.obj.assign({}, opt_options); - - /** - * @private - * @type {Array.<number>} - */ - this.hints_ = [0, 0]; - - /** - * @private - * @type {Array.<Array.<ol.ViewAnimation>>} - */ - this.animations_ = []; - - /** - * @private - * @type {number|undefined} - */ - this.updateAnimationKey_; - - this.updateAnimations_ = this.updateAnimations_.bind(this); - - /** - * @private - * @const - * @type {ol.proj.Projection} - */ - this.projection_ = ol.proj.createProjection(options.projection, 'EPSG:3857'); - - this.applyOptions_(options); -}; -ol.inherits(ol.View, ol.Object); - - -/** - * Set up the view with the given options. - * @param {olx.ViewOptions} options View options. - */ -ol.View.prototype.applyOptions_ = function(options) { - - /** - * @type {Object.<string, *>} - */ - var properties = {}; - properties[ol.ViewProperty.CENTER] = options.center !== undefined ? - options.center : null; - - var resolutionConstraintInfo = ol.View.createResolutionConstraint_( - options); - - /** - * @private - * @type {number} - */ - this.maxResolution_ = resolutionConstraintInfo.maxResolution; - - /** - * @private - * @type {number} - */ - this.minResolution_ = resolutionConstraintInfo.minResolution; - - /** - * @private - * @type {number} - */ - this.zoomFactor_ = resolutionConstraintInfo.zoomFactor; - - /** - * @private - * @type {Array.<number>|undefined} - */ - this.resolutions_ = options.resolutions; - - /** - * @private - * @type {number} - */ - this.minZoom_ = resolutionConstraintInfo.minZoom; - - var centerConstraint = ol.View.createCenterConstraint_(options); - var resolutionConstraint = resolutionConstraintInfo.constraint; - var rotationConstraint = ol.View.createRotationConstraint_(options); - - /** - * @private - * @type {ol.Constraints} - */ - this.constraints_ = { - center: centerConstraint, - resolution: resolutionConstraint, - rotation: rotationConstraint - }; - - if (options.resolution !== undefined) { - properties[ol.ViewProperty.RESOLUTION] = options.resolution; - } else if (options.zoom !== undefined) { - properties[ol.ViewProperty.RESOLUTION] = this.constrainResolution( - this.maxResolution_, options.zoom - this.minZoom_); - } - properties[ol.ViewProperty.ROTATION] = - options.rotation !== undefined ? options.rotation : 0; - this.setProperties(properties); - - /** - * @private - * @type {olx.ViewOptions} - */ - this.options_ = options; - -}; - -/** - * Get an updated version of the view options used to construct the view. The - * current resolution (or zoom), center, and rotation are applied to any stored - * options. The provided options can be uesd to apply new min/max zoom or - * resolution limits. - * @param {olx.ViewOptions} newOptions New options to be applied. - * @return {olx.ViewOptions} New options updated with the current view state. - */ -ol.View.prototype.getUpdatedOptions_ = function(newOptions) { - var options = ol.obj.assign({}, this.options_); - - // preserve resolution (or zoom) - if (options.resolution !== undefined) { - options.resolution = this.getResolution(); - } else { - options.zoom = this.getZoom(); - } - - // preserve center - options.center = this.getCenter(); - - // preserve rotation - options.rotation = this.getRotation(); - - return ol.obj.assign({}, options, newOptions); -}; - - -/** - * Animate the view. The view's center, zoom (or resolution), and rotation - * can be animated for smooth transitions between view states. For example, - * to animate the view to a new zoom level: - * - * view.animate({zoom: view.getZoom() + 1}); - * - * By default, the animation lasts one second and uses in-and-out easing. You - * can customize this behavior by including `duration` (in milliseconds) and - * `easing` options (see {@link ol.easing}). - * - * To chain together multiple animations, call the method with multiple - * animation objects. For example, to first zoom and then pan: - * - * view.animate({zoom: 10}, {center: [0, 0]}); - * - * If you provide a function as the last argument to the animate method, it - * will get called at the end of an animation series. The callback will be - * called with `true` if the animation series completed on its own or `false` - * if it was cancelled. - * - * Animations are cancelled by user interactions (e.g. dragging the map) or by - * calling `view.setCenter()`, `view.setResolution()`, or `view.setRotation()` - * (or another method that calls one of these). - * - * @param {...(olx.AnimationOptions|function(boolean))} var_args Animation - * options. Multiple animations can be run in series by passing multiple - * options objects. To run multiple animations in parallel, call the method - * multiple times. An optional callback can be provided as a final - * argument. The callback will be called with a boolean indicating whether - * the animation completed without being cancelled. - * @api - */ -ol.View.prototype.animate = function(var_args) { - var animationCount = arguments.length; - var callback; - if (animationCount > 1 && typeof arguments[animationCount - 1] === 'function') { - callback = arguments[animationCount - 1]; - --animationCount; - } - if (!this.isDef()) { - // if view properties are not yet set, shortcut to the final state - var state = arguments[animationCount - 1]; - if (state.center) { - this.setCenter(state.center); - } - if (state.zoom !== undefined) { - this.setZoom(state.zoom); - } - if (state.rotation !== undefined) { - this.setRotation(state.rotation); - } - if (callback) { - callback(true); - } - return; - } - var start = Date.now(); - var center = this.getCenter().slice(); - var resolution = this.getResolution(); - var rotation = this.getRotation(); - var series = []; - for (var i = 0; i < animationCount; ++i) { - var options = /** @type {olx.AnimationOptions} */ (arguments[i]); - - var animation = /** @type {ol.ViewAnimation} */ ({ - start: start, - complete: false, - anchor: options.anchor, - duration: options.duration !== undefined ? options.duration : 1000, - easing: options.easing || ol.easing.inAndOut - }); - - if (options.center) { - animation.sourceCenter = center; - animation.targetCenter = options.center; - center = animation.targetCenter; - } - - if (options.zoom !== undefined) { - animation.sourceResolution = resolution; - animation.targetResolution = this.constrainResolution( - this.maxResolution_, options.zoom - this.minZoom_, 0); - resolution = animation.targetResolution; - } else if (options.resolution) { - animation.sourceResolution = resolution; - animation.targetResolution = options.resolution; - resolution = animation.targetResolution; - } - - if (options.rotation !== undefined) { - animation.sourceRotation = rotation; - var delta = ol.math.modulo(options.rotation - rotation + Math.PI, 2 * Math.PI) - Math.PI; - animation.targetRotation = rotation + delta; - rotation = animation.targetRotation; - } - - animation.callback = callback; - - // check if animation is a no-op - if (ol.View.isNoopAnimation(animation)) { - animation.complete = true; - // we still push it onto the series for callback handling - } else { - start += animation.duration; - } - series.push(animation); - } - this.animations_.push(series); - this.setHint(ol.ViewHint.ANIMATING, 1); - this.updateAnimations_(); -}; - - -/** - * Determine if the view is being animated. - * @return {boolean} The view is being animated. - * @api - */ -ol.View.prototype.getAnimating = function() { - return this.getHints()[ol.ViewHint.ANIMATING] > 0; -}; - - -/** - * Determine if the user is interacting with the view, such as panning or zooming. - * @return {boolean} The view is being interacted with. - * @api - */ -ol.View.prototype.getInteracting = function() { - return this.getHints()[ol.ViewHint.INTERACTING] > 0; -}; - - -/** - * Cancel any ongoing animations. - * @api - */ -ol.View.prototype.cancelAnimations = function() { - this.setHint(ol.ViewHint.ANIMATING, -this.getHints()[ol.ViewHint.ANIMATING]); - for (var i = 0, ii = this.animations_.length; i < ii; ++i) { - var series = this.animations_[i]; - if (series[0].callback) { - series[0].callback(false); - } - } - this.animations_.length = 0; -}; - -/** - * Update all animations. - */ -ol.View.prototype.updateAnimations_ = function() { - if (this.updateAnimationKey_ !== undefined) { - cancelAnimationFrame(this.updateAnimationKey_); - this.updateAnimationKey_ = undefined; - } - if (!this.getAnimating()) { - return; - } - var now = Date.now(); - var more = false; - for (var i = this.animations_.length - 1; i >= 0; --i) { - var series = this.animations_[i]; - var seriesComplete = true; - for (var j = 0, jj = series.length; j < jj; ++j) { - var animation = series[j]; - if (animation.complete) { - continue; - } - var elapsed = now - animation.start; - var fraction = animation.duration > 0 ? elapsed / animation.duration : 1; - if (fraction >= 1) { - animation.complete = true; - fraction = 1; - } else { - seriesComplete = false; - } - var progress = animation.easing(fraction); - if (animation.sourceCenter) { - var x0 = animation.sourceCenter[0]; - var y0 = animation.sourceCenter[1]; - var x1 = animation.targetCenter[0]; - var y1 = animation.targetCenter[1]; - var x = x0 + progress * (x1 - x0); - var y = y0 + progress * (y1 - y0); - this.set(ol.ViewProperty.CENTER, [x, y]); - } - if (animation.sourceResolution && animation.targetResolution) { - var resolution = progress === 1 ? - animation.targetResolution : - animation.sourceResolution + progress * (animation.targetResolution - animation.sourceResolution); - if (animation.anchor) { - this.set(ol.ViewProperty.CENTER, - this.calculateCenterZoom(resolution, animation.anchor)); - } - this.set(ol.ViewProperty.RESOLUTION, resolution); - } - if (animation.sourceRotation !== undefined && animation.targetRotation !== undefined) { - var rotation = progress === 1 ? - ol.math.modulo(animation.targetRotation + Math.PI, 2 * Math.PI) - Math.PI : - animation.sourceRotation + progress * (animation.targetRotation - animation.sourceRotation); - if (animation.anchor) { - this.set(ol.ViewProperty.CENTER, - this.calculateCenterRotate(rotation, animation.anchor)); - } - this.set(ol.ViewProperty.ROTATION, rotation); - } - more = true; - if (!animation.complete) { - break; - } - } - if (seriesComplete) { - this.animations_[i] = null; - this.setHint(ol.ViewHint.ANIMATING, -1); - var callback = series[0].callback; - if (callback) { - callback(true); - } - } - } - // prune completed series - this.animations_ = this.animations_.filter(Boolean); - if (more && this.updateAnimationKey_ === undefined) { - this.updateAnimationKey_ = requestAnimationFrame(this.updateAnimations_); - } -}; - -/** - * @param {number} rotation Target rotation. - * @param {ol.Coordinate} anchor Rotation anchor. - * @return {ol.Coordinate|undefined} Center for rotation and anchor. - */ -ol.View.prototype.calculateCenterRotate = function(rotation, anchor) { - var center; - var currentCenter = this.getCenter(); - if (currentCenter !== undefined) { - center = [currentCenter[0] - anchor[0], currentCenter[1] - anchor[1]]; - ol.coordinate.rotate(center, rotation - this.getRotation()); - ol.coordinate.add(center, anchor); - } - return center; -}; - - -/** - * @param {number} resolution Target resolution. - * @param {ol.Coordinate} anchor Zoom anchor. - * @return {ol.Coordinate|undefined} Center for resolution and anchor. - */ -ol.View.prototype.calculateCenterZoom = function(resolution, anchor) { - var center; - var currentCenter = this.getCenter(); - var currentResolution = this.getResolution(); - if (currentCenter !== undefined && currentResolution !== undefined) { - var x = anchor[0] - - resolution * (anchor[0] - currentCenter[0]) / currentResolution; - var y = anchor[1] - - resolution * (anchor[1] - currentCenter[1]) / currentResolution; - center = [x, y]; - } - return center; -}; - - -/** - * @private - * @return {ol.Size} Viewport size or `[100, 100]` when no viewport is found. - */ -ol.View.prototype.getSizeFromViewport_ = function() { - var size = [100, 100]; - var selector = '.ol-viewport[data-view="' + ol.getUid(this) + '"]'; - var element = document.querySelector(selector); - if (element) { - var metrics = getComputedStyle(element); - size[0] = parseInt(metrics.width, 10); - size[1] = parseInt(metrics.height, 10); - } - return size; -}; - - -/** - * Get the constrained center of this view. - * @param {ol.Coordinate|undefined} center Center. - * @return {ol.Coordinate|undefined} Constrained center. - * @api - */ -ol.View.prototype.constrainCenter = function(center) { - return this.constraints_.center(center); -}; - - -/** - * Get the constrained resolution of this view. - * @param {number|undefined} resolution Resolution. - * @param {number=} opt_delta Delta. Default is `0`. - * @param {number=} opt_direction Direction. Default is `0`. - * @return {number|undefined} Constrained resolution. - * @api - */ -ol.View.prototype.constrainResolution = function( - resolution, opt_delta, opt_direction) { - var delta = opt_delta || 0; - var direction = opt_direction || 0; - return this.constraints_.resolution(resolution, delta, direction); -}; - - -/** - * Get the constrained rotation of this view. - * @param {number|undefined} rotation Rotation. - * @param {number=} opt_delta Delta. Default is `0`. - * @return {number|undefined} Constrained rotation. - * @api - */ -ol.View.prototype.constrainRotation = function(rotation, opt_delta) { - var delta = opt_delta || 0; - return this.constraints_.rotation(rotation, delta); -}; - - -/** - * Get the view center. - * @return {ol.Coordinate|undefined} The center of the view. - * @observable - * @api - */ -ol.View.prototype.getCenter = function() { - return /** @type {ol.Coordinate|undefined} */ ( - this.get(ol.ViewProperty.CENTER)); -}; - - -/** - * @return {ol.Constraints} Constraints. - */ -ol.View.prototype.getConstraints = function() { - return this.constraints_; -}; - - -/** - * @param {Array.<number>=} opt_hints Destination array. - * @return {Array.<number>} Hint. - */ -ol.View.prototype.getHints = function(opt_hints) { - if (opt_hints !== undefined) { - opt_hints[0] = this.hints_[0]; - opt_hints[1] = this.hints_[1]; - return opt_hints; - } else { - return this.hints_.slice(); - } -}; - - -/** - * Calculate the extent for the current view state and the passed size. - * The size is the pixel dimensions of the box into which the calculated extent - * should fit. In most cases you want to get the extent of the entire map, - * that is `map.getSize()`. - * @param {ol.Size=} opt_size Box pixel size. If not provided, the size of the - * first map that uses this view will be used. - * @return {ol.Extent} Extent. - * @api - */ -ol.View.prototype.calculateExtent = function(opt_size) { - var size = opt_size || this.getSizeFromViewport_(); - var center = /** @type {!ol.Coordinate} */ (this.getCenter()); - ol.asserts.assert(center, 1); // The view center is not defined - var resolution = /** @type {!number} */ (this.getResolution()); - ol.asserts.assert(resolution !== undefined, 2); // The view resolution is not defined - var rotation = /** @type {!number} */ (this.getRotation()); - ol.asserts.assert(rotation !== undefined, 3); // The view rotation is not defined - - return ol.extent.getForViewAndSize(center, resolution, rotation, size); -}; - - -/** - * Get the maximum resolution of the view. - * @return {number} The maximum resolution of the view. - * @api - */ -ol.View.prototype.getMaxResolution = function() { - return this.maxResolution_; -}; - - -/** - * Get the minimum resolution of the view. - * @return {number} The minimum resolution of the view. - * @api - */ -ol.View.prototype.getMinResolution = function() { - return this.minResolution_; -}; - - -/** - * Get the maximum zoom level for the view. - * @return {number} The maximum zoom level. - * @api - */ -ol.View.prototype.getMaxZoom = function() { - return /** @type {number} */ (this.getZoomForResolution(this.minResolution_)); -}; - - -/** - * Set a new maximum zoom level for the view. - * @param {number} zoom The maximum zoom level. - * @api - */ -ol.View.prototype.setMaxZoom = function(zoom) { - this.applyOptions_(this.getUpdatedOptions_({maxZoom: zoom})); -}; - - -/** - * Get the minimum zoom level for the view. - * @return {number} The minimum zoom level. - * @api - */ -ol.View.prototype.getMinZoom = function() { - return /** @type {number} */ (this.getZoomForResolution(this.maxResolution_)); -}; - - -/** - * Set a new minimum zoom level for the view. - * @param {number} zoom The minimum zoom level. - * @api - */ -ol.View.prototype.setMinZoom = function(zoom) { - this.applyOptions_(this.getUpdatedOptions_({minZoom: zoom})); -}; - - -/** - * Get the view projection. - * @return {ol.proj.Projection} The projection of the view. - * @api - */ -ol.View.prototype.getProjection = function() { - return this.projection_; -}; - - -/** - * Get the view resolution. - * @return {number|undefined} The resolution of the view. - * @observable - * @api - */ -ol.View.prototype.getResolution = function() { - return /** @type {number|undefined} */ ( - this.get(ol.ViewProperty.RESOLUTION)); -}; - - -/** - * Get the resolutions for the view. This returns the array of resolutions - * passed to the constructor of the {ol.View}, or undefined if none were given. - * @return {Array.<number>|undefined} The resolutions of the view. - * @api - */ -ol.View.prototype.getResolutions = function() { - return this.resolutions_; -}; - - -/** - * Get the resolution for a provided extent (in map units) and size (in pixels). - * @param {ol.Extent} extent Extent. - * @param {ol.Size=} opt_size Box pixel size. - * @return {number} The resolution at which the provided extent will render at - * the given size. - * @api - */ -ol.View.prototype.getResolutionForExtent = function(extent, opt_size) { - var size = opt_size || this.getSizeFromViewport_(); - var xResolution = ol.extent.getWidth(extent) / size[0]; - var yResolution = ol.extent.getHeight(extent) / size[1]; - return Math.max(xResolution, yResolution); -}; - - -/** - * Return a function that returns a value between 0 and 1 for a - * resolution. Exponential scaling is assumed. - * @param {number=} opt_power Power. - * @return {function(number): number} Resolution for value function. - */ -ol.View.prototype.getResolutionForValueFunction = function(opt_power) { - var power = opt_power || 2; - var maxResolution = this.maxResolution_; - var minResolution = this.minResolution_; - var max = Math.log(maxResolution / minResolution) / Math.log(power); - return ( - /** - * @param {number} value Value. - * @return {number} Resolution. - */ - function(value) { - var resolution = maxResolution / Math.pow(power, value * max); - return resolution; - }); -}; - - -/** - * Get the view rotation. - * @return {number} The rotation of the view in radians. - * @observable - * @api - */ -ol.View.prototype.getRotation = function() { - return /** @type {number} */ (this.get(ol.ViewProperty.ROTATION)); -}; - - -/** - * Return a function that returns a resolution for a value between - * 0 and 1. Exponential scaling is assumed. - * @param {number=} opt_power Power. - * @return {function(number): number} Value for resolution function. - */ -ol.View.prototype.getValueForResolutionFunction = function(opt_power) { - var power = opt_power || 2; - var maxResolution = this.maxResolution_; - var minResolution = this.minResolution_; - var max = Math.log(maxResolution / minResolution) / Math.log(power); - return ( - /** - * @param {number} resolution Resolution. - * @return {number} Value. - */ - function(resolution) { - var value = - (Math.log(maxResolution / resolution) / Math.log(power)) / max; - return value; - }); -}; - - -/** - * @return {olx.ViewState} View state. - */ -ol.View.prototype.getState = function() { - var center = /** @type {ol.Coordinate} */ (this.getCenter()); - var projection = this.getProjection(); - var resolution = /** @type {number} */ (this.getResolution()); - var rotation = this.getRotation(); - return /** @type {olx.ViewState} */ ({ - center: center.slice(), - projection: projection !== undefined ? projection : null, - resolution: resolution, - rotation: rotation - }); -}; - - -/** - * Get the current zoom level. Return undefined if the current - * resolution is undefined or not within the "resolution constraints". - * @return {number|undefined} Zoom. - * @api - */ -ol.View.prototype.getZoom = function() { - var zoom; - var resolution = this.getResolution(); - if (resolution !== undefined) { - zoom = this.getZoomForResolution(resolution); - } - return zoom; -}; - - -/** - * Get the zoom level for a resolution. - * @param {number} resolution The resolution. - * @return {number|undefined} The zoom level for the provided resolution. - * @api - */ -ol.View.prototype.getZoomForResolution = function(resolution) { - var zoom; - if (resolution >= this.minResolution_ && resolution <= this.maxResolution_) { - var offset = this.minZoom_ || 0; - var max, zoomFactor; - if (this.resolutions_) { - var nearest = ol.array.linearFindNearest(this.resolutions_, resolution, 1); - offset += nearest; - if (nearest == this.resolutions_.length - 1) { - return offset; - } - max = this.resolutions_[nearest]; - zoomFactor = max / this.resolutions_[nearest + 1]; - } else { - max = this.maxResolution_; - zoomFactor = this.zoomFactor_; - } - zoom = offset + Math.log(max / resolution) / Math.log(zoomFactor); - } - return zoom; -}; - - -/** - * Get the resolution for a zoom level. - * @param {number} zoom Zoom level. - * @return {number} The view resolution for the provided zoom level. - * @api - */ -ol.View.prototype.getResolutionForZoom = function(zoom) { - return /** @type {number} */ (this.constrainResolution( - this.maxResolution_, zoom - this.minZoom_, 0)); -}; - - -/** - * Fit the given geometry or extent based on the given map size and border. - * The size is pixel dimensions of the box to fit the extent into. - * In most cases you will want to use the map size, that is `map.getSize()`. - * Takes care of the map angle. - * @param {ol.geom.SimpleGeometry|ol.Extent} geometryOrExtent The geometry or - * extent to fit the view to. - * @param {olx.view.FitOptions=} opt_options Options. - * @api - */ -ol.View.prototype.fit = function(geometryOrExtent, opt_options) { - var options = opt_options || {}; - var size = options.size; - if (!size) { - size = this.getSizeFromViewport_(); - } - /** @type {ol.geom.SimpleGeometry} */ - var geometry; - if (!(geometryOrExtent instanceof ol.geom.SimpleGeometry)) { - ol.asserts.assert(Array.isArray(geometryOrExtent), - 24); // Invalid extent or geometry provided as `geometry` - ol.asserts.assert(!ol.extent.isEmpty(geometryOrExtent), - 25); // Cannot fit empty extent provided as `geometry` - geometry = ol.geom.Polygon.fromExtent(geometryOrExtent); - } else if (geometryOrExtent.getType() === ol.geom.GeometryType.CIRCLE) { - geometryOrExtent = geometryOrExtent.getExtent(); - geometry = ol.geom.Polygon.fromExtent(geometryOrExtent); - geometry.rotate(this.getRotation(), ol.extent.getCenter(geometryOrExtent)); - } else { - geometry = geometryOrExtent; - } - - var padding = options.padding !== undefined ? options.padding : [0, 0, 0, 0]; - var constrainResolution = options.constrainResolution !== undefined ? - options.constrainResolution : true; - var nearest = options.nearest !== undefined ? options.nearest : false; - var minResolution; - if (options.minResolution !== undefined) { - minResolution = options.minResolution; - } else if (options.maxZoom !== undefined) { - minResolution = this.constrainResolution( - this.maxResolution_, options.maxZoom - this.minZoom_, 0); - } else { - minResolution = 0; - } - var coords = geometry.getFlatCoordinates(); - - // calculate rotated extent - var rotation = this.getRotation(); - var cosAngle = Math.cos(-rotation); - var sinAngle = Math.sin(-rotation); - var minRotX = +Infinity; - var minRotY = +Infinity; - var maxRotX = -Infinity; - var maxRotY = -Infinity; - var stride = geometry.getStride(); - for (var i = 0, ii = coords.length; i < ii; i += stride) { - var rotX = coords[i] * cosAngle - coords[i + 1] * sinAngle; - var rotY = coords[i] * sinAngle + coords[i + 1] * cosAngle; - minRotX = Math.min(minRotX, rotX); - minRotY = Math.min(minRotY, rotY); - maxRotX = Math.max(maxRotX, rotX); - maxRotY = Math.max(maxRotY, rotY); - } - - // calculate resolution - var resolution = this.getResolutionForExtent( - [minRotX, minRotY, maxRotX, maxRotY], - [size[0] - padding[1] - padding[3], size[1] - padding[0] - padding[2]]); - resolution = isNaN(resolution) ? minResolution : - Math.max(resolution, minResolution); - if (constrainResolution) { - var constrainedResolution = this.constrainResolution(resolution, 0, 0); - if (!nearest && constrainedResolution < resolution) { - constrainedResolution = this.constrainResolution( - constrainedResolution, -1, 0); - } - resolution = constrainedResolution; - } - - // calculate center - sinAngle = -sinAngle; // go back to original rotation - var centerRotX = (minRotX + maxRotX) / 2; - var centerRotY = (minRotY + maxRotY) / 2; - centerRotX += (padding[1] - padding[3]) / 2 * resolution; - centerRotY += (padding[0] - padding[2]) / 2 * resolution; - var centerX = centerRotX * cosAngle - centerRotY * sinAngle; - var centerY = centerRotY * cosAngle + centerRotX * sinAngle; - var center = [centerX, centerY]; - var callback = options.callback ? options.callback : ol.nullFunction; - - if (options.duration !== undefined) { - this.animate({ - resolution: resolution, - center: center, - duration: options.duration, - easing: options.easing - }, callback); - } else { - this.setResolution(resolution); - this.setCenter(center); - setTimeout(callback.bind(undefined, true), 0); - } -}; - - -/** - * Center on coordinate and view position. - * @param {ol.Coordinate} coordinate Coordinate. - * @param {ol.Size} size Box pixel size. - * @param {ol.Pixel} position Position on the view to center on. - * @api - */ -ol.View.prototype.centerOn = function(coordinate, size, position) { - // calculate rotated position - var rotation = this.getRotation(); - var cosAngle = Math.cos(-rotation); - var sinAngle = Math.sin(-rotation); - var rotX = coordinate[0] * cosAngle - coordinate[1] * sinAngle; - var rotY = coordinate[1] * cosAngle + coordinate[0] * sinAngle; - var resolution = this.getResolution(); - rotX += (size[0] / 2 - position[0]) * resolution; - rotY += (position[1] - size[1] / 2) * resolution; - - // go back to original angle - sinAngle = -sinAngle; // go back to original rotation - var centerX = rotX * cosAngle - rotY * sinAngle; - var centerY = rotY * cosAngle + rotX * sinAngle; - - this.setCenter([centerX, centerY]); -}; - - -/** - * @return {boolean} Is defined. - */ -ol.View.prototype.isDef = function() { - return !!this.getCenter() && this.getResolution() !== undefined; -}; - - -/** - * Rotate the view around a given coordinate. - * @param {number} rotation New rotation value for the view. - * @param {ol.Coordinate=} opt_anchor The rotation center. - * @api - */ -ol.View.prototype.rotate = function(rotation, opt_anchor) { - if (opt_anchor !== undefined) { - var center = this.calculateCenterRotate(rotation, opt_anchor); - this.setCenter(center); - } - this.setRotation(rotation); -}; - - -/** - * Set the center of the current view. - * @param {ol.Coordinate|undefined} center The center of the view. - * @observable - * @api - */ -ol.View.prototype.setCenter = function(center) { - this.set(ol.ViewProperty.CENTER, center); - if (this.getAnimating()) { - this.cancelAnimations(); - } -}; - - -/** - * @param {ol.ViewHint} hint Hint. - * @param {number} delta Delta. - * @return {number} New value. - */ -ol.View.prototype.setHint = function(hint, delta) { - this.hints_[hint] += delta; - this.changed(); - return this.hints_[hint]; -}; - - -/** - * Set the resolution for this view. - * @param {number|undefined} resolution The resolution of the view. - * @observable - * @api - */ -ol.View.prototype.setResolution = function(resolution) { - this.set(ol.ViewProperty.RESOLUTION, resolution); - if (this.getAnimating()) { - this.cancelAnimations(); - } -}; - - -/** - * Set the rotation for this view. - * @param {number} rotation The rotation of the view in radians. - * @observable - * @api - */ -ol.View.prototype.setRotation = function(rotation) { - this.set(ol.ViewProperty.ROTATION, rotation); - if (this.getAnimating()) { - this.cancelAnimations(); - } -}; - - -/** - * Zoom to a specific zoom level. - * @param {number} zoom Zoom level. - * @api - */ -ol.View.prototype.setZoom = function(zoom) { - this.setResolution(this.getResolutionForZoom(zoom)); -}; - - -/** - * @param {olx.ViewOptions} options View options. - * @private - * @return {ol.CenterConstraintType} The constraint. - */ -ol.View.createCenterConstraint_ = function(options) { - if (options.extent !== undefined) { - return ol.CenterConstraint.createExtent(options.extent); - } else { - return ol.CenterConstraint.none; - } -}; - - -/** - * @private - * @param {olx.ViewOptions} options View options. - * @return {{constraint: ol.ResolutionConstraintType, maxResolution: number, - * minResolution: number, zoomFactor: number}} The constraint. - */ -ol.View.createResolutionConstraint_ = function(options) { - var resolutionConstraint; - var maxResolution; - var minResolution; - - // TODO: move these to be ol constants - // see https://github.com/openlayers/openlayers/issues/2076 - var defaultMaxZoom = 28; - var defaultZoomFactor = 2; - - var minZoom = options.minZoom !== undefined ? - options.minZoom : ol.DEFAULT_MIN_ZOOM; - - var maxZoom = options.maxZoom !== undefined ? - options.maxZoom : defaultMaxZoom; - - var zoomFactor = options.zoomFactor !== undefined ? - options.zoomFactor : defaultZoomFactor; - - if (options.resolutions !== undefined) { - var resolutions = options.resolutions; - maxResolution = resolutions[0]; - minResolution = resolutions[resolutions.length - 1]; - resolutionConstraint = ol.ResolutionConstraint.createSnapToResolutions( - resolutions); - } else { - // calculate the default min and max resolution - var projection = ol.proj.createProjection(options.projection, 'EPSG:3857'); - var extent = projection.getExtent(); - var size = !extent ? - // use an extent that can fit the whole world if need be - 360 * ol.proj.METERS_PER_UNIT[ol.proj.Units.DEGREES] / - projection.getMetersPerUnit() : - Math.max(ol.extent.getWidth(extent), ol.extent.getHeight(extent)); - - var defaultMaxResolution = size / ol.DEFAULT_TILE_SIZE / Math.pow( - defaultZoomFactor, ol.DEFAULT_MIN_ZOOM); - - var defaultMinResolution = defaultMaxResolution / Math.pow( - defaultZoomFactor, defaultMaxZoom - ol.DEFAULT_MIN_ZOOM); - - // user provided maxResolution takes precedence - maxResolution = options.maxResolution; - if (maxResolution !== undefined) { - minZoom = 0; - } else { - maxResolution = defaultMaxResolution / Math.pow(zoomFactor, minZoom); - } - - // user provided minResolution takes precedence - minResolution = options.minResolution; - if (minResolution === undefined) { - if (options.maxZoom !== undefined) { - if (options.maxResolution !== undefined) { - minResolution = maxResolution / Math.pow(zoomFactor, maxZoom); - } else { - minResolution = defaultMaxResolution / Math.pow(zoomFactor, maxZoom); - } - } else { - minResolution = defaultMinResolution; - } - } - - // given discrete zoom levels, minResolution may be different than provided - maxZoom = minZoom + Math.floor( - Math.log(maxResolution / minResolution) / Math.log(zoomFactor)); - minResolution = maxResolution / Math.pow(zoomFactor, maxZoom - minZoom); - - resolutionConstraint = ol.ResolutionConstraint.createSnapToPower( - zoomFactor, maxResolution, maxZoom - minZoom); - } - return {constraint: resolutionConstraint, maxResolution: maxResolution, - minResolution: minResolution, minZoom: minZoom, zoomFactor: zoomFactor}; -}; - - -/** - * @private - * @param {olx.ViewOptions} options View options. - * @return {ol.RotationConstraintType} Rotation constraint. - */ -ol.View.createRotationConstraint_ = function(options) { - var enableRotation = options.enableRotation !== undefined ? - options.enableRotation : true; - if (enableRotation) { - var constrainRotation = options.constrainRotation; - if (constrainRotation === undefined || constrainRotation === true) { - return ol.RotationConstraint.createSnapToZero(); - } else if (constrainRotation === false) { - return ol.RotationConstraint.none; - } else if (typeof constrainRotation === 'number') { - return ol.RotationConstraint.createSnapToN(constrainRotation); - } else { - return ol.RotationConstraint.none; - } - } else { - return ol.RotationConstraint.disable; - } -}; - - -/** - * Determine if an animation involves no view change. - * @param {ol.ViewAnimation} animation The animation. - * @return {boolean} The animation involves no view change. - */ -ol.View.isNoopAnimation = function(animation) { - if (animation.sourceCenter && animation.targetCenter) { - if (!ol.coordinate.equals(animation.sourceCenter, animation.targetCenter)) { - return false; - } - } - if (animation.sourceResolution !== animation.targetResolution) { - return false; - } - if (animation.sourceRotation !== animation.targetRotation) { - return false; - } - return true; -}; - -goog.provide('ol.dom'); - - -/** - * Create an html canvas element and returns its 2d context. - * @param {number=} opt_width Canvas width. - * @param {number=} opt_height Canvas height. - * @return {CanvasRenderingContext2D} The context. - */ -ol.dom.createCanvasContext2D = function(opt_width, opt_height) { - var canvas = document.createElement('CANVAS'); - if (opt_width) { - canvas.width = opt_width; - } - if (opt_height) { - canvas.height = opt_height; - } - return canvas.getContext('2d'); -}; - - -/** - * Get the current computed width for the given element including margin, - * padding and border. - * Equivalent to jQuery's `$(el).outerWidth(true)`. - * @param {!Element} element Element. - * @return {number} The width. - */ -ol.dom.outerWidth = function(element) { - var width = element.offsetWidth; - var style = getComputedStyle(element); - width += parseInt(style.marginLeft, 10) + parseInt(style.marginRight, 10); - - return width; -}; - - -/** - * Get the current computed height for the given element including margin, - * padding and border. - * Equivalent to jQuery's `$(el).outerHeight(true)`. - * @param {!Element} element Element. - * @return {number} The height. - */ -ol.dom.outerHeight = function(element) { - var height = element.offsetHeight; - var style = getComputedStyle(element); - height += parseInt(style.marginTop, 10) + parseInt(style.marginBottom, 10); - - return height; -}; - -/** - * @param {Node} newNode Node to replace old node - * @param {Node} oldNode The node to be replaced - */ -ol.dom.replaceNode = function(newNode, oldNode) { - var parent = oldNode.parentNode; - if (parent) { - parent.replaceChild(newNode, oldNode); - } -}; - -/** - * @param {Node} node The node to remove. - * @returns {Node} The node that was removed or null. - */ -ol.dom.removeNode = function(node) { - return node && node.parentNode ? node.parentNode.removeChild(node) : null; -}; - -/** - * @param {Node} node The node to remove the children from. - */ -ol.dom.removeChildren = function(node) { - while (node.lastChild) { - node.removeChild(node.lastChild); - } -}; - -goog.provide('ol.layer.Property'); - -/** - * @enum {string} - */ -ol.layer.Property = { - OPACITY: 'opacity', - VISIBLE: 'visible', - EXTENT: 'extent', - Z_INDEX: 'zIndex', - MAX_RESOLUTION: 'maxResolution', - MIN_RESOLUTION: 'minResolution', - SOURCE: 'source' -}; - -goog.provide('ol.layer.Base'); - -goog.require('ol'); -goog.require('ol.Object'); -goog.require('ol.layer.Property'); -goog.require('ol.math'); -goog.require('ol.obj'); - - -/** - * @classdesc - * Abstract base class; normally only used for creating subclasses and not - * instantiated in apps. - * Note that with `ol.layer.Base` and all its subclasses, any property set in - * the options is set as a {@link ol.Object} property on the layer object, so - * is observable, and has get/set accessors. - * - * @constructor - * @abstract - * @extends {ol.Object} - * @param {olx.layer.BaseOptions} options Layer options. - * @api - */ -ol.layer.Base = function(options) { - - ol.Object.call(this); - - /** - * @type {Object.<string, *>} - */ - var properties = ol.obj.assign({}, options); - properties[ol.layer.Property.OPACITY] = - options.opacity !== undefined ? options.opacity : 1; - properties[ol.layer.Property.VISIBLE] = - options.visible !== undefined ? options.visible : true; - properties[ol.layer.Property.Z_INDEX] = - options.zIndex !== undefined ? options.zIndex : 0; - properties[ol.layer.Property.MAX_RESOLUTION] = - options.maxResolution !== undefined ? options.maxResolution : Infinity; - properties[ol.layer.Property.MIN_RESOLUTION] = - options.minResolution !== undefined ? options.minResolution : 0; - - this.setProperties(properties); - - /** - * @type {ol.LayerState} - * @private - */ - this.state_ = /** @type {ol.LayerState} */ ({ - layer: /** @type {ol.layer.Layer} */ (this), - managed: true - }); - - /** - * The layer type. - * @type {ol.LayerType} - * @protected; - */ - this.type; - -}; -ol.inherits(ol.layer.Base, ol.Object); - - -/** - * Get the layer type (used when creating a layer renderer). - * @return {ol.LayerType} The layer type. - */ -ol.layer.Base.prototype.getType = function() { - return this.type; -}; - - -/** - * @return {ol.LayerState} Layer state. - */ -ol.layer.Base.prototype.getLayerState = function() { - this.state_.opacity = ol.math.clamp(this.getOpacity(), 0, 1); - this.state_.sourceState = this.getSourceState(); - this.state_.visible = this.getVisible(); - this.state_.extent = this.getExtent(); - this.state_.zIndex = this.getZIndex(); - this.state_.maxResolution = this.getMaxResolution(); - this.state_.minResolution = Math.max(this.getMinResolution(), 0); - - return this.state_; -}; - - -/** - * @abstract - * @param {Array.<ol.layer.Layer>=} opt_array Array of layers (to be - * modified in place). - * @return {Array.<ol.layer.Layer>} Array of layers. - */ -ol.layer.Base.prototype.getLayersArray = function(opt_array) {}; - - -/** - * @abstract - * @param {Array.<ol.LayerState>=} opt_states Optional list of layer - * states (to be modified in place). - * @return {Array.<ol.LayerState>} List of layer states. - */ -ol.layer.Base.prototype.getLayerStatesArray = function(opt_states) {}; - - -/** - * Return the {@link ol.Extent extent} of the layer or `undefined` if it - * will be visible regardless of extent. - * @return {ol.Extent|undefined} The layer extent. - * @observable - * @api - */ -ol.layer.Base.prototype.getExtent = function() { - return /** @type {ol.Extent|undefined} */ ( - this.get(ol.layer.Property.EXTENT)); -}; - - -/** - * Return the maximum resolution of the layer. - * @return {number} The maximum resolution of the layer. - * @observable - * @api - */ -ol.layer.Base.prototype.getMaxResolution = function() { - return /** @type {number} */ ( - this.get(ol.layer.Property.MAX_RESOLUTION)); -}; - - -/** - * Return the minimum resolution of the layer. - * @return {number} The minimum resolution of the layer. - * @observable - * @api - */ -ol.layer.Base.prototype.getMinResolution = function() { - return /** @type {number} */ ( - this.get(ol.layer.Property.MIN_RESOLUTION)); -}; - - -/** - * Return the opacity of the layer (between 0 and 1). - * @return {number} The opacity of the layer. - * @observable - * @api - */ -ol.layer.Base.prototype.getOpacity = function() { - return /** @type {number} */ (this.get(ol.layer.Property.OPACITY)); -}; - - -/** - * @abstract - * @return {ol.source.State} Source state. - */ -ol.layer.Base.prototype.getSourceState = function() {}; - - -/** - * Return the visibility of the layer (`true` or `false`). - * @return {boolean} The visibility of the layer. - * @observable - * @api - */ -ol.layer.Base.prototype.getVisible = function() { - return /** @type {boolean} */ (this.get(ol.layer.Property.VISIBLE)); -}; - - -/** - * Return the Z-index of the layer, which is used to order layers before - * rendering. The default Z-index is 0. - * @return {number} The Z-index of the layer. - * @observable - * @api - */ -ol.layer.Base.prototype.getZIndex = function() { - return /** @type {number} */ (this.get(ol.layer.Property.Z_INDEX)); -}; - - -/** - * Set the extent at which the layer is visible. If `undefined`, the layer - * will be visible at all extents. - * @param {ol.Extent|undefined} extent The extent of the layer. - * @observable - * @api - */ -ol.layer.Base.prototype.setExtent = function(extent) { - this.set(ol.layer.Property.EXTENT, extent); -}; - - -/** - * Set the maximum resolution at which the layer is visible. - * @param {number} maxResolution The maximum resolution of the layer. - * @observable - * @api - */ -ol.layer.Base.prototype.setMaxResolution = function(maxResolution) { - this.set(ol.layer.Property.MAX_RESOLUTION, maxResolution); -}; - - -/** - * Set the minimum resolution at which the layer is visible. - * @param {number} minResolution The minimum resolution of the layer. - * @observable - * @api - */ -ol.layer.Base.prototype.setMinResolution = function(minResolution) { - this.set(ol.layer.Property.MIN_RESOLUTION, minResolution); -}; - - -/** - * Set the opacity of the layer, allowed values range from 0 to 1. - * @param {number} opacity The opacity of the layer. - * @observable - * @api - */ -ol.layer.Base.prototype.setOpacity = function(opacity) { - this.set(ol.layer.Property.OPACITY, opacity); -}; - - -/** - * Set the visibility of the layer (`true` or `false`). - * @param {boolean} visible The visibility of the layer. - * @observable - * @api - */ -ol.layer.Base.prototype.setVisible = function(visible) { - this.set(ol.layer.Property.VISIBLE, visible); -}; - - -/** - * Set Z-index of the layer, which is used to order layers before rendering. - * The default Z-index is 0. - * @param {number} zindex The z-index of the layer. - * @observable - * @api - */ -ol.layer.Base.prototype.setZIndex = function(zindex) { - this.set(ol.layer.Property.Z_INDEX, zindex); -}; - -goog.provide('ol.source.State'); - - -/** - * State of the source, one of 'undefined', 'loading', 'ready' or 'error'. - * @enum {string} - */ -ol.source.State = { - UNDEFINED: 'undefined', - LOADING: 'loading', - READY: 'ready', - ERROR: 'error' -}; - - -goog.provide('ol.layer.Group'); - -goog.require('ol'); -goog.require('ol.Collection'); -goog.require('ol.CollectionEventType'); -goog.require('ol.Object'); -goog.require('ol.ObjectEventType'); -goog.require('ol.asserts'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.extent'); -goog.require('ol.layer.Base'); -goog.require('ol.obj'); -goog.require('ol.source.State'); - - -/** - * @classdesc - * A {@link ol.Collection} of layers that are handled together. - * - * A generic `change` event is triggered when the group/Collection changes. - * - * @constructor - * @extends {ol.layer.Base} - * @param {olx.layer.GroupOptions=} opt_options Layer options. - * @api - */ -ol.layer.Group = function(opt_options) { - - var options = opt_options || {}; - var baseOptions = /** @type {olx.layer.GroupOptions} */ - (ol.obj.assign({}, options)); - delete baseOptions.layers; - - var layers = options.layers; - - ol.layer.Base.call(this, baseOptions); - - /** - * @private - * @type {Array.<ol.EventsKey>} - */ - this.layersListenerKeys_ = []; - - /** - * @private - * @type {Object.<string, Array.<ol.EventsKey>>} - */ - this.listenerKeys_ = {}; - - ol.events.listen(this, - ol.Object.getChangeEventType(ol.layer.Group.Property_.LAYERS), - this.handleLayersChanged_, this); - - if (layers) { - if (Array.isArray(layers)) { - layers = new ol.Collection(layers.slice(), {unique: true}); - } else { - ol.asserts.assert(layers instanceof ol.Collection, - 43); // Expected `layers` to be an array or an `ol.Collection` - layers = layers; - } - } else { - layers = new ol.Collection(undefined, {unique: true}); - } - - this.setLayers(layers); - -}; -ol.inherits(ol.layer.Group, ol.layer.Base); - - -/** - * @private - */ -ol.layer.Group.prototype.handleLayerChange_ = function() { - this.changed(); -}; - - -/** - * @param {ol.events.Event} event Event. - * @private - */ -ol.layer.Group.prototype.handleLayersChanged_ = function(event) { - this.layersListenerKeys_.forEach(ol.events.unlistenByKey); - this.layersListenerKeys_.length = 0; - - var layers = this.getLayers(); - this.layersListenerKeys_.push( - ol.events.listen(layers, ol.CollectionEventType.ADD, - this.handleLayersAdd_, this), - ol.events.listen(layers, ol.CollectionEventType.REMOVE, - this.handleLayersRemove_, this)); - - for (var id in this.listenerKeys_) { - this.listenerKeys_[id].forEach(ol.events.unlistenByKey); - } - ol.obj.clear(this.listenerKeys_); - - var layersArray = layers.getArray(); - var i, ii, layer; - for (i = 0, ii = layersArray.length; i < ii; i++) { - layer = layersArray[i]; - this.listenerKeys_[ol.getUid(layer).toString()] = [ - ol.events.listen(layer, ol.ObjectEventType.PROPERTYCHANGE, - this.handleLayerChange_, this), - ol.events.listen(layer, ol.events.EventType.CHANGE, - this.handleLayerChange_, this) - ]; - } - - this.changed(); -}; - - -/** - * @param {ol.Collection.Event} collectionEvent Collection event. - * @private - */ -ol.layer.Group.prototype.handleLayersAdd_ = function(collectionEvent) { - var layer = /** @type {ol.layer.Base} */ (collectionEvent.element); - var key = ol.getUid(layer).toString(); - this.listenerKeys_[key] = [ - ol.events.listen(layer, ol.ObjectEventType.PROPERTYCHANGE, - this.handleLayerChange_, this), - ol.events.listen(layer, ol.events.EventType.CHANGE, - this.handleLayerChange_, this) - ]; - this.changed(); -}; - - -/** - * @param {ol.Collection.Event} collectionEvent Collection event. - * @private - */ -ol.layer.Group.prototype.handleLayersRemove_ = function(collectionEvent) { - var layer = /** @type {ol.layer.Base} */ (collectionEvent.element); - var key = ol.getUid(layer).toString(); - this.listenerKeys_[key].forEach(ol.events.unlistenByKey); - delete this.listenerKeys_[key]; - this.changed(); -}; - - -/** - * Returns the {@link ol.Collection collection} of {@link ol.layer.Layer layers} - * in this group. - * @return {!ol.Collection.<ol.layer.Base>} Collection of - * {@link ol.layer.Base layers} that are part of this group. - * @observable - * @api - */ -ol.layer.Group.prototype.getLayers = function() { - return /** @type {!ol.Collection.<ol.layer.Base>} */ (this.get( - ol.layer.Group.Property_.LAYERS)); -}; - - -/** - * Set the {@link ol.Collection collection} of {@link ol.layer.Layer layers} - * in this group. - * @param {!ol.Collection.<ol.layer.Base>} layers Collection of - * {@link ol.layer.Base layers} that are part of this group. - * @observable - * @api - */ -ol.layer.Group.prototype.setLayers = function(layers) { - this.set(ol.layer.Group.Property_.LAYERS, layers); -}; - - -/** - * @inheritDoc - */ -ol.layer.Group.prototype.getLayersArray = function(opt_array) { - var array = opt_array !== undefined ? opt_array : []; - this.getLayers().forEach(function(layer) { - layer.getLayersArray(array); - }); - return array; -}; - - -/** - * @inheritDoc - */ -ol.layer.Group.prototype.getLayerStatesArray = function(opt_states) { - var states = opt_states !== undefined ? opt_states : []; - - var pos = states.length; - - this.getLayers().forEach(function(layer) { - layer.getLayerStatesArray(states); - }); - - var ownLayerState = this.getLayerState(); - var i, ii, layerState; - for (i = pos, ii = states.length; i < ii; i++) { - layerState = states[i]; - layerState.opacity *= ownLayerState.opacity; - layerState.visible = layerState.visible && ownLayerState.visible; - layerState.maxResolution = Math.min( - layerState.maxResolution, ownLayerState.maxResolution); - layerState.minResolution = Math.max( - layerState.minResolution, ownLayerState.minResolution); - if (ownLayerState.extent !== undefined) { - if (layerState.extent !== undefined) { - layerState.extent = ol.extent.getIntersection( - layerState.extent, ownLayerState.extent); - } else { - layerState.extent = ownLayerState.extent; - } - } - } - - return states; -}; - - -/** - * @inheritDoc - */ -ol.layer.Group.prototype.getSourceState = function() { - return ol.source.State.READY; -}; - -/** - * @enum {string} - * @private - */ -ol.layer.Group.Property_ = { - LAYERS: 'layers' -}; - -goog.provide('ol.PluginType'); - -/** - * A plugin type used when registering a plugin. The supported plugin types are - * 'MAP_RENDERER', and 'LAYER_RENDERER'. - * @enum {string} - */ -ol.PluginType = { - MAP_RENDERER: 'MAP_RENDERER', - LAYER_RENDERER: 'LAYER_RENDERER' -}; - -goog.provide('ol.plugins'); - -goog.require('ol.PluginType'); - -/** - * The registry of map renderer plugins. - * @type {Array<olx.MapRendererPlugin>} - * @private - */ -ol.plugins.mapRendererPlugins_ = []; - - -/** - * Get all registered map renderer plugins. - * @return {Array<olx.MapRendererPlugin>} The registered map renderer plugins. - */ -ol.plugins.getMapRendererPlugins = function() { - return ol.plugins.mapRendererPlugins_; -}; - - -/** - * The registry of layer renderer plugins. - * @type {Array<olx.LayerRendererPlugin>} - * @private - */ -ol.plugins.layerRendererPlugins_ = []; - - -/** - * Get all registered layer renderer plugins. - * @return {Array<olx.LayerRendererPlugin>} The registered layer renderer plugins. - */ -ol.plugins.getLayerRendererPlugins = function() { - return ol.plugins.layerRendererPlugins_; -}; - - -/** - * Register a plugin. - * @param {ol.PluginType} type The plugin type. - * @param {*} plugin The plugin. - */ -ol.plugins.register = function(type, plugin) { - var plugins; - switch (type) { - case ol.PluginType.MAP_RENDERER: { - plugins = ol.plugins.mapRendererPlugins_; - plugins.push(/** @type {olx.MapRendererPlugin} */ (plugin)); - break; - } - case ol.PluginType.LAYER_RENDERER: { - plugins = ol.plugins.layerRendererPlugins_; - plugins.push(/** @type {olx.LayerRendererPlugin} */ (plugin)); - break; - } - default: { - throw new Error('Unsupported plugin type: ' + type); - } - } -}; - - -/** - * Register multiple plugins. - * @param {ol.PluginType} type The plugin type. - * @param {Array} plugins The plugins. - */ -ol.plugins.registerMultiple = function(type, plugins) { - for (var i = 0, ii = plugins.length; i < ii; ++i) { - ol.plugins.register(type, plugins[i]); - } -}; - -goog.provide('ol.renderer.Type'); - - -/** - * Available renderers: `'canvas'` or `'webgl'`. - * @enum {string} - */ -ol.renderer.Type = { - CANVAS: 'canvas', - WEBGL: 'webgl' -}; - -goog.provide('ol.PluggableMap'); - -goog.require('ol'); -goog.require('ol.Collection'); -goog.require('ol.CollectionEventType'); -goog.require('ol.MapBrowserEvent'); -goog.require('ol.MapBrowserEventHandler'); -goog.require('ol.MapBrowserEventType'); -goog.require('ol.MapEvent'); -goog.require('ol.MapEventType'); -goog.require('ol.MapProperty'); -goog.require('ol.Object'); -goog.require('ol.ObjectEventType'); -goog.require('ol.TileQueue'); -goog.require('ol.View'); -goog.require('ol.ViewHint'); -goog.require('ol.asserts'); -goog.require('ol.dom'); -goog.require('ol.events'); -goog.require('ol.events.Event'); -goog.require('ol.events.EventType'); -goog.require('ol.extent'); -goog.require('ol.functions'); -goog.require('ol.has'); -goog.require('ol.layer.Group'); -goog.require('ol.obj'); -goog.require('ol.plugins'); -goog.require('ol.renderer.Type'); -goog.require('ol.size'); -goog.require('ol.structs.PriorityQueue'); -goog.require('ol.transform'); - - -/** - * @constructor - * @extends {ol.Object} - * @param {olx.MapOptions} options Map options. - * @fires ol.MapBrowserEvent - * @fires ol.MapEvent - * @fires ol.render.Event#postcompose - * @fires ol.render.Event#precompose - * @api - */ -ol.PluggableMap = function(options) { - - ol.Object.call(this); - - var optionsInternal = ol.PluggableMap.createOptionsInternal(options); - - /** - * @type {boolean} - * @private - */ - this.loadTilesWhileAnimating_ = - options.loadTilesWhileAnimating !== undefined ? - options.loadTilesWhileAnimating : false; - - /** - * @type {boolean} - * @private - */ - this.loadTilesWhileInteracting_ = - options.loadTilesWhileInteracting !== undefined ? - options.loadTilesWhileInteracting : false; - - /** - * @private - * @type {number} - */ - this.pixelRatio_ = options.pixelRatio !== undefined ? - options.pixelRatio : ol.has.DEVICE_PIXEL_RATIO; - - /** - * @private - * @type {Object.<string, string>} - */ - this.logos_ = optionsInternal.logos; - - /** - * @private - * @type {number|undefined} - */ - this.animationDelayKey_; - - /** - * @private - */ - this.animationDelay_ = function() { - this.animationDelayKey_ = undefined; - this.renderFrame_.call(this, Date.now()); - }.bind(this); - - /** - * @private - * @type {ol.Transform} - */ - this.coordinateToPixelTransform_ = ol.transform.create(); - - /** - * @private - * @type {ol.Transform} - */ - this.pixelToCoordinateTransform_ = ol.transform.create(); - - /** - * @private - * @type {number} - */ - this.frameIndex_ = 0; - - /** - * @private - * @type {?olx.FrameState} - */ - this.frameState_ = null; - - /** - * The extent at the previous 'moveend' event. - * @private - * @type {ol.Extent} - */ - this.previousExtent_ = null; - - /** - * @private - * @type {?ol.EventsKey} - */ - this.viewPropertyListenerKey_ = null; - - /** - * @private - * @type {?ol.EventsKey} - */ - this.viewChangeListenerKey_ = null; - - /** - * @private - * @type {Array.<ol.EventsKey>} - */ - this.layerGroupPropertyListenerKeys_ = null; - - /** - * @private - * @type {Element} - */ - this.viewport_ = document.createElement('DIV'); - this.viewport_.className = 'ol-viewport' + (ol.has.TOUCH ? ' ol-touch' : ''); - this.viewport_.style.position = 'relative'; - this.viewport_.style.overflow = 'hidden'; - this.viewport_.style.width = '100%'; - this.viewport_.style.height = '100%'; - // prevent page zoom on IE >= 10 browsers - this.viewport_.style.msTouchAction = 'none'; - this.viewport_.style.touchAction = 'none'; - - /** - * @private - * @type {!Element} - */ - this.overlayContainer_ = document.createElement('DIV'); - this.overlayContainer_.className = 'ol-overlaycontainer'; - this.viewport_.appendChild(this.overlayContainer_); - - /** - * @private - * @type {!Element} - */ - this.overlayContainerStopEvent_ = document.createElement('DIV'); - this.overlayContainerStopEvent_.className = 'ol-overlaycontainer-stopevent'; - var overlayEvents = [ - ol.events.EventType.CLICK, - ol.events.EventType.DBLCLICK, - ol.events.EventType.MOUSEDOWN, - ol.events.EventType.TOUCHSTART, - ol.events.EventType.MSPOINTERDOWN, - ol.MapBrowserEventType.POINTERDOWN, - ol.events.EventType.MOUSEWHEEL, - ol.events.EventType.WHEEL - ]; - for (var i = 0, ii = overlayEvents.length; i < ii; ++i) { - ol.events.listen(this.overlayContainerStopEvent_, overlayEvents[i], - ol.events.Event.stopPropagation); - } - this.viewport_.appendChild(this.overlayContainerStopEvent_); - - /** - * @private - * @type {ol.MapBrowserEventHandler} - */ - this.mapBrowserEventHandler_ = new ol.MapBrowserEventHandler(this, options.moveTolerance); - for (var key in ol.MapBrowserEventType) { - ol.events.listen(this.mapBrowserEventHandler_, ol.MapBrowserEventType[key], - this.handleMapBrowserEvent, this); - } - - /** - * @private - * @type {Element|Document} - */ - this.keyboardEventTarget_ = optionsInternal.keyboardEventTarget; - - /** - * @private - * @type {Array.<ol.EventsKey>} - */ - this.keyHandlerKeys_ = null; - - ol.events.listen(this.viewport_, ol.events.EventType.WHEEL, - this.handleBrowserEvent, this); - ol.events.listen(this.viewport_, ol.events.EventType.MOUSEWHEEL, - this.handleBrowserEvent, this); - - /** - * @type {ol.Collection.<ol.control.Control>} - * @protected - */ - this.controls = optionsInternal.controls || new ol.Collection(); - - /** - * @type {ol.Collection.<ol.interaction.Interaction>} - * @protected - */ - this.interactions = optionsInternal.interactions || new ol.Collection(); - - /** - * @type {ol.Collection.<ol.Overlay>} - * @private - */ - this.overlays_ = optionsInternal.overlays; - - /** - * A lookup of overlays by id. - * @private - * @type {Object.<string, ol.Overlay>} - */ - this.overlayIdIndex_ = {}; - - /** - * @type {ol.renderer.Map} - * @private - */ - this.renderer_ = optionsInternal.mapRendererPlugin.create(this.viewport_, this); - - /** - * @type {function(Event)|undefined} - * @private - */ - this.handleResize_; - - /** - * @private - * @type {ol.Coordinate} - */ - this.focus_ = null; - - /** - * @private - * @type {Array.<ol.PostRenderFunction>} - */ - this.postRenderFunctions_ = []; - - /** - * @private - * @type {ol.TileQueue} - */ - this.tileQueue_ = new ol.TileQueue( - this.getTilePriority.bind(this), - this.handleTileChange_.bind(this)); - - /** - * Uids of features to skip at rendering time. - * @type {Object.<string, boolean>} - * @private - */ - this.skippedFeatureUids_ = {}; - - ol.events.listen( - this, ol.Object.getChangeEventType(ol.MapProperty.LAYERGROUP), - this.handleLayerGroupChanged_, this); - ol.events.listen(this, ol.Object.getChangeEventType(ol.MapProperty.VIEW), - this.handleViewChanged_, this); - ol.events.listen(this, ol.Object.getChangeEventType(ol.MapProperty.SIZE), - this.handleSizeChanged_, this); - ol.events.listen(this, ol.Object.getChangeEventType(ol.MapProperty.TARGET), - this.handleTargetChanged_, this); - - // setProperties will trigger the rendering of the map if the map - // is "defined" already. - this.setProperties(optionsInternal.values); - - this.controls.forEach( - /** - * @param {ol.control.Control} control Control. - * @this {ol.PluggableMap} - */ - function(control) { - control.setMap(this); - }, this); - - ol.events.listen(this.controls, ol.CollectionEventType.ADD, - /** - * @param {ol.Collection.Event} event Collection event. - */ - function(event) { - event.element.setMap(this); - }, this); - - ol.events.listen(this.controls, ol.CollectionEventType.REMOVE, - /** - * @param {ol.Collection.Event} event Collection event. - */ - function(event) { - event.element.setMap(null); - }, this); - - this.interactions.forEach( - /** - * @param {ol.interaction.Interaction} interaction Interaction. - * @this {ol.PluggableMap} - */ - function(interaction) { - interaction.setMap(this); - }, this); - - ol.events.listen(this.interactions, ol.CollectionEventType.ADD, - /** - * @param {ol.Collection.Event} event Collection event. - */ - function(event) { - event.element.setMap(this); - }, this); - - ol.events.listen(this.interactions, ol.CollectionEventType.REMOVE, - /** - * @param {ol.Collection.Event} event Collection event. - */ - function(event) { - event.element.setMap(null); - }, this); - - this.overlays_.forEach(this.addOverlayInternal_, this); - - ol.events.listen(this.overlays_, ol.CollectionEventType.ADD, - /** - * @param {ol.Collection.Event} event Collection event. - */ - function(event) { - this.addOverlayInternal_(/** @type {ol.Overlay} */ (event.element)); - }, this); - - ol.events.listen(this.overlays_, ol.CollectionEventType.REMOVE, - /** - * @param {ol.Collection.Event} event Collection event. - */ - function(event) { - var overlay = /** @type {ol.Overlay} */ (event.element); - var id = overlay.getId(); - if (id !== undefined) { - delete this.overlayIdIndex_[id.toString()]; - } - event.element.setMap(null); - }, this); - -}; -ol.inherits(ol.PluggableMap, ol.Object); - - -/** - * Add the given control to the map. - * @param {ol.control.Control} control Control. - * @api - */ -ol.PluggableMap.prototype.addControl = function(control) { - this.getControls().push(control); -}; - - -/** - * Add the given interaction to the map. - * @param {ol.interaction.Interaction} interaction Interaction to add. - * @api - */ -ol.PluggableMap.prototype.addInteraction = function(interaction) { - this.getInteractions().push(interaction); -}; - - -/** - * Adds the given layer to the top of this map. If you want to add a layer - * elsewhere in the stack, use `getLayers()` and the methods available on - * {@link ol.Collection}. - * @param {ol.layer.Base} layer Layer. - * @api - */ -ol.PluggableMap.prototype.addLayer = function(layer) { - var layers = this.getLayerGroup().getLayers(); - layers.push(layer); -}; - - -/** - * Add the given overlay to the map. - * @param {ol.Overlay} overlay Overlay. - * @api - */ -ol.PluggableMap.prototype.addOverlay = function(overlay) { - this.getOverlays().push(overlay); -}; - - -/** - * This deals with map's overlay collection changes. - * @param {ol.Overlay} overlay Overlay. - * @private - */ -ol.PluggableMap.prototype.addOverlayInternal_ = function(overlay) { - var id = overlay.getId(); - if (id !== undefined) { - this.overlayIdIndex_[id.toString()] = overlay; - } - overlay.setMap(this); -}; - - -/** - * - * @inheritDoc - */ -ol.PluggableMap.prototype.disposeInternal = function() { - this.mapBrowserEventHandler_.dispose(); - this.renderer_.dispose(); - ol.events.unlisten(this.viewport_, ol.events.EventType.WHEEL, - this.handleBrowserEvent, this); - ol.events.unlisten(this.viewport_, ol.events.EventType.MOUSEWHEEL, - this.handleBrowserEvent, this); - if (this.handleResize_ !== undefined) { - window.removeEventListener(ol.events.EventType.RESIZE, - this.handleResize_, false); - this.handleResize_ = undefined; - } - if (this.animationDelayKey_) { - cancelAnimationFrame(this.animationDelayKey_); - this.animationDelayKey_ = undefined; - } - this.setTarget(null); - ol.Object.prototype.disposeInternal.call(this); -}; - - -/** - * Detect features that intersect a pixel on the viewport, and execute a - * callback with each intersecting feature. Layers included in the detection can - * be configured through the `layerFilter` option in `opt_options`. - * @param {ol.Pixel} pixel Pixel. - * @param {function(this: S, (ol.Feature|ol.render.Feature), - * ol.layer.Layer): T} callback Feature callback. The callback will be - * called with two arguments. The first argument is one - * {@link ol.Feature feature} or - * {@link ol.render.Feature render feature} at the pixel, the second is - * the {@link ol.layer.Layer layer} of the feature and will be null for - * unmanaged layers. To stop detection, callback functions can return a - * truthy value. - * @param {olx.AtPixelOptions=} opt_options Optional options. - * @return {T|undefined} Callback result, i.e. the return value of last - * callback execution, or the first truthy callback return value. - * @template S,T - * @api - */ -ol.PluggableMap.prototype.forEachFeatureAtPixel = function(pixel, callback, opt_options) { - if (!this.frameState_) { - return; - } - var coordinate = this.getCoordinateFromPixel(pixel); - opt_options = opt_options !== undefined ? opt_options : {}; - var hitTolerance = opt_options.hitTolerance !== undefined ? - opt_options.hitTolerance * this.frameState_.pixelRatio : 0; - var layerFilter = opt_options.layerFilter !== undefined ? - opt_options.layerFilter : ol.functions.TRUE; - return this.renderer_.forEachFeatureAtCoordinate( - coordinate, this.frameState_, hitTolerance, callback, null, - layerFilter, null); -}; - - -/** - * Get all features that intersect a pixel on the viewport. - * @param {ol.Pixel} pixel Pixel. - * @param {olx.AtPixelOptions=} opt_options Optional options. - * @return {Array.<ol.Feature|ol.render.Feature>} The detected features or - * `null` if none were found. - * @api - */ -ol.PluggableMap.prototype.getFeaturesAtPixel = function(pixel, opt_options) { - var features = null; - this.forEachFeatureAtPixel(pixel, function(feature) { - if (!features) { - features = []; - } - features.push(feature); - }, opt_options); - return features; -}; - -/** - * Detect layers that have a color value at a pixel on the viewport, and - * execute a callback with each matching layer. Layers included in the - * detection can be configured through `opt_layerFilter`. - * @param {ol.Pixel} pixel Pixel. - * @param {function(this: S, ol.layer.Layer, (Uint8ClampedArray|Uint8Array)): T} callback - * Layer callback. This callback will receive two arguments: first is the - * {@link ol.layer.Layer layer}, second argument is an array representing - * [R, G, B, A] pixel values (0 - 255) and will be `null` for layer types - * that do not currently support this argument. To stop detection, callback - * functions can return a truthy value. - * @param {S=} opt_this Value to use as `this` when executing `callback`. - * @param {(function(this: U, ol.layer.Layer): boolean)=} opt_layerFilter Layer - * filter function. The filter function will receive one argument, the - * {@link ol.layer.Layer layer-candidate} and it should return a boolean - * value. Only layers which are visible and for which this function returns - * `true` will be tested for features. By default, all visible layers will - * be tested. - * @param {U=} opt_this2 Value to use as `this` when executing `layerFilter`. - * @return {T|undefined} Callback result, i.e. the return value of last - * callback execution, or the first truthy callback return value. - * @template S,T,U - * @api - */ -ol.PluggableMap.prototype.forEachLayerAtPixel = function(pixel, callback, opt_this, opt_layerFilter, opt_this2) { - if (!this.frameState_) { - return; - } - var thisArg = opt_this !== undefined ? opt_this : null; - var layerFilter = opt_layerFilter !== undefined ? - opt_layerFilter : ol.functions.TRUE; - var thisArg2 = opt_this2 !== undefined ? opt_this2 : null; - return this.renderer_.forEachLayerAtPixel( - pixel, this.frameState_, callback, thisArg, - layerFilter, thisArg2); -}; - - -/** - * Detect if features intersect a pixel on the viewport. Layers included in the - * detection can be configured through `opt_layerFilter`. - * @param {ol.Pixel} pixel Pixel. - * @param {olx.AtPixelOptions=} opt_options Optional options. - * @return {boolean} Is there a feature at the given pixel? - * @template U - * @api - */ -ol.PluggableMap.prototype.hasFeatureAtPixel = function(pixel, opt_options) { - if (!this.frameState_) { - return false; - } - var coordinate = this.getCoordinateFromPixel(pixel); - opt_options = opt_options !== undefined ? opt_options : {}; - var layerFilter = opt_options.layerFilter !== undefined ? - opt_options.layerFilter : ol.functions.TRUE; - var hitTolerance = opt_options.hitTolerance !== undefined ? - opt_options.hitTolerance * this.frameState_.pixelRatio : 0; - return this.renderer_.hasFeatureAtCoordinate( - coordinate, this.frameState_, hitTolerance, layerFilter, null); -}; - - -/** - * Returns the coordinate in view projection for a browser event. - * @param {Event} event Event. - * @return {ol.Coordinate} Coordinate. - * @api - */ -ol.PluggableMap.prototype.getEventCoordinate = function(event) { - return this.getCoordinateFromPixel(this.getEventPixel(event)); -}; - - -/** - * Returns the map pixel position for a browser event relative to the viewport. - * @param {Event} event Event. - * @return {ol.Pixel} Pixel. - * @api - */ -ol.PluggableMap.prototype.getEventPixel = function(event) { - var viewportPosition = this.viewport_.getBoundingClientRect(); - var eventPosition = event.changedTouches ? event.changedTouches[0] : event; - return [ - eventPosition.clientX - viewportPosition.left, - eventPosition.clientY - viewportPosition.top - ]; -}; - - -/** - * Get the target in which this map is rendered. - * Note that this returns what is entered as an option or in setTarget: - * if that was an element, it returns an element; if a string, it returns that. - * @return {Element|string|undefined} The Element or id of the Element that the - * map is rendered in. - * @observable - * @api - */ -ol.PluggableMap.prototype.getTarget = function() { - return /** @type {Element|string|undefined} */ ( - this.get(ol.MapProperty.TARGET)); -}; - - -/** - * Get the DOM element into which this map is rendered. In contrast to - * `getTarget` this method always return an `Element`, or `null` if the - * map has no target. - * @return {Element} The element that the map is rendered in. - * @api - */ -ol.PluggableMap.prototype.getTargetElement = function() { - var target = this.getTarget(); - if (target !== undefined) { - return typeof target === 'string' ? - document.getElementById(target) : - target; - } else { - return null; - } -}; - - -/** - * Get the coordinate for a given pixel. This returns a coordinate in the - * map view projection. - * @param {ol.Pixel} pixel Pixel position in the map viewport. - * @return {ol.Coordinate} The coordinate for the pixel position. - * @api - */ -ol.PluggableMap.prototype.getCoordinateFromPixel = function(pixel) { - var frameState = this.frameState_; - if (!frameState) { - return null; - } else { - return ol.transform.apply(frameState.pixelToCoordinateTransform, pixel.slice()); - } -}; - - -/** - * Get the map controls. Modifying this collection changes the controls - * associated with the map. - * @return {ol.Collection.<ol.control.Control>} Controls. - * @api - */ -ol.PluggableMap.prototype.getControls = function() { - return this.controls; -}; - - -/** - * Get the map overlays. Modifying this collection changes the overlays - * associated with the map. - * @return {ol.Collection.<ol.Overlay>} Overlays. - * @api - */ -ol.PluggableMap.prototype.getOverlays = function() { - return this.overlays_; -}; - - -/** - * Get an overlay by its identifier (the value returned by overlay.getId()). - * Note that the index treats string and numeric identifiers as the same. So - * `map.getOverlayById(2)` will return an overlay with id `'2'` or `2`. - * @param {string|number} id Overlay identifier. - * @return {ol.Overlay} Overlay. - * @api - */ -ol.PluggableMap.prototype.getOverlayById = function(id) { - var overlay = this.overlayIdIndex_[id.toString()]; - return overlay !== undefined ? overlay : null; -}; - - -/** - * Get the map interactions. Modifying this collection changes the interactions - * associated with the map. - * - * Interactions are used for e.g. pan, zoom and rotate. - * @return {ol.Collection.<ol.interaction.Interaction>} Interactions. - * @api - */ -ol.PluggableMap.prototype.getInteractions = function() { - return this.interactions; -}; - - -/** - * Get the layergroup associated with this map. - * @return {ol.layer.Group} A layer group containing the layers in this map. - * @observable - * @api - */ -ol.PluggableMap.prototype.getLayerGroup = function() { - return /** @type {ol.layer.Group} */ (this.get(ol.MapProperty.LAYERGROUP)); -}; - - -/** - * Get the collection of layers associated with this map. - * @return {!ol.Collection.<ol.layer.Base>} Layers. - * @api - */ -ol.PluggableMap.prototype.getLayers = function() { - var layers = this.getLayerGroup().getLayers(); - return layers; -}; - - -/** - * Get the pixel for a coordinate. This takes a coordinate in the map view - * projection and returns the corresponding pixel. - * @param {ol.Coordinate} coordinate A map coordinate. - * @return {ol.Pixel} A pixel position in the map viewport. - * @api - */ -ol.PluggableMap.prototype.getPixelFromCoordinate = function(coordinate) { - var frameState = this.frameState_; - if (!frameState) { - return null; - } else { - return ol.transform.apply(frameState.coordinateToPixelTransform, - coordinate.slice(0, 2)); - } -}; - - -/** - * Get the map renderer. - * @return {ol.renderer.Map} Renderer - */ -ol.PluggableMap.prototype.getRenderer = function() { - return this.renderer_; -}; - - -/** - * Get the size of this map. - * @return {ol.Size|undefined} The size in pixels of the map in the DOM. - * @observable - * @api - */ -ol.PluggableMap.prototype.getSize = function() { - return /** @type {ol.Size|undefined} */ (this.get(ol.MapProperty.SIZE)); -}; - - -/** - * Get the view associated with this map. A view manages properties such as - * center and resolution. - * @return {ol.View} The view that controls this map. - * @observable - * @api - */ -ol.PluggableMap.prototype.getView = function() { - return /** @type {ol.View} */ (this.get(ol.MapProperty.VIEW)); -}; - - -/** - * Get the element that serves as the map viewport. - * @return {Element} Viewport. - * @api - */ -ol.PluggableMap.prototype.getViewport = function() { - return this.viewport_; -}; - - -/** - * Get the element that serves as the container for overlays. Elements added to - * this container will let mousedown and touchstart events through to the map, - * so clicks and gestures on an overlay will trigger {@link ol.MapBrowserEvent} - * events. - * @return {!Element} The map's overlay container. - */ -ol.PluggableMap.prototype.getOverlayContainer = function() { - return this.overlayContainer_; -}; - - -/** - * Get the element that serves as a container for overlays that don't allow - * event propagation. Elements added to this container won't let mousedown and - * touchstart events through to the map, so clicks and gestures on an overlay - * don't trigger any {@link ol.MapBrowserEvent}. - * @return {!Element} The map's overlay container that stops events. - */ -ol.PluggableMap.prototype.getOverlayContainerStopEvent = function() { - return this.overlayContainerStopEvent_; -}; - - -/** - * @param {ol.Tile} tile Tile. - * @param {string} tileSourceKey Tile source key. - * @param {ol.Coordinate} tileCenter Tile center. - * @param {number} tileResolution Tile resolution. - * @return {number} Tile priority. - */ -ol.PluggableMap.prototype.getTilePriority = function(tile, tileSourceKey, tileCenter, tileResolution) { - // Filter out tiles at higher zoom levels than the current zoom level, or that - // are outside the visible extent. - var frameState = this.frameState_; - if (!frameState || !(tileSourceKey in frameState.wantedTiles)) { - return ol.structs.PriorityQueue.DROP; - } - if (!frameState.wantedTiles[tileSourceKey][tile.getKey()]) { - return ol.structs.PriorityQueue.DROP; - } - // Prioritize the highest zoom level tiles closest to the focus. - // Tiles at higher zoom levels are prioritized using Math.log(tileResolution). - // Within a zoom level, tiles are prioritized by the distance in pixels - // between the center of the tile and the focus. The factor of 65536 means - // that the prioritization should behave as desired for tiles up to - // 65536 * Math.log(2) = 45426 pixels from the focus. - var deltaX = tileCenter[0] - frameState.focus[0]; - var deltaY = tileCenter[1] - frameState.focus[1]; - return 65536 * Math.log(tileResolution) + - Math.sqrt(deltaX * deltaX + deltaY * deltaY) / tileResolution; -}; - - -/** - * @param {Event} browserEvent Browser event. - * @param {string=} opt_type Type. - */ -ol.PluggableMap.prototype.handleBrowserEvent = function(browserEvent, opt_type) { - var type = opt_type || browserEvent.type; - var mapBrowserEvent = new ol.MapBrowserEvent(type, this, browserEvent); - this.handleMapBrowserEvent(mapBrowserEvent); -}; - - -/** - * @param {ol.MapBrowserEvent} mapBrowserEvent The event to handle. - */ -ol.PluggableMap.prototype.handleMapBrowserEvent = function(mapBrowserEvent) { - if (!this.frameState_) { - // With no view defined, we cannot translate pixels into geographical - // coordinates so interactions cannot be used. - return; - } - this.focus_ = mapBrowserEvent.coordinate; - mapBrowserEvent.frameState = this.frameState_; - var interactionsArray = this.getInteractions().getArray(); - var i; - if (this.dispatchEvent(mapBrowserEvent) !== false) { - for (i = interactionsArray.length - 1; i >= 0; i--) { - var interaction = interactionsArray[i]; - if (!interaction.getActive()) { - continue; - } - var cont = interaction.handleEvent(mapBrowserEvent); - if (!cont) { - break; - } - } - } -}; - - -/** - * @protected - */ -ol.PluggableMap.prototype.handlePostRender = function() { - - var frameState = this.frameState_; - - // Manage the tile queue - // Image loads are expensive and a limited resource, so try to use them - // efficiently: - // * When the view is static we allow a large number of parallel tile loads - // to complete the frame as quickly as possible. - // * When animating or interacting, image loads can cause janks, so we reduce - // the maximum number of loads per frame and limit the number of parallel - // tile loads to remain reactive to view changes and to reduce the chance of - // loading tiles that will quickly disappear from view. - var tileQueue = this.tileQueue_; - if (!tileQueue.isEmpty()) { - var maxTotalLoading = 16; - var maxNewLoads = maxTotalLoading; - if (frameState) { - var hints = frameState.viewHints; - if (hints[ol.ViewHint.ANIMATING]) { - maxTotalLoading = this.loadTilesWhileAnimating_ ? 8 : 0; - maxNewLoads = 2; - } - if (hints[ol.ViewHint.INTERACTING]) { - maxTotalLoading = this.loadTilesWhileInteracting_ ? 8 : 0; - maxNewLoads = 2; - } - } - if (tileQueue.getTilesLoading() < maxTotalLoading) { - tileQueue.reprioritize(); // FIXME only call if view has changed - tileQueue.loadMoreTiles(maxTotalLoading, maxNewLoads); - } - } - - var postRenderFunctions = this.postRenderFunctions_; - var i, ii; - for (i = 0, ii = postRenderFunctions.length; i < ii; ++i) { - postRenderFunctions[i](this, frameState); - } - postRenderFunctions.length = 0; -}; - - -/** - * @private - */ -ol.PluggableMap.prototype.handleSizeChanged_ = function() { - this.render(); -}; - - -/** - * @private - */ -ol.PluggableMap.prototype.handleTargetChanged_ = function() { - // target may be undefined, null, a string or an Element. - // If it's a string we convert it to an Element before proceeding. - // If it's not now an Element we remove the viewport from the DOM. - // If it's an Element we append the viewport element to it. - - var targetElement; - if (this.getTarget()) { - targetElement = this.getTargetElement(); - } - - if (this.keyHandlerKeys_) { - for (var i = 0, ii = this.keyHandlerKeys_.length; i < ii; ++i) { - ol.events.unlistenByKey(this.keyHandlerKeys_[i]); - } - this.keyHandlerKeys_ = null; - } - - if (!targetElement) { - ol.dom.removeNode(this.viewport_); - if (this.handleResize_ !== undefined) { - window.removeEventListener(ol.events.EventType.RESIZE, - this.handleResize_, false); - this.handleResize_ = undefined; - } - } else { - targetElement.appendChild(this.viewport_); - - var keyboardEventTarget = !this.keyboardEventTarget_ ? - targetElement : this.keyboardEventTarget_; - this.keyHandlerKeys_ = [ - ol.events.listen(keyboardEventTarget, ol.events.EventType.KEYDOWN, - this.handleBrowserEvent, this), - ol.events.listen(keyboardEventTarget, ol.events.EventType.KEYPRESS, - this.handleBrowserEvent, this) - ]; - - if (!this.handleResize_) { - this.handleResize_ = this.updateSize.bind(this); - window.addEventListener(ol.events.EventType.RESIZE, - this.handleResize_, false); - } - } - - this.updateSize(); - // updateSize calls setSize, so no need to call this.render - // ourselves here. -}; - - -/** - * @private - */ -ol.PluggableMap.prototype.handleTileChange_ = function() { - this.render(); -}; - - -/** - * @private - */ -ol.PluggableMap.prototype.handleViewPropertyChanged_ = function() { - this.render(); -}; - - -/** - * @private - */ -ol.PluggableMap.prototype.handleViewChanged_ = function() { - if (this.viewPropertyListenerKey_) { - ol.events.unlistenByKey(this.viewPropertyListenerKey_); - this.viewPropertyListenerKey_ = null; - } - if (this.viewChangeListenerKey_) { - ol.events.unlistenByKey(this.viewChangeListenerKey_); - this.viewChangeListenerKey_ = null; - } - var view = this.getView(); - if (view) { - this.viewport_.setAttribute('data-view', ol.getUid(view)); - this.viewPropertyListenerKey_ = ol.events.listen( - view, ol.ObjectEventType.PROPERTYCHANGE, - this.handleViewPropertyChanged_, this); - this.viewChangeListenerKey_ = ol.events.listen( - view, ol.events.EventType.CHANGE, - this.handleViewPropertyChanged_, this); - } - this.render(); -}; - - -/** - * @private - */ -ol.PluggableMap.prototype.handleLayerGroupChanged_ = function() { - if (this.layerGroupPropertyListenerKeys_) { - this.layerGroupPropertyListenerKeys_.forEach(ol.events.unlistenByKey); - this.layerGroupPropertyListenerKeys_ = null; - } - var layerGroup = this.getLayerGroup(); - if (layerGroup) { - this.layerGroupPropertyListenerKeys_ = [ - ol.events.listen( - layerGroup, ol.ObjectEventType.PROPERTYCHANGE, - this.render, this), - ol.events.listen( - layerGroup, ol.events.EventType.CHANGE, - this.render, this) - ]; - } - this.render(); -}; - - -/** - * @return {boolean} Is rendered. - */ -ol.PluggableMap.prototype.isRendered = function() { - return !!this.frameState_; -}; - - -/** - * Requests an immediate render in a synchronous manner. - * @api - */ -ol.PluggableMap.prototype.renderSync = function() { - if (this.animationDelayKey_) { - cancelAnimationFrame(this.animationDelayKey_); - } - this.animationDelay_(); -}; - - -/** - * Request a map rendering (at the next animation frame). - * @api - */ -ol.PluggableMap.prototype.render = function() { - if (this.animationDelayKey_ === undefined) { - this.animationDelayKey_ = requestAnimationFrame( - this.animationDelay_); - } -}; - - -/** - * Remove the given control from the map. - * @param {ol.control.Control} control Control. - * @return {ol.control.Control|undefined} The removed control (or undefined - * if the control was not found). - * @api - */ -ol.PluggableMap.prototype.removeControl = function(control) { - return this.getControls().remove(control); -}; - - -/** - * Remove the given interaction from the map. - * @param {ol.interaction.Interaction} interaction Interaction to remove. - * @return {ol.interaction.Interaction|undefined} The removed interaction (or - * undefined if the interaction was not found). - * @api - */ -ol.PluggableMap.prototype.removeInteraction = function(interaction) { - return this.getInteractions().remove(interaction); -}; - - -/** - * Removes the given layer from the map. - * @param {ol.layer.Base} layer Layer. - * @return {ol.layer.Base|undefined} The removed layer (or undefined if the - * layer was not found). - * @api - */ -ol.PluggableMap.prototype.removeLayer = function(layer) { - var layers = this.getLayerGroup().getLayers(); - return layers.remove(layer); -}; - - -/** - * Remove the given overlay from the map. - * @param {ol.Overlay} overlay Overlay. - * @return {ol.Overlay|undefined} The removed overlay (or undefined - * if the overlay was not found). - * @api - */ -ol.PluggableMap.prototype.removeOverlay = function(overlay) { - return this.getOverlays().remove(overlay); -}; - - -/** - * @param {number} time Time. - * @private - */ -ol.PluggableMap.prototype.renderFrame_ = function(time) { - var i, ii, viewState; - - var size = this.getSize(); - var view = this.getView(); - var extent = ol.extent.createEmpty(); - var previousFrameState = this.frameState_; - /** @type {?olx.FrameState} */ - var frameState = null; - if (size !== undefined && ol.size.hasArea(size) && view && view.isDef()) { - var viewHints = view.getHints(this.frameState_ ? this.frameState_.viewHints : undefined); - var layerStatesArray = this.getLayerGroup().getLayerStatesArray(); - var layerStates = {}; - for (i = 0, ii = layerStatesArray.length; i < ii; ++i) { - layerStates[ol.getUid(layerStatesArray[i].layer)] = layerStatesArray[i]; - } - viewState = view.getState(); - frameState = /** @type {olx.FrameState} */ ({ - animate: false, - attributions: {}, - coordinateToPixelTransform: this.coordinateToPixelTransform_, - extent: extent, - focus: !this.focus_ ? viewState.center : this.focus_, - index: this.frameIndex_++, - layerStates: layerStates, - layerStatesArray: layerStatesArray, - logos: ol.obj.assign({}, this.logos_), - pixelRatio: this.pixelRatio_, - pixelToCoordinateTransform: this.pixelToCoordinateTransform_, - postRenderFunctions: [], - size: size, - skippedFeatureUids: this.skippedFeatureUids_, - tileQueue: this.tileQueue_, - time: time, - usedTiles: {}, - viewState: viewState, - viewHints: viewHints, - wantedTiles: {} - }); - } - - if (frameState) { - frameState.extent = ol.extent.getForViewAndSize(viewState.center, - viewState.resolution, viewState.rotation, frameState.size, extent); - } - - this.frameState_ = frameState; - this.renderer_.renderFrame(frameState); - - if (frameState) { - if (frameState.animate) { - this.render(); - } - Array.prototype.push.apply( - this.postRenderFunctions_, frameState.postRenderFunctions); - - if (previousFrameState) { - var moveStart = !this.previousExtent_ || - (!ol.extent.isEmpty(this.previousExtent_) && - !ol.extent.equals(frameState.extent, this.previousExtent_)); - if (moveStart) { - this.dispatchEvent( - new ol.MapEvent(ol.MapEventType.MOVESTART, this, previousFrameState)); - this.previousExtent_ = ol.extent.createOrUpdateEmpty(this.previousExtent_); - } - } - - var idle = this.previousExtent_ && - !frameState.viewHints[ol.ViewHint.ANIMATING] && - !frameState.viewHints[ol.ViewHint.INTERACTING] && - !ol.extent.equals(frameState.extent, this.previousExtent_); - - if (idle) { - this.dispatchEvent( - new ol.MapEvent(ol.MapEventType.MOVEEND, this, frameState)); - ol.extent.clone(frameState.extent, this.previousExtent_); - } - } - - this.dispatchEvent( - new ol.MapEvent(ol.MapEventType.POSTRENDER, this, frameState)); - - setTimeout(this.handlePostRender.bind(this), 0); - -}; - - -/** - * Sets the layergroup of this map. - * @param {ol.layer.Group} layerGroup A layer group containing the layers in - * this map. - * @observable - * @api - */ -ol.PluggableMap.prototype.setLayerGroup = function(layerGroup) { - this.set(ol.MapProperty.LAYERGROUP, layerGroup); -}; - - -/** - * Set the size of this map. - * @param {ol.Size|undefined} size The size in pixels of the map in the DOM. - * @observable - * @api - */ -ol.PluggableMap.prototype.setSize = function(size) { - this.set(ol.MapProperty.SIZE, size); -}; - - -/** - * Set the target element to render this map into. - * @param {Element|string|undefined} target The Element or id of the Element - * that the map is rendered in. - * @observable - * @api - */ -ol.PluggableMap.prototype.setTarget = function(target) { - this.set(ol.MapProperty.TARGET, target); -}; - - -/** - * Set the view for this map. - * @param {ol.View} view The view that controls this map. - * @observable - * @api - */ -ol.PluggableMap.prototype.setView = function(view) { - this.set(ol.MapProperty.VIEW, view); -}; - - -/** - * @param {ol.Feature} feature Feature. - */ -ol.PluggableMap.prototype.skipFeature = function(feature) { - var featureUid = ol.getUid(feature).toString(); - this.skippedFeatureUids_[featureUid] = true; - this.render(); -}; - - -/** - * Force a recalculation of the map viewport size. This should be called when - * third-party code changes the size of the map viewport. - * @api - */ -ol.PluggableMap.prototype.updateSize = function() { - var targetElement = this.getTargetElement(); - - if (!targetElement) { - this.setSize(undefined); - } else { - var computedStyle = getComputedStyle(targetElement); - this.setSize([ - targetElement.offsetWidth - - parseFloat(computedStyle['borderLeftWidth']) - - parseFloat(computedStyle['paddingLeft']) - - parseFloat(computedStyle['paddingRight']) - - parseFloat(computedStyle['borderRightWidth']), - targetElement.offsetHeight - - parseFloat(computedStyle['borderTopWidth']) - - parseFloat(computedStyle['paddingTop']) - - parseFloat(computedStyle['paddingBottom']) - - parseFloat(computedStyle['borderBottomWidth']) - ]); - } -}; - - -/** - * @param {ol.Feature} feature Feature. - */ -ol.PluggableMap.prototype.unskipFeature = function(feature) { - var featureUid = ol.getUid(feature).toString(); - delete this.skippedFeatureUids_[featureUid]; - this.render(); -}; - - -/** - * @type {Array.<ol.renderer.Type>} - * @const - */ -ol.PluggableMap.DEFAULT_RENDERER_TYPES = [ - ol.renderer.Type.CANVAS, - ol.renderer.Type.WEBGL -]; - - -/** - * @const - * @type {string} - */ -ol.PluggableMap.LOGO_URL = 'data:image/png;base64,' + - 'iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAMAAABEpIrGAAAAA3NCSVQICAjb4U/gAAAACXBI' + - 'WXMAAAHGAAABxgEXwfpGAAAAGXRFWHRTb2Z0d2FyZQB3d3cuaW5rc2NhcGUub3Jnm+48GgAA' + - 'AhNQTFRF////AP//AICAgP//AFVVQECA////K1VVSbbbYL/fJ05idsTYJFtbbcjbJllmZszW' + - 'WMTOIFhoHlNiZszTa9DdUcHNHlNlV8XRIVdiasrUHlZjIVZjaMnVH1RlIFRkH1RkH1ZlasvY' + - 'asvXVsPQH1VkacnVa8vWIVZjIFRjVMPQa8rXIVVkXsXRsNveIFVkIFZlIVVj3eDeh6GmbMvX' + - 'H1ZkIFRka8rWbMvXIFVkIFVjIFVkbMvWH1VjbMvWIFVlbcvWIFVla8vVIFVkbMvWbMvVH1Vk' + - 'bMvWIFVlbcvWIFVkbcvVbMvWjNPbIFVkU8LPwMzNIFVkbczWIFVkbsvWbMvXIFVkRnB8bcvW' + - '2+TkW8XRIFVkIlZlJVloJlpoKlxrLl9tMmJwOWd0Omh1RXF8TneCT3iDUHiDU8LPVMLPVcLP' + - 'VcPQVsPPVsPQV8PQWMTQWsTQW8TQXMXSXsXRX4SNX8bSYMfTYcfTYsfTY8jUZcfSZsnUaIqT' + - 'acrVasrVa8jTa8rWbI2VbMvWbcvWdJObdcvUdszUd8vVeJaee87Yfc3WgJyjhqGnitDYjaar' + - 'ldPZnrK2oNbborW5o9bbo9fbpLa6q9ndrL3ArtndscDDutzfu8fJwN7gwt7gxc/QyuHhy+Hi' + - 'zeHi0NfX0+Pj19zb1+Tj2uXk29/e3uLg3+Lh3+bl4uXj4ufl4+fl5Ofl5ufl5ujm5+jmySDn' + - 'BAAAAFp0Uk5TAAECAgMEBAYHCA0NDg4UGRogIiMmKSssLzU7PkJJT1JTVFliY2hrdHZ3foSF' + - 'hYeJjY2QkpugqbG1tre5w8zQ09XY3uXn6+zx8vT09vf4+Pj5+fr6/P39/f3+gz7SsAAAAVVJ' + - 'REFUOMtjYKA7EBDnwCPLrObS1BRiLoJLnte6CQy8FLHLCzs2QUG4FjZ5GbcmBDDjxJBXDWxC' + - 'Brb8aM4zbkIDzpLYnAcE9VXlJSWlZRU13koIeW57mGx5XjoMZEUqwxWYQaQbSzLSkYGfKFSe' + - '0QMsX5WbjgY0YS4MBplemI4BdGBW+DQ11eZiymfqQuXZIjqwyadPNoSZ4L+0FVM6e+oGI6g8' + - 'a9iKNT3o8kVzNkzRg5lgl7p4wyRUL9Yt2jAxVh6mQCogae6GmflI8p0r13VFWTHBQ0rWPW7a' + - 'hgWVcPm+9cuLoyy4kCJDzCm6d8PSFoh0zvQNC5OjDJhQopPPJqph1doJBUD5tnkbZiUEqaCn' + - 'B3bTqLTFG1bPn71kw4b+GFdpLElKIzRxxgYgWNYc5SCENVHKeUaltHdXx0dZ8uBI1hJ2UUDg' + - 'q82CM2MwKeibqAvSO7MCABq0wXEPiqWEAAAAAElFTkSuQmCC'; - - -/** - * @param {olx.MapOptions} options Map options. - * @return {ol.MapOptionsInternal} Internal map options. - */ -ol.PluggableMap.createOptionsInternal = function(options) { - - /** - * @type {Element|Document} - */ - var keyboardEventTarget = null; - if (options.keyboardEventTarget !== undefined) { - keyboardEventTarget = typeof options.keyboardEventTarget === 'string' ? - document.getElementById(options.keyboardEventTarget) : - options.keyboardEventTarget; - } - - /** - * @type {Object.<string, *>} - */ - var values = {}; - - var logos = {}; - if (options.logo === undefined || - (typeof options.logo === 'boolean' && options.logo)) { - logos[ol.PluggableMap.LOGO_URL] = 'https://openlayers.org/'; - } else { - var logo = options.logo; - if (typeof logo === 'string') { - logos[logo] = ''; - } else if (logo instanceof HTMLElement) { - logos[ol.getUid(logo).toString()] = logo; - } else if (logo) { - ol.asserts.assert(typeof logo.href == 'string', 44); // `logo.href` should be a string. - ol.asserts.assert(typeof logo.src == 'string', 45); // `logo.src` should be a string. - logos[logo.src] = logo.href; - } - } - - var layerGroup = (options.layers instanceof ol.layer.Group) ? - options.layers : new ol.layer.Group({layers: options.layers}); - values[ol.MapProperty.LAYERGROUP] = layerGroup; - - values[ol.MapProperty.TARGET] = options.target; - - values[ol.MapProperty.VIEW] = options.view !== undefined ? - options.view : new ol.View(); - - /** - * @type {Array.<ol.renderer.Type>} - */ - var rendererTypes; - - if (options.renderer !== undefined) { - if (Array.isArray(options.renderer)) { - rendererTypes = options.renderer; - } else if (typeof options.renderer === 'string') { - rendererTypes = [options.renderer]; - } else { - ol.asserts.assert(false, 46); // Incorrect format for `renderer` option - } - if (rendererTypes.indexOf(/** @type {ol.renderer.Type} */ ('dom')) >= 0) { - rendererTypes = rendererTypes.concat(ol.PluggableMap.DEFAULT_RENDERER_TYPES); - } - } else { - rendererTypes = ol.PluggableMap.DEFAULT_RENDERER_TYPES; - } - - /** - * @type {olx.MapRendererPlugin} - */ - var mapRendererPlugin; - - var mapRendererPlugins = ol.plugins.getMapRendererPlugins(); - outer: for (var i = 0, ii = rendererTypes.length; i < ii; ++i) { - var rendererType = rendererTypes[i]; - for (var j = 0, jj = mapRendererPlugins.length; j < jj; ++j) { - var candidate = mapRendererPlugins[j]; - if (candidate.handles(rendererType)) { - mapRendererPlugin = candidate; - break outer; - } - } - } - - if (!mapRendererPlugin) { - throw new Error('Unable to create a map renderer for types: ' + rendererTypes.join(', ')); - } - - var controls; - if (options.controls !== undefined) { - if (Array.isArray(options.controls)) { - controls = new ol.Collection(options.controls.slice()); - } else { - ol.asserts.assert(options.controls instanceof ol.Collection, - 47); // Expected `controls` to be an array or an `ol.Collection` - controls = options.controls; - } - } - - var interactions; - if (options.interactions !== undefined) { - if (Array.isArray(options.interactions)) { - interactions = new ol.Collection(options.interactions.slice()); - } else { - ol.asserts.assert(options.interactions instanceof ol.Collection, - 48); // Expected `interactions` to be an array or an `ol.Collection` - interactions = options.interactions; - } - } - - var overlays; - if (options.overlays !== undefined) { - if (Array.isArray(options.overlays)) { - overlays = new ol.Collection(options.overlays.slice()); - } else { - ol.asserts.assert(options.overlays instanceof ol.Collection, - 49); // Expected `overlays` to be an array or an `ol.Collection` - overlays = options.overlays; - } - } else { - overlays = new ol.Collection(); - } - - return { - controls: controls, - interactions: interactions, - keyboardEventTarget: keyboardEventTarget, - logos: logos, - overlays: overlays, - mapRendererPlugin: mapRendererPlugin, - values: values - }; - -}; - -goog.provide('ol.control.Control'); - -goog.require('ol'); -goog.require('ol.MapEventType'); -goog.require('ol.Object'); -goog.require('ol.dom'); -goog.require('ol.events'); - - -/** - * @classdesc - * A control is a visible widget with a DOM element in a fixed position on the - * screen. They can involve user input (buttons), or be informational only; - * the position is determined using CSS. By default these are placed in the - * container with CSS class name `ol-overlaycontainer-stopevent`, but can use - * any outside DOM element. - * - * This is the base class for controls. You can use it for simple custom - * controls by creating the element with listeners, creating an instance: - * ```js - * var myControl = new ol.control.Control({element: myElement}); - * ``` - * and then adding this to the map. - * - * The main advantage of having this as a control rather than a simple separate - * DOM element is that preventing propagation is handled for you. Controls - * will also be `ol.Object`s in a `ol.Collection`, so you can use their - * methods. - * - * You can also extend this base for your own control class. See - * examples/custom-controls for an example of how to do this. - * - * @constructor - * @extends {ol.Object} - * @implements {oli.control.Control} - * @param {olx.control.ControlOptions} options Control options. - * @api - */ -ol.control.Control = function(options) { - - ol.Object.call(this); - - /** - * @protected - * @type {Element} - */ - this.element = options.element ? options.element : null; - - /** - * @private - * @type {Element} - */ - this.target_ = null; - - /** - * @private - * @type {ol.PluggableMap} - */ - this.map_ = null; - - /** - * @protected - * @type {!Array.<ol.EventsKey>} - */ - this.listenerKeys = []; - - /** - * @type {function(ol.MapEvent)} - */ - this.render = options.render ? options.render : ol.nullFunction; - - if (options.target) { - this.setTarget(options.target); - } - -}; -ol.inherits(ol.control.Control, ol.Object); - - -/** - * @inheritDoc - */ -ol.control.Control.prototype.disposeInternal = function() { - ol.dom.removeNode(this.element); - ol.Object.prototype.disposeInternal.call(this); -}; - - -/** - * Get the map associated with this control. - * @return {ol.PluggableMap} Map. - * @api - */ -ol.control.Control.prototype.getMap = function() { - return this.map_; -}; - - -/** - * Remove the control from its current map and attach it to the new map. - * Subclasses may set up event handlers to get notified about changes to - * the map here. - * @param {ol.PluggableMap} map Map. - * @override - * @api - */ -ol.control.Control.prototype.setMap = function(map) { - if (this.map_) { - ol.dom.removeNode(this.element); - } - for (var i = 0, ii = this.listenerKeys.length; i < ii; ++i) { - ol.events.unlistenByKey(this.listenerKeys[i]); - } - this.listenerKeys.length = 0; - this.map_ = map; - if (this.map_) { - var target = this.target_ ? - this.target_ : map.getOverlayContainerStopEvent(); - target.appendChild(this.element); - if (this.render !== ol.nullFunction) { - this.listenerKeys.push(ol.events.listen(map, - ol.MapEventType.POSTRENDER, this.render, this)); - } - map.render(); - } -}; - - -/** - * This function is used to set a target element for the control. It has no - * effect if it is called after the control has been added to the map (i.e. - * after `setMap` is called on the control). If no `target` is set in the - * options passed to the control constructor and if `setTarget` is not called - * then the control is added to the map's overlay container. - * @param {Element|string} target Target. - * @api - */ -ol.control.Control.prototype.setTarget = function(target) { - this.target_ = typeof target === 'string' ? - document.getElementById(target) : - target; -}; - -goog.provide('ol.css'); - - -/** - * The CSS class for hidden feature. - * - * @const - * @type {string} - */ -ol.css.CLASS_HIDDEN = 'ol-hidden'; - - -/** - * The CSS class that we'll give the DOM elements to have them selectable. - * - * @const - * @type {string} - */ -ol.css.CLASS_SELECTABLE = 'ol-selectable'; - -/** - * The CSS class that we'll give the DOM elements to have them unselectable. - * - * @const - * @type {string} - */ -ol.css.CLASS_UNSELECTABLE = 'ol-unselectable'; - - -/** - * The CSS class for unsupported feature. - * - * @const - * @type {string} - */ -ol.css.CLASS_UNSUPPORTED = 'ol-unsupported'; - - -/** - * The CSS class for controls. - * - * @const - * @type {string} - */ -ol.css.CLASS_CONTROL = 'ol-control'; - -// FIXME handle date line wrap - -goog.provide('ol.control.Attribution'); - -goog.require('ol'); -goog.require('ol.dom'); -goog.require('ol.control.Control'); -goog.require('ol.css'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.obj'); - - -/** - * @classdesc - * Control to show all the attributions associated with the layer sources - * in the map. This control is one of the default controls included in maps. - * By default it will show in the bottom right portion of the map, but this can - * be changed by using a css selector for `.ol-attribution`. - * - * @constructor - * @extends {ol.control.Control} - * @param {olx.control.AttributionOptions=} opt_options Attribution options. - * @api - */ -ol.control.Attribution = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - /** - * @private - * @type {Element} - */ - this.ulElement_ = document.createElement('UL'); - - /** - * @private - * @type {Element} - */ - this.logoLi_ = document.createElement('LI'); - - this.ulElement_.appendChild(this.logoLi_); - this.logoLi_.style.display = 'none'; - - /** - * @private - * @type {boolean} - */ - this.collapsed_ = options.collapsed !== undefined ? options.collapsed : true; - - /** - * @private - * @type {boolean} - */ - this.collapsible_ = options.collapsible !== undefined ? - options.collapsible : true; - - if (!this.collapsible_) { - this.collapsed_ = false; - } - - var className = options.className !== undefined ? options.className : 'ol-attribution'; - - var tipLabel = options.tipLabel !== undefined ? options.tipLabel : 'Attributions'; - - var collapseLabel = options.collapseLabel !== undefined ? options.collapseLabel : '\u00BB'; - - if (typeof collapseLabel === 'string') { - /** - * @private - * @type {Node} - */ - this.collapseLabel_ = document.createElement('span'); - this.collapseLabel_.textContent = collapseLabel; - } else { - this.collapseLabel_ = collapseLabel; - } - - var label = options.label !== undefined ? options.label : 'i'; - - if (typeof label === 'string') { - /** - * @private - * @type {Node} - */ - this.label_ = document.createElement('span'); - this.label_.textContent = label; - } else { - this.label_ = label; - } - - - var activeLabel = (this.collapsible_ && !this.collapsed_) ? - this.collapseLabel_ : this.label_; - var button = document.createElement('button'); - button.setAttribute('type', 'button'); - button.title = tipLabel; - button.appendChild(activeLabel); - - ol.events.listen(button, ol.events.EventType.CLICK, this.handleClick_, this); - - var cssClasses = className + ' ' + ol.css.CLASS_UNSELECTABLE + ' ' + - ol.css.CLASS_CONTROL + - (this.collapsed_ && this.collapsible_ ? ' ol-collapsed' : '') + - (this.collapsible_ ? '' : ' ol-uncollapsible'); - var element = document.createElement('div'); - element.className = cssClasses; - element.appendChild(this.ulElement_); - element.appendChild(button); - - var render = options.render ? options.render : ol.control.Attribution.render; - - ol.control.Control.call(this, { - element: element, - render: render, - target: options.target - }); - - /** - * @private - * @type {boolean} - */ - this.renderedVisible_ = true; - - /** - * @private - * @type {Object.<string, Element>} - */ - this.attributionElements_ = {}; - - /** - * @private - * @type {Object.<string, boolean>} - */ - this.attributionElementRenderedVisible_ = {}; - - /** - * @private - * @type {Object.<string, Element>} - */ - this.logoElements_ = {}; - -}; -ol.inherits(ol.control.Attribution, ol.control.Control); - - -/** - * @param {?olx.FrameState} frameState Frame state. - * @return {Array.<Object.<string, ol.Attribution>>} Attributions. - */ -ol.control.Attribution.prototype.getSourceAttributions = function(frameState) { - var i, ii, j, jj, tileRanges, source, sourceAttribution, - sourceAttributionKey, sourceAttributions, sourceKey; - var intersectsTileRange; - var layerStatesArray = frameState.layerStatesArray; - /** @type {Object.<string, ol.Attribution>} */ - var attributions = ol.obj.assign({}, frameState.attributions); - /** @type {Object.<string, ol.Attribution>} */ - var hiddenAttributions = {}; - var uniqueAttributions = {}; - var projection = /** @type {!ol.proj.Projection} */ (frameState.viewState.projection); - for (i = 0, ii = layerStatesArray.length; i < ii; i++) { - source = layerStatesArray[i].layer.getSource(); - if (!source) { - continue; - } - sourceKey = ol.getUid(source).toString(); - sourceAttributions = source.getAttributions(); - if (!sourceAttributions) { - continue; - } - for (j = 0, jj = sourceAttributions.length; j < jj; j++) { - sourceAttribution = sourceAttributions[j]; - sourceAttributionKey = ol.getUid(sourceAttribution).toString(); - if (sourceAttributionKey in attributions) { - continue; - } - tileRanges = frameState.usedTiles[sourceKey]; - if (tileRanges) { - var tileGrid = /** @type {ol.source.Tile} */ (source).getTileGridForProjection(projection); - intersectsTileRange = sourceAttribution.intersectsAnyTileRange( - tileRanges, tileGrid, projection); - } else { - intersectsTileRange = false; - } - if (intersectsTileRange) { - if (sourceAttributionKey in hiddenAttributions) { - delete hiddenAttributions[sourceAttributionKey]; - } - var html = sourceAttribution.getHTML(); - if (!(html in uniqueAttributions)) { - uniqueAttributions[html] = true; - attributions[sourceAttributionKey] = sourceAttribution; - } - } else { - hiddenAttributions[sourceAttributionKey] = sourceAttribution; - } - } - } - return [attributions, hiddenAttributions]; -}; - - -/** - * Update the attribution element. - * @param {ol.MapEvent} mapEvent Map event. - * @this {ol.control.Attribution} - * @api - */ -ol.control.Attribution.render = function(mapEvent) { - this.updateElement_(mapEvent.frameState); -}; - - -/** - * @private - * @param {?olx.FrameState} frameState Frame state. - */ -ol.control.Attribution.prototype.updateElement_ = function(frameState) { - - if (!frameState) { - if (this.renderedVisible_) { - this.element.style.display = 'none'; - this.renderedVisible_ = false; - } - return; - } - - var attributions = this.getSourceAttributions(frameState); - /** @type {Object.<string, ol.Attribution>} */ - var visibleAttributions = attributions[0]; - /** @type {Object.<string, ol.Attribution>} */ - var hiddenAttributions = attributions[1]; - - var attributionElement, attributionKey; - for (attributionKey in this.attributionElements_) { - if (attributionKey in visibleAttributions) { - if (!this.attributionElementRenderedVisible_[attributionKey]) { - this.attributionElements_[attributionKey].style.display = ''; - this.attributionElementRenderedVisible_[attributionKey] = true; - } - delete visibleAttributions[attributionKey]; - } else if (attributionKey in hiddenAttributions) { - if (this.attributionElementRenderedVisible_[attributionKey]) { - this.attributionElements_[attributionKey].style.display = 'none'; - delete this.attributionElementRenderedVisible_[attributionKey]; - } - delete hiddenAttributions[attributionKey]; - } else { - ol.dom.removeNode(this.attributionElements_[attributionKey]); - delete this.attributionElements_[attributionKey]; - delete this.attributionElementRenderedVisible_[attributionKey]; - } - } - for (attributionKey in visibleAttributions) { - attributionElement = document.createElement('LI'); - attributionElement.innerHTML = - visibleAttributions[attributionKey].getHTML(); - this.ulElement_.appendChild(attributionElement); - this.attributionElements_[attributionKey] = attributionElement; - this.attributionElementRenderedVisible_[attributionKey] = true; - } - for (attributionKey in hiddenAttributions) { - attributionElement = document.createElement('LI'); - attributionElement.innerHTML = - hiddenAttributions[attributionKey].getHTML(); - attributionElement.style.display = 'none'; - this.ulElement_.appendChild(attributionElement); - this.attributionElements_[attributionKey] = attributionElement; - } - - var renderVisible = - !ol.obj.isEmpty(this.attributionElementRenderedVisible_) || - !ol.obj.isEmpty(frameState.logos); - if (this.renderedVisible_ != renderVisible) { - this.element.style.display = renderVisible ? '' : 'none'; - this.renderedVisible_ = renderVisible; - } - if (renderVisible && - ol.obj.isEmpty(this.attributionElementRenderedVisible_)) { - this.element.classList.add('ol-logo-only'); - } else { - this.element.classList.remove('ol-logo-only'); - } - - this.insertLogos_(frameState); - -}; - - -/** - * @param {?olx.FrameState} frameState Frame state. - * @private - */ -ol.control.Attribution.prototype.insertLogos_ = function(frameState) { - - var logo; - var logos = frameState.logos; - var logoElements = this.logoElements_; - - for (logo in logoElements) { - if (!(logo in logos)) { - ol.dom.removeNode(logoElements[logo]); - delete logoElements[logo]; - } - } - - var image, logoElement, logoKey; - for (logoKey in logos) { - var logoValue = logos[logoKey]; - if (logoValue instanceof HTMLElement) { - this.logoLi_.appendChild(logoValue); - logoElements[logoKey] = logoValue; - } - if (!(logoKey in logoElements)) { - image = new Image(); - image.src = logoKey; - if (logoValue === '') { - logoElement = image; - } else { - logoElement = document.createElement('a'); - logoElement.href = logoValue; - logoElement.appendChild(image); - } - this.logoLi_.appendChild(logoElement); - logoElements[logoKey] = logoElement; - } - } - - this.logoLi_.style.display = !ol.obj.isEmpty(logos) ? '' : 'none'; - -}; - - -/** - * @param {Event} event The event to handle - * @private - */ -ol.control.Attribution.prototype.handleClick_ = function(event) { - event.preventDefault(); - this.handleToggle_(); -}; - - -/** - * @private - */ -ol.control.Attribution.prototype.handleToggle_ = function() { - this.element.classList.toggle('ol-collapsed'); - if (this.collapsed_) { - ol.dom.replaceNode(this.collapseLabel_, this.label_); - } else { - ol.dom.replaceNode(this.label_, this.collapseLabel_); - } - this.collapsed_ = !this.collapsed_; -}; - - -/** - * Return `true` if the attribution is collapsible, `false` otherwise. - * @return {boolean} True if the widget is collapsible. - * @api - */ -ol.control.Attribution.prototype.getCollapsible = function() { - return this.collapsible_; -}; - - -/** - * Set whether the attribution should be collapsible. - * @param {boolean} collapsible True if the widget is collapsible. - * @api - */ -ol.control.Attribution.prototype.setCollapsible = function(collapsible) { - if (this.collapsible_ === collapsible) { - return; - } - this.collapsible_ = collapsible; - this.element.classList.toggle('ol-uncollapsible'); - if (!collapsible && this.collapsed_) { - this.handleToggle_(); - } -}; - - -/** - * Collapse or expand the attribution according to the passed parameter. Will - * not do anything if the attribution isn't collapsible or if the current - * collapsed state is already the one requested. - * @param {boolean} collapsed True if the widget is collapsed. - * @api - */ -ol.control.Attribution.prototype.setCollapsed = function(collapsed) { - if (!this.collapsible_ || this.collapsed_ === collapsed) { - return; - } - this.handleToggle_(); -}; - - -/** - * Return `true` when the attribution is currently collapsed or `false` - * otherwise. - * @return {boolean} True if the widget is collapsed. - * @api - */ -ol.control.Attribution.prototype.getCollapsed = function() { - return this.collapsed_; -}; - -goog.provide('ol.control.Rotate'); - -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol'); -goog.require('ol.control.Control'); -goog.require('ol.css'); -goog.require('ol.easing'); - - -/** - * @classdesc - * A button control to reset rotation to 0. - * To style this control use css selector `.ol-rotate`. A `.ol-hidden` css - * selector is added to the button when the rotation is 0. - * - * @constructor - * @extends {ol.control.Control} - * @param {olx.control.RotateOptions=} opt_options Rotate options. - * @api - */ -ol.control.Rotate = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - var className = options.className !== undefined ? options.className : 'ol-rotate'; - - var label = options.label !== undefined ? options.label : '\u21E7'; - - /** - * @type {Element} - * @private - */ - this.label_ = null; - - if (typeof label === 'string') { - this.label_ = document.createElement('span'); - this.label_.className = 'ol-compass'; - this.label_.textContent = label; - } else { - this.label_ = label; - this.label_.classList.add('ol-compass'); - } - - var tipLabel = options.tipLabel ? options.tipLabel : 'Reset rotation'; - - var button = document.createElement('button'); - button.className = className + '-reset'; - button.setAttribute('type', 'button'); - button.title = tipLabel; - button.appendChild(this.label_); - - ol.events.listen(button, ol.events.EventType.CLICK, - ol.control.Rotate.prototype.handleClick_, this); - - var cssClasses = className + ' ' + ol.css.CLASS_UNSELECTABLE + ' ' + - ol.css.CLASS_CONTROL; - var element = document.createElement('div'); - element.className = cssClasses; - element.appendChild(button); - - var render = options.render ? options.render : ol.control.Rotate.render; - - this.callResetNorth_ = options.resetNorth ? options.resetNorth : undefined; - - ol.control.Control.call(this, { - element: element, - render: render, - target: options.target - }); - - /** - * @type {number} - * @private - */ - this.duration_ = options.duration !== undefined ? options.duration : 250; - - /** - * @type {boolean} - * @private - */ - this.autoHide_ = options.autoHide !== undefined ? options.autoHide : true; - - /** - * @private - * @type {number|undefined} - */ - this.rotation_ = undefined; - - if (this.autoHide_) { - this.element.classList.add(ol.css.CLASS_HIDDEN); - } - -}; -ol.inherits(ol.control.Rotate, ol.control.Control); - - -/** - * @param {Event} event The event to handle - * @private - */ -ol.control.Rotate.prototype.handleClick_ = function(event) { - event.preventDefault(); - if (this.callResetNorth_ !== undefined) { - this.callResetNorth_(); - } else { - this.resetNorth_(); - } -}; - - -/** - * @private - */ -ol.control.Rotate.prototype.resetNorth_ = function() { - var map = this.getMap(); - var view = map.getView(); - if (!view) { - // the map does not have a view, so we can't act - // upon it - return; - } - if (view.getRotation() !== undefined) { - if (this.duration_ > 0) { - view.animate({ - rotation: 0, - duration: this.duration_, - easing: ol.easing.easeOut - }); - } else { - view.setRotation(0); - } - } -}; - - -/** - * Update the rotate control element. - * @param {ol.MapEvent} mapEvent Map event. - * @this {ol.control.Rotate} - * @api - */ -ol.control.Rotate.render = function(mapEvent) { - var frameState = mapEvent.frameState; - if (!frameState) { - return; - } - var rotation = frameState.viewState.rotation; - if (rotation != this.rotation_) { - var transform = 'rotate(' + rotation + 'rad)'; - if (this.autoHide_) { - var contains = this.element.classList.contains(ol.css.CLASS_HIDDEN); - if (!contains && rotation === 0) { - this.element.classList.add(ol.css.CLASS_HIDDEN); - } else if (contains && rotation !== 0) { - this.element.classList.remove(ol.css.CLASS_HIDDEN); - } - } - this.label_.style.msTransform = transform; - this.label_.style.webkitTransform = transform; - this.label_.style.transform = transform; - } - this.rotation_ = rotation; -}; - -goog.provide('ol.control.Zoom'); - -goog.require('ol'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.control.Control'); -goog.require('ol.css'); -goog.require('ol.easing'); - - -/** - * @classdesc - * A control with 2 buttons, one for zoom in and one for zoom out. - * This control is one of the default controls of a map. To style this control - * use css selectors `.ol-zoom-in` and `.ol-zoom-out`. - * - * @constructor - * @extends {ol.control.Control} - * @param {olx.control.ZoomOptions=} opt_options Zoom options. - * @api - */ -ol.control.Zoom = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - var className = options.className !== undefined ? options.className : 'ol-zoom'; - - var delta = options.delta !== undefined ? options.delta : 1; - - var zoomInLabel = options.zoomInLabel !== undefined ? options.zoomInLabel : '+'; - var zoomOutLabel = options.zoomOutLabel !== undefined ? options.zoomOutLabel : '\u2212'; - - var zoomInTipLabel = options.zoomInTipLabel !== undefined ? - options.zoomInTipLabel : 'Zoom in'; - var zoomOutTipLabel = options.zoomOutTipLabel !== undefined ? - options.zoomOutTipLabel : 'Zoom out'; - - var inElement = document.createElement('button'); - inElement.className = className + '-in'; - inElement.setAttribute('type', 'button'); - inElement.title = zoomInTipLabel; - inElement.appendChild( - typeof zoomInLabel === 'string' ? document.createTextNode(zoomInLabel) : zoomInLabel - ); - - ol.events.listen(inElement, ol.events.EventType.CLICK, - ol.control.Zoom.prototype.handleClick_.bind(this, delta)); - - var outElement = document.createElement('button'); - outElement.className = className + '-out'; - outElement.setAttribute('type', 'button'); - outElement.title = zoomOutTipLabel; - outElement.appendChild( - typeof zoomOutLabel === 'string' ? document.createTextNode(zoomOutLabel) : zoomOutLabel - ); - - ol.events.listen(outElement, ol.events.EventType.CLICK, - ol.control.Zoom.prototype.handleClick_.bind(this, -delta)); - - var cssClasses = className + ' ' + ol.css.CLASS_UNSELECTABLE + ' ' + - ol.css.CLASS_CONTROL; - var element = document.createElement('div'); - element.className = cssClasses; - element.appendChild(inElement); - element.appendChild(outElement); - - ol.control.Control.call(this, { - element: element, - target: options.target - }); - - /** - * @type {number} - * @private - */ - this.duration_ = options.duration !== undefined ? options.duration : 250; - -}; -ol.inherits(ol.control.Zoom, ol.control.Control); - - -/** - * @param {number} delta Zoom delta. - * @param {Event} event The event to handle - * @private - */ -ol.control.Zoom.prototype.handleClick_ = function(delta, event) { - event.preventDefault(); - this.zoomByDelta_(delta); -}; - - -/** - * @param {number} delta Zoom delta. - * @private - */ -ol.control.Zoom.prototype.zoomByDelta_ = function(delta) { - var map = this.getMap(); - var view = map.getView(); - if (!view) { - // the map does not have a view, so we can't act - // upon it - return; - } - var currentResolution = view.getResolution(); - if (currentResolution) { - var newResolution = view.constrainResolution(currentResolution, delta); - if (this.duration_ > 0) { - if (view.getAnimating()) { - view.cancelAnimations(); - } - view.animate({ - resolution: newResolution, - duration: this.duration_, - easing: ol.easing.easeOut - }); - } else { - view.setResolution(newResolution); - } - } -}; - -goog.provide('ol.control'); - -goog.require('ol.Collection'); -goog.require('ol.control.Attribution'); -goog.require('ol.control.Rotate'); -goog.require('ol.control.Zoom'); - - -/** - * Set of controls included in maps by default. Unless configured otherwise, - * this returns a collection containing an instance of each of the following - * controls: - * * {@link ol.control.Zoom} - * * {@link ol.control.Rotate} - * * {@link ol.control.Attribution} - * - * @param {olx.control.DefaultsOptions=} opt_options Defaults options. - * @return {ol.Collection.<ol.control.Control>} Controls. - * @api - */ -ol.control.defaults = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - var controls = new ol.Collection(); - - var zoomControl = options.zoom !== undefined ? options.zoom : true; - if (zoomControl) { - controls.push(new ol.control.Zoom(options.zoomOptions)); - } - - var rotateControl = options.rotate !== undefined ? options.rotate : true; - if (rotateControl) { - controls.push(new ol.control.Rotate(options.rotateOptions)); - } - - var attributionControl = options.attribution !== undefined ? - options.attribution : true; - if (attributionControl) { - controls.push(new ol.control.Attribution(options.attributionOptions)); - } - - return controls; - -}; - -goog.provide('ol.Kinetic'); - - -/** - * @classdesc - * Implementation of inertial deceleration for map movement. - * - * @constructor - * @param {number} decay Rate of decay (must be negative). - * @param {number} minVelocity Minimum velocity (pixels/millisecond). - * @param {number} delay Delay to consider to calculate the kinetic - * initial values (milliseconds). - * @struct - * @api - */ -ol.Kinetic = function(decay, minVelocity, delay) { - - /** - * @private - * @type {number} - */ - this.decay_ = decay; - - /** - * @private - * @type {number} - */ - this.minVelocity_ = minVelocity; - - /** - * @private - * @type {number} - */ - this.delay_ = delay; - - /** - * @private - * @type {Array.<number>} - */ - this.points_ = []; - - /** - * @private - * @type {number} - */ - this.angle_ = 0; - - /** - * @private - * @type {number} - */ - this.initialVelocity_ = 0; -}; - - -/** - * FIXME empty description for jsdoc - */ -ol.Kinetic.prototype.begin = function() { - this.points_.length = 0; - this.angle_ = 0; - this.initialVelocity_ = 0; -}; - - -/** - * @param {number} x X. - * @param {number} y Y. - */ -ol.Kinetic.prototype.update = function(x, y) { - this.points_.push(x, y, Date.now()); -}; - - -/** - * @return {boolean} Whether we should do kinetic animation. - */ -ol.Kinetic.prototype.end = function() { - if (this.points_.length < 6) { - // at least 2 points are required (i.e. there must be at least 6 elements - // in the array) - return false; - } - var delay = Date.now() - this.delay_; - var lastIndex = this.points_.length - 3; - if (this.points_[lastIndex + 2] < delay) { - // the last tracked point is too old, which means that the user stopped - // panning before releasing the map - return false; - } - - // get the first point which still falls into the delay time - var firstIndex = lastIndex - 3; - while (firstIndex > 0 && this.points_[firstIndex + 2] > delay) { - firstIndex -= 3; - } - - var duration = this.points_[lastIndex + 2] - this.points_[firstIndex + 2]; - // we don't want a duration of 0 (divide by zero) - // we also make sure the user panned for a duration of at least one frame - // (1/60s) to compute sane displacement values - if (duration < 1000 / 60) { - return false; - } - - var dx = this.points_[lastIndex] - this.points_[firstIndex]; - var dy = this.points_[lastIndex + 1] - this.points_[firstIndex + 1]; - this.angle_ = Math.atan2(dy, dx); - this.initialVelocity_ = Math.sqrt(dx * dx + dy * dy) / duration; - return this.initialVelocity_ > this.minVelocity_; -}; - - -/** - * @return {number} Total distance travelled (pixels). - */ -ol.Kinetic.prototype.getDistance = function() { - return (this.minVelocity_ - this.initialVelocity_) / this.decay_; -}; - - -/** - * @return {number} Angle of the kinetic panning animation (radians). - */ -ol.Kinetic.prototype.getAngle = function() { - return this.angle_; -}; - -goog.provide('ol.interaction.Property'); - -/** - * @enum {string} - */ -ol.interaction.Property = { - ACTIVE: 'active' -}; - -// FIXME factor out key precondition (shift et. al) - -goog.provide('ol.interaction.Interaction'); - -goog.require('ol'); -goog.require('ol.Object'); -goog.require('ol.easing'); -goog.require('ol.interaction.Property'); - - -/** - * @classdesc - * Abstract base class; normally only used for creating subclasses and not - * instantiated in apps. - * User actions that change the state of the map. Some are similar to controls, - * but are not associated with a DOM element. - * For example, {@link ol.interaction.KeyboardZoom} is functionally the same as - * {@link ol.control.Zoom}, but triggered by a keyboard event not a button - * element event. - * Although interactions do not have a DOM element, some of them do render - * vectors and so are visible on the screen. - * - * @constructor - * @param {olx.interaction.InteractionOptions} options Options. - * @extends {ol.Object} - * @api - */ -ol.interaction.Interaction = function(options) { - - ol.Object.call(this); - - /** - * @private - * @type {ol.PluggableMap} - */ - this.map_ = null; - - this.setActive(true); - - /** - * @type {function(ol.MapBrowserEvent):boolean} - */ - this.handleEvent = options.handleEvent; - -}; -ol.inherits(ol.interaction.Interaction, ol.Object); - - -/** - * Return whether the interaction is currently active. - * @return {boolean} `true` if the interaction is active, `false` otherwise. - * @observable - * @api - */ -ol.interaction.Interaction.prototype.getActive = function() { - return /** @type {boolean} */ ( - this.get(ol.interaction.Property.ACTIVE)); -}; - - -/** - * Get the map associated with this interaction. - * @return {ol.PluggableMap} Map. - * @api - */ -ol.interaction.Interaction.prototype.getMap = function() { - return this.map_; -}; - - -/** - * Activate or deactivate the interaction. - * @param {boolean} active Active. - * @observable - * @api - */ -ol.interaction.Interaction.prototype.setActive = function(active) { - this.set(ol.interaction.Property.ACTIVE, active); -}; - - -/** - * Remove the interaction from its current map and attach it to the new map. - * Subclasses may set up event handlers to get notified about changes to - * the map here. - * @param {ol.PluggableMap} map Map. - */ -ol.interaction.Interaction.prototype.setMap = function(map) { - this.map_ = map; -}; - - -/** - * @param {ol.View} view View. - * @param {ol.Coordinate} delta Delta. - * @param {number=} opt_duration Duration. - */ -ol.interaction.Interaction.pan = function(view, delta, opt_duration) { - var currentCenter = view.getCenter(); - if (currentCenter) { - var center = view.constrainCenter( - [currentCenter[0] + delta[0], currentCenter[1] + delta[1]]); - if (opt_duration) { - view.animate({ - duration: opt_duration, - easing: ol.easing.linear, - center: center - }); - } else { - view.setCenter(center); - } - } -}; - - -/** - * @param {ol.View} view View. - * @param {number|undefined} rotation Rotation. - * @param {ol.Coordinate=} opt_anchor Anchor coordinate. - * @param {number=} opt_duration Duration. - */ -ol.interaction.Interaction.rotate = function(view, rotation, opt_anchor, opt_duration) { - rotation = view.constrainRotation(rotation, 0); - ol.interaction.Interaction.rotateWithoutConstraints( - view, rotation, opt_anchor, opt_duration); -}; - - -/** - * @param {ol.View} view View. - * @param {number|undefined} rotation Rotation. - * @param {ol.Coordinate=} opt_anchor Anchor coordinate. - * @param {number=} opt_duration Duration. - */ -ol.interaction.Interaction.rotateWithoutConstraints = function(view, rotation, opt_anchor, opt_duration) { - if (rotation !== undefined) { - var currentRotation = view.getRotation(); - var currentCenter = view.getCenter(); - if (currentRotation !== undefined && currentCenter && opt_duration > 0) { - view.animate({ - rotation: rotation, - anchor: opt_anchor, - duration: opt_duration, - easing: ol.easing.easeOut - }); - } else { - view.rotate(rotation, opt_anchor); - } - } -}; - - -/** - * @param {ol.View} view View. - * @param {number|undefined} resolution Resolution to go to. - * @param {ol.Coordinate=} opt_anchor Anchor coordinate. - * @param {number=} opt_duration Duration. - * @param {number=} opt_direction Zooming direction; > 0 indicates - * zooming out, in which case the constraints system will select - * the largest nearest resolution; < 0 indicates zooming in, in - * which case the constraints system will select the smallest - * nearest resolution; == 0 indicates that the zooming direction - * is unknown/not relevant, in which case the constraints system - * will select the nearest resolution. If not defined 0 is - * assumed. - */ -ol.interaction.Interaction.zoom = function(view, resolution, opt_anchor, opt_duration, opt_direction) { - resolution = view.constrainResolution(resolution, 0, opt_direction); - ol.interaction.Interaction.zoomWithoutConstraints( - view, resolution, opt_anchor, opt_duration); -}; - - -/** - * @param {ol.View} view View. - * @param {number} delta Delta from previous zoom level. - * @param {ol.Coordinate=} opt_anchor Anchor coordinate. - * @param {number=} opt_duration Duration. - */ -ol.interaction.Interaction.zoomByDelta = function(view, delta, opt_anchor, opt_duration) { - var currentResolution = view.getResolution(); - var resolution = view.constrainResolution(currentResolution, delta, 0); - - // If we have a constraint on center, we need to change the anchor so that the - // new center is within the extent. We first calculate the new center, apply - // the constraint to it, and then calculate back the anchor - if (opt_anchor && resolution !== undefined && resolution !== currentResolution) { - var currentCenter = view.getCenter(); - var center = view.calculateCenterZoom(resolution, opt_anchor); - center = view.constrainCenter(center); - - opt_anchor = [ - (resolution * currentCenter[0] - currentResolution * center[0]) / - (resolution - currentResolution), - (resolution * currentCenter[1] - currentResolution * center[1]) / - (resolution - currentResolution) - ]; - } - - ol.interaction.Interaction.zoomWithoutConstraints( - view, resolution, opt_anchor, opt_duration); -}; - - -/** - * @param {ol.View} view View. - * @param {number|undefined} resolution Resolution to go to. - * @param {ol.Coordinate=} opt_anchor Anchor coordinate. - * @param {number=} opt_duration Duration. - */ -ol.interaction.Interaction.zoomWithoutConstraints = function(view, resolution, opt_anchor, opt_duration) { - if (resolution) { - var currentResolution = view.getResolution(); - var currentCenter = view.getCenter(); - if (currentResolution !== undefined && currentCenter && - resolution !== currentResolution && opt_duration) { - view.animate({ - resolution: resolution, - anchor: opt_anchor, - duration: opt_duration, - easing: ol.easing.easeOut - }); - } else { - if (opt_anchor) { - var center = view.calculateCenterZoom(resolution, opt_anchor); - view.setCenter(center); - } - view.setResolution(resolution); - } - } -}; - -goog.provide('ol.interaction.DoubleClickZoom'); - -goog.require('ol'); -goog.require('ol.MapBrowserEventType'); -goog.require('ol.interaction.Interaction'); - - -/** - * @classdesc - * Allows the user to zoom by double-clicking on the map. - * - * @constructor - * @extends {ol.interaction.Interaction} - * @param {olx.interaction.DoubleClickZoomOptions=} opt_options Options. - * @api - */ -ol.interaction.DoubleClickZoom = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - /** - * @private - * @type {number} - */ - this.delta_ = options.delta ? options.delta : 1; - - ol.interaction.Interaction.call(this, { - handleEvent: ol.interaction.DoubleClickZoom.handleEvent - }); - - /** - * @private - * @type {number} - */ - this.duration_ = options.duration !== undefined ? options.duration : 250; - -}; -ol.inherits(ol.interaction.DoubleClickZoom, ol.interaction.Interaction); - - -/** - * Handles the {@link ol.MapBrowserEvent map browser event} (if it was a - * doubleclick) and eventually zooms the map. - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} `false` to stop event propagation. - * @this {ol.interaction.DoubleClickZoom} - * @api - */ -ol.interaction.DoubleClickZoom.handleEvent = function(mapBrowserEvent) { - var stopEvent = false; - var browserEvent = mapBrowserEvent.originalEvent; - if (mapBrowserEvent.type == ol.MapBrowserEventType.DBLCLICK) { - var map = mapBrowserEvent.map; - var anchor = mapBrowserEvent.coordinate; - var delta = browserEvent.shiftKey ? -this.delta_ : this.delta_; - var view = map.getView(); - ol.interaction.Interaction.zoomByDelta( - view, delta, anchor, this.duration_); - mapBrowserEvent.preventDefault(); - stopEvent = true; - } - return !stopEvent; -}; - -goog.provide('ol.events.condition'); - -goog.require('ol.MapBrowserEventType'); -goog.require('ol.asserts'); -goog.require('ol.functions'); -goog.require('ol.has'); - - -/** - * Return `true` if only the alt-key is pressed, `false` otherwise (e.g. when - * additionally the shift-key is pressed). - * - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} True if only the alt key is pressed. - * @api - */ -ol.events.condition.altKeyOnly = function(mapBrowserEvent) { - var originalEvent = mapBrowserEvent.originalEvent; - return ( - originalEvent.altKey && - !(originalEvent.metaKey || originalEvent.ctrlKey) && - !originalEvent.shiftKey); -}; - - -/** - * Return `true` if only the alt-key and shift-key is pressed, `false` otherwise - * (e.g. when additionally the platform-modifier-key is pressed). - * - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} True if only the alt and shift keys are pressed. - * @api - */ -ol.events.condition.altShiftKeysOnly = function(mapBrowserEvent) { - var originalEvent = mapBrowserEvent.originalEvent; - return ( - originalEvent.altKey && - !(originalEvent.metaKey || originalEvent.ctrlKey) && - originalEvent.shiftKey); -}; - - -/** - * Return always true. - * - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} True. - * @function - * @api - */ -ol.events.condition.always = ol.functions.TRUE; - - -/** - * Return `true` if the event is a `click` event, `false` otherwise. - * - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} True if the event is a map `click` event. - * @api - */ -ol.events.condition.click = function(mapBrowserEvent) { - return mapBrowserEvent.type == ol.MapBrowserEventType.CLICK; -}; - - -/** - * Return `true` if the event has an "action"-producing mouse button. - * - * By definition, this includes left-click on windows/linux, and left-click - * without the ctrl key on Macs. - * - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} The result. - */ -ol.events.condition.mouseActionButton = function(mapBrowserEvent) { - var originalEvent = mapBrowserEvent.originalEvent; - return originalEvent.button == 0 && - !(ol.has.WEBKIT && ol.has.MAC && originalEvent.ctrlKey); -}; - - -/** - * Return always false. - * - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} False. - * @function - * @api - */ -ol.events.condition.never = ol.functions.FALSE; - - -/** - * Return `true` if the browser event is a `pointermove` event, `false` - * otherwise. - * - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} True if the browser event is a `pointermove` event. - * @api - */ -ol.events.condition.pointerMove = function(mapBrowserEvent) { - return mapBrowserEvent.type == 'pointermove'; -}; - - -/** - * Return `true` if the event is a map `singleclick` event, `false` otherwise. - * - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} True if the event is a map `singleclick` event. - * @api - */ -ol.events.condition.singleClick = function(mapBrowserEvent) { - return mapBrowserEvent.type == ol.MapBrowserEventType.SINGLECLICK; -}; - - -/** - * Return `true` if the event is a map `dblclick` event, `false` otherwise. - * - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} True if the event is a map `dblclick` event. - * @api - */ -ol.events.condition.doubleClick = function(mapBrowserEvent) { - return mapBrowserEvent.type == ol.MapBrowserEventType.DBLCLICK; -}; - - -/** - * Return `true` if no modifier key (alt-, shift- or platform-modifier-key) is - * pressed. - * - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} True only if there no modifier keys are pressed. - * @api - */ -ol.events.condition.noModifierKeys = function(mapBrowserEvent) { - var originalEvent = mapBrowserEvent.originalEvent; - return ( - !originalEvent.altKey && - !(originalEvent.metaKey || originalEvent.ctrlKey) && - !originalEvent.shiftKey); -}; - - -/** - * Return `true` if only the platform-modifier-key (the meta-key on Mac, - * ctrl-key otherwise) is pressed, `false` otherwise (e.g. when additionally - * the shift-key is pressed). - * - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} True if only the platform modifier key is pressed. - * @api - */ -ol.events.condition.platformModifierKeyOnly = function(mapBrowserEvent) { - var originalEvent = mapBrowserEvent.originalEvent; - return ( - !originalEvent.altKey && - (ol.has.MAC ? originalEvent.metaKey : originalEvent.ctrlKey) && - !originalEvent.shiftKey); -}; - - -/** - * Return `true` if only the shift-key is pressed, `false` otherwise (e.g. when - * additionally the alt-key is pressed). - * - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} True if only the shift key is pressed. - * @api - */ -ol.events.condition.shiftKeyOnly = function(mapBrowserEvent) { - var originalEvent = mapBrowserEvent.originalEvent; - return ( - !originalEvent.altKey && - !(originalEvent.metaKey || originalEvent.ctrlKey) && - originalEvent.shiftKey); -}; - - -/** - * Return `true` if the target element is not editable, i.e. not a `<input>`-, - * `<select>`- or `<textarea>`-element, `false` otherwise. - * - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} True only if the target element is not editable. - * @api - */ -ol.events.condition.targetNotEditable = function(mapBrowserEvent) { - var target = mapBrowserEvent.originalEvent.target; - var tagName = target.tagName; - return ( - tagName !== 'INPUT' && - tagName !== 'SELECT' && - tagName !== 'TEXTAREA'); -}; - - -/** - * Return `true` if the event originates from a mouse device. - * - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} True if the event originates from a mouse device. - * @api - */ -ol.events.condition.mouseOnly = function(mapBrowserEvent) { - ol.asserts.assert(mapBrowserEvent.pointerEvent, 56); // mapBrowserEvent must originate from a pointer event - // see http://www.w3.org/TR/pointerevents/#widl-PointerEvent-pointerType - return /** @type {ol.MapBrowserEvent} */ (mapBrowserEvent).pointerEvent.pointerType == 'mouse'; -}; - - -/** - * Return `true` if the event originates from a primary pointer in - * contact with the surface or if the left mouse button is pressed. - * @see http://www.w3.org/TR/pointerevents/#button-states - * - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} True if the event originates from a primary pointer. - * @api - */ -ol.events.condition.primaryAction = function(mapBrowserEvent) { - var pointerEvent = mapBrowserEvent.pointerEvent; - return pointerEvent.isPrimary && pointerEvent.button === 0; -}; - -goog.provide('ol.interaction.Pointer'); - -goog.require('ol'); -goog.require('ol.functions'); -goog.require('ol.MapBrowserEventType'); -goog.require('ol.MapBrowserPointerEvent'); -goog.require('ol.interaction.Interaction'); -goog.require('ol.obj'); - - -/** - * @classdesc - * Base class that calls user-defined functions on `down`, `move` and `up` - * events. This class also manages "drag sequences". - * - * When the `handleDownEvent` user function returns `true` a drag sequence is - * started. During a drag sequence the `handleDragEvent` user function is - * called on `move` events. The drag sequence ends when the `handleUpEvent` - * user function is called and returns `false`. - * - * @constructor - * @param {olx.interaction.PointerOptions=} opt_options Options. - * @extends {ol.interaction.Interaction} - * @api - */ -ol.interaction.Pointer = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - var handleEvent = options.handleEvent ? - options.handleEvent : ol.interaction.Pointer.handleEvent; - - ol.interaction.Interaction.call(this, { - handleEvent: handleEvent - }); - - /** - * @type {function(ol.MapBrowserPointerEvent):boolean} - * @private - */ - this.handleDownEvent_ = options.handleDownEvent ? - options.handleDownEvent : ol.interaction.Pointer.handleDownEvent; - - /** - * @type {function(ol.MapBrowserPointerEvent)} - * @private - */ - this.handleDragEvent_ = options.handleDragEvent ? - options.handleDragEvent : ol.interaction.Pointer.handleDragEvent; - - /** - * @type {function(ol.MapBrowserPointerEvent)} - * @private - */ - this.handleMoveEvent_ = options.handleMoveEvent ? - options.handleMoveEvent : ol.interaction.Pointer.handleMoveEvent; - - /** - * @type {function(ol.MapBrowserPointerEvent):boolean} - * @private - */ - this.handleUpEvent_ = options.handleUpEvent ? - options.handleUpEvent : ol.interaction.Pointer.handleUpEvent; - - /** - * @type {boolean} - * @protected - */ - this.handlingDownUpSequence = false; - - /** - * @type {Object.<string, ol.pointer.PointerEvent>} - * @private - */ - this.trackedPointers_ = {}; - - /** - * @type {Array.<ol.pointer.PointerEvent>} - * @protected - */ - this.targetPointers = []; - -}; -ol.inherits(ol.interaction.Pointer, ol.interaction.Interaction); - - -/** - * @param {Array.<ol.pointer.PointerEvent>} pointerEvents List of events. - * @return {ol.Pixel} Centroid pixel. - */ -ol.interaction.Pointer.centroid = function(pointerEvents) { - var length = pointerEvents.length; - var clientX = 0; - var clientY = 0; - for (var i = 0; i < length; i++) { - clientX += pointerEvents[i].clientX; - clientY += pointerEvents[i].clientY; - } - return [clientX / length, clientY / length]; -}; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Whether the event is a pointerdown, pointerdrag - * or pointerup event. - * @private - */ -ol.interaction.Pointer.prototype.isPointerDraggingEvent_ = function(mapBrowserEvent) { - var type = mapBrowserEvent.type; - return ( - type === ol.MapBrowserEventType.POINTERDOWN || - type === ol.MapBrowserEventType.POINTERDRAG || - type === ol.MapBrowserEventType.POINTERUP); -}; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @private - */ -ol.interaction.Pointer.prototype.updateTrackedPointers_ = function(mapBrowserEvent) { - if (this.isPointerDraggingEvent_(mapBrowserEvent)) { - var event = mapBrowserEvent.pointerEvent; - - var id = event.pointerId.toString(); - if (mapBrowserEvent.type == ol.MapBrowserEventType.POINTERUP) { - delete this.trackedPointers_[id]; - } else if (mapBrowserEvent.type == - ol.MapBrowserEventType.POINTERDOWN) { - this.trackedPointers_[id] = event; - } else if (id in this.trackedPointers_) { - // update only when there was a pointerdown event for this pointer - this.trackedPointers_[id] = event; - } - this.targetPointers = ol.obj.getValues(this.trackedPointers_); - } -}; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @this {ol.interaction.Pointer} - */ -ol.interaction.Pointer.handleDragEvent = ol.nullFunction; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Capture dragging. - * @this {ol.interaction.Pointer} - */ -ol.interaction.Pointer.handleUpEvent = ol.functions.FALSE; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Capture dragging. - * @this {ol.interaction.Pointer} - */ -ol.interaction.Pointer.handleDownEvent = ol.functions.FALSE; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @this {ol.interaction.Pointer} - */ -ol.interaction.Pointer.handleMoveEvent = ol.nullFunction; - - -/** - * Handles the {@link ol.MapBrowserEvent map browser event} and may call into - * other functions, if event sequences like e.g. 'drag' or 'down-up' etc. are - * detected. - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} `false` to stop event propagation. - * @this {ol.interaction.Pointer} - * @api - */ -ol.interaction.Pointer.handleEvent = function(mapBrowserEvent) { - if (!(mapBrowserEvent instanceof ol.MapBrowserPointerEvent)) { - return true; - } - - var stopEvent = false; - this.updateTrackedPointers_(mapBrowserEvent); - if (this.handlingDownUpSequence) { - if (mapBrowserEvent.type == ol.MapBrowserEventType.POINTERDRAG) { - this.handleDragEvent_(mapBrowserEvent); - } else if (mapBrowserEvent.type == ol.MapBrowserEventType.POINTERUP) { - var handledUp = this.handleUpEvent_(mapBrowserEvent); - this.handlingDownUpSequence = handledUp && this.targetPointers.length > 0; - } - } else { - if (mapBrowserEvent.type == ol.MapBrowserEventType.POINTERDOWN) { - var handled = this.handleDownEvent_(mapBrowserEvent); - this.handlingDownUpSequence = handled; - stopEvent = this.shouldStopEvent(handled); - } else if (mapBrowserEvent.type == ol.MapBrowserEventType.POINTERMOVE) { - this.handleMoveEvent_(mapBrowserEvent); - } - } - return !stopEvent; -}; - - -/** - * This method is used to determine if "down" events should be propagated to - * other interactions or should be stopped. - * - * The method receives the return code of the "handleDownEvent" function. - * - * By default this function is the "identity" function. It's overidden in - * child classes. - * - * @param {boolean} handled Was the event handled by the interaction? - * @return {boolean} Should the event be stopped? - * @protected - */ -ol.interaction.Pointer.prototype.shouldStopEvent = function(handled) { - return handled; -}; - -goog.provide('ol.interaction.DragPan'); - -goog.require('ol'); -goog.require('ol.ViewHint'); -goog.require('ol.coordinate'); -goog.require('ol.easing'); -goog.require('ol.events.condition'); -goog.require('ol.functions'); -goog.require('ol.interaction.Pointer'); - - -/** - * @classdesc - * Allows the user to pan the map by dragging the map. - * - * @constructor - * @extends {ol.interaction.Pointer} - * @param {olx.interaction.DragPanOptions=} opt_options Options. - * @api - */ -ol.interaction.DragPan = function(opt_options) { - - ol.interaction.Pointer.call(this, { - handleDownEvent: ol.interaction.DragPan.handleDownEvent_, - handleDragEvent: ol.interaction.DragPan.handleDragEvent_, - handleUpEvent: ol.interaction.DragPan.handleUpEvent_ - }); - - var options = opt_options ? opt_options : {}; - - /** - * @private - * @type {ol.Kinetic|undefined} - */ - this.kinetic_ = options.kinetic; - - /** - * @type {ol.Pixel} - */ - this.lastCentroid = null; - - /** - * @type {number} - */ - this.lastPointersCount_; - - /** - * @private - * @type {ol.EventsConditionType} - */ - this.condition_ = options.condition ? - options.condition : ol.events.condition.noModifierKeys; - - /** - * @private - * @type {boolean} - */ - this.noKinetic_ = false; - -}; -ol.inherits(ol.interaction.DragPan, ol.interaction.Pointer); - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @this {ol.interaction.DragPan} - * @private - */ -ol.interaction.DragPan.handleDragEvent_ = function(mapBrowserEvent) { - var targetPointers = this.targetPointers; - var centroid = - ol.interaction.Pointer.centroid(targetPointers); - if (targetPointers.length == this.lastPointersCount_) { - if (this.kinetic_) { - this.kinetic_.update(centroid[0], centroid[1]); - } - if (this.lastCentroid) { - var deltaX = this.lastCentroid[0] - centroid[0]; - var deltaY = centroid[1] - this.lastCentroid[1]; - var map = mapBrowserEvent.map; - var view = map.getView(); - var viewState = view.getState(); - var center = [deltaX, deltaY]; - ol.coordinate.scale(center, viewState.resolution); - ol.coordinate.rotate(center, viewState.rotation); - ol.coordinate.add(center, viewState.center); - center = view.constrainCenter(center); - view.setCenter(center); - } - } else if (this.kinetic_) { - // reset so we don't overestimate the kinetic energy after - // after one finger down, tiny drag, second finger down - this.kinetic_.begin(); - } - this.lastCentroid = centroid; - this.lastPointersCount_ = targetPointers.length; -}; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Stop drag sequence? - * @this {ol.interaction.DragPan} - * @private - */ -ol.interaction.DragPan.handleUpEvent_ = function(mapBrowserEvent) { - var map = mapBrowserEvent.map; - var view = map.getView(); - if (this.targetPointers.length === 0) { - if (!this.noKinetic_ && this.kinetic_ && this.kinetic_.end()) { - var distance = this.kinetic_.getDistance(); - var angle = this.kinetic_.getAngle(); - var center = /** @type {!ol.Coordinate} */ (view.getCenter()); - var centerpx = map.getPixelFromCoordinate(center); - var dest = map.getCoordinateFromPixel([ - centerpx[0] - distance * Math.cos(angle), - centerpx[1] - distance * Math.sin(angle) - ]); - view.animate({ - center: view.constrainCenter(dest), - duration: 500, - easing: ol.easing.easeOut - }); - } - view.setHint(ol.ViewHint.INTERACTING, -1); - return false; - } else { - if (this.kinetic_) { - // reset so we don't overestimate the kinetic energy after - // after one finger up, tiny drag, second finger up - this.kinetic_.begin(); - } - this.lastCentroid = null; - return true; - } -}; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Start drag sequence? - * @this {ol.interaction.DragPan} - * @private - */ -ol.interaction.DragPan.handleDownEvent_ = function(mapBrowserEvent) { - if (this.targetPointers.length > 0 && this.condition_(mapBrowserEvent)) { - var map = mapBrowserEvent.map; - var view = map.getView(); - this.lastCentroid = null; - if (!this.handlingDownUpSequence) { - view.setHint(ol.ViewHint.INTERACTING, 1); - } - // stop any current animation - if (view.getHints()[ol.ViewHint.ANIMATING]) { - view.setCenter(mapBrowserEvent.frameState.viewState.center); - } - if (this.kinetic_) { - this.kinetic_.begin(); - } - // No kinetic as soon as more than one pointer on the screen is - // detected. This is to prevent nasty pans after pinch. - this.noKinetic_ = this.targetPointers.length > 1; - return true; - } else { - return false; - } -}; - - -/** - * @inheritDoc - */ -ol.interaction.DragPan.prototype.shouldStopEvent = ol.functions.FALSE; - -goog.provide('ol.interaction.DragRotate'); - -goog.require('ol'); -goog.require('ol.RotationConstraint'); -goog.require('ol.ViewHint'); -goog.require('ol.events.condition'); -goog.require('ol.functions'); -goog.require('ol.interaction.Interaction'); -goog.require('ol.interaction.Pointer'); - - -/** - * @classdesc - * Allows the user to rotate the map by clicking and dragging on the map, - * normally combined with an {@link ol.events.condition} that limits - * it to when the alt and shift keys are held down. - * - * This interaction is only supported for mouse devices. - * - * @constructor - * @extends {ol.interaction.Pointer} - * @param {olx.interaction.DragRotateOptions=} opt_options Options. - * @api - */ -ol.interaction.DragRotate = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - ol.interaction.Pointer.call(this, { - handleDownEvent: ol.interaction.DragRotate.handleDownEvent_, - handleDragEvent: ol.interaction.DragRotate.handleDragEvent_, - handleUpEvent: ol.interaction.DragRotate.handleUpEvent_ - }); - - /** - * @private - * @type {ol.EventsConditionType} - */ - this.condition_ = options.condition ? - options.condition : ol.events.condition.altShiftKeysOnly; - - /** - * @private - * @type {number|undefined} - */ - this.lastAngle_ = undefined; - - /** - * @private - * @type {number} - */ - this.duration_ = options.duration !== undefined ? options.duration : 250; -}; -ol.inherits(ol.interaction.DragRotate, ol.interaction.Pointer); - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @this {ol.interaction.DragRotate} - * @private - */ -ol.interaction.DragRotate.handleDragEvent_ = function(mapBrowserEvent) { - if (!ol.events.condition.mouseOnly(mapBrowserEvent)) { - return; - } - - var map = mapBrowserEvent.map; - var view = map.getView(); - if (view.getConstraints().rotation === ol.RotationConstraint.disable) { - return; - } - var size = map.getSize(); - var offset = mapBrowserEvent.pixel; - var theta = - Math.atan2(size[1] / 2 - offset[1], offset[0] - size[0] / 2); - if (this.lastAngle_ !== undefined) { - var delta = theta - this.lastAngle_; - var rotation = view.getRotation(); - ol.interaction.Interaction.rotateWithoutConstraints( - view, rotation - delta); - } - this.lastAngle_ = theta; -}; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Stop drag sequence? - * @this {ol.interaction.DragRotate} - * @private - */ -ol.interaction.DragRotate.handleUpEvent_ = function(mapBrowserEvent) { - if (!ol.events.condition.mouseOnly(mapBrowserEvent)) { - return true; - } - - var map = mapBrowserEvent.map; - var view = map.getView(); - view.setHint(ol.ViewHint.INTERACTING, -1); - var rotation = view.getRotation(); - ol.interaction.Interaction.rotate(view, rotation, - undefined, this.duration_); - return false; -}; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Start drag sequence? - * @this {ol.interaction.DragRotate} - * @private - */ -ol.interaction.DragRotate.handleDownEvent_ = function(mapBrowserEvent) { - if (!ol.events.condition.mouseOnly(mapBrowserEvent)) { - return false; - } - - if (ol.events.condition.mouseActionButton(mapBrowserEvent) && - this.condition_(mapBrowserEvent)) { - var map = mapBrowserEvent.map; - map.getView().setHint(ol.ViewHint.INTERACTING, 1); - this.lastAngle_ = undefined; - return true; - } else { - return false; - } -}; - - -/** - * @inheritDoc - */ -ol.interaction.DragRotate.prototype.shouldStopEvent = ol.functions.FALSE; - -// FIXME add rotation - -goog.provide('ol.render.Box'); - -goog.require('ol'); -goog.require('ol.Disposable'); -goog.require('ol.geom.Polygon'); - - -/** - * @constructor - * @extends {ol.Disposable} - * @param {string} className CSS class name. - */ -ol.render.Box = function(className) { - - /** - * @type {ol.geom.Polygon} - * @private - */ - this.geometry_ = null; - - /** - * @type {HTMLDivElement} - * @private - */ - this.element_ = /** @type {HTMLDivElement} */ (document.createElement('div')); - this.element_.style.position = 'absolute'; - this.element_.className = 'ol-box ' + className; - - /** - * @private - * @type {ol.PluggableMap} - */ - this.map_ = null; - - /** - * @private - * @type {ol.Pixel} - */ - this.startPixel_ = null; - - /** - * @private - * @type {ol.Pixel} - */ - this.endPixel_ = null; - -}; -ol.inherits(ol.render.Box, ol.Disposable); - - -/** - * @inheritDoc - */ -ol.render.Box.prototype.disposeInternal = function() { - this.setMap(null); -}; - - -/** - * @private - */ -ol.render.Box.prototype.render_ = function() { - var startPixel = this.startPixel_; - var endPixel = this.endPixel_; - var px = 'px'; - var style = this.element_.style; - style.left = Math.min(startPixel[0], endPixel[0]) + px; - style.top = Math.min(startPixel[1], endPixel[1]) + px; - style.width = Math.abs(endPixel[0] - startPixel[0]) + px; - style.height = Math.abs(endPixel[1] - startPixel[1]) + px; -}; - - -/** - * @param {ol.PluggableMap} map Map. - */ -ol.render.Box.prototype.setMap = function(map) { - if (this.map_) { - this.map_.getOverlayContainer().removeChild(this.element_); - var style = this.element_.style; - style.left = style.top = style.width = style.height = 'inherit'; - } - this.map_ = map; - if (this.map_) { - this.map_.getOverlayContainer().appendChild(this.element_); - } -}; - - -/** - * @param {ol.Pixel} startPixel Start pixel. - * @param {ol.Pixel} endPixel End pixel. - */ -ol.render.Box.prototype.setPixels = function(startPixel, endPixel) { - this.startPixel_ = startPixel; - this.endPixel_ = endPixel; - this.createOrUpdateGeometry(); - this.render_(); -}; - - -/** - * Creates or updates the cached geometry. - */ -ol.render.Box.prototype.createOrUpdateGeometry = function() { - var startPixel = this.startPixel_; - var endPixel = this.endPixel_; - var pixels = [ - startPixel, - [startPixel[0], endPixel[1]], - endPixel, - [endPixel[0], startPixel[1]] - ]; - var coordinates = pixels.map(this.map_.getCoordinateFromPixel, this.map_); - // close the polygon - coordinates[4] = coordinates[0].slice(); - if (!this.geometry_) { - this.geometry_ = new ol.geom.Polygon([coordinates]); - } else { - this.geometry_.setCoordinates([coordinates]); - } -}; - - -/** - * @return {ol.geom.Polygon} Geometry. - */ -ol.render.Box.prototype.getGeometry = function() { - return this.geometry_; -}; - -// FIXME draw drag box -goog.provide('ol.interaction.DragBox'); - -goog.require('ol.events.Event'); -goog.require('ol'); -goog.require('ol.events.condition'); -goog.require('ol.interaction.Pointer'); -goog.require('ol.render.Box'); - - -/** - * @classdesc - * Allows the user to draw a vector box by clicking and dragging on the map, - * normally combined with an {@link ol.events.condition} that limits - * it to when the shift or other key is held down. This is used, for example, - * for zooming to a specific area of the map - * (see {@link ol.interaction.DragZoom} and - * {@link ol.interaction.DragRotateAndZoom}). - * - * This interaction is only supported for mouse devices. - * - * @constructor - * @extends {ol.interaction.Pointer} - * @fires ol.interaction.DragBox.Event - * @param {olx.interaction.DragBoxOptions=} opt_options Options. - * @api - */ -ol.interaction.DragBox = function(opt_options) { - - ol.interaction.Pointer.call(this, { - handleDownEvent: ol.interaction.DragBox.handleDownEvent_, - handleDragEvent: ol.interaction.DragBox.handleDragEvent_, - handleUpEvent: ol.interaction.DragBox.handleUpEvent_ - }); - - var options = opt_options ? opt_options : {}; - - /** - * @type {ol.render.Box} - * @private - */ - this.box_ = new ol.render.Box(options.className || 'ol-dragbox'); - - /** - * @type {number} - * @private - */ - this.minArea_ = options.minArea !== undefined ? options.minArea : 64; - - /** - * @type {ol.Pixel} - * @private - */ - this.startPixel_ = null; - - /** - * @private - * @type {ol.EventsConditionType} - */ - this.condition_ = options.condition ? - options.condition : ol.events.condition.always; - - /** - * @private - * @type {ol.DragBoxEndConditionType} - */ - this.boxEndCondition_ = options.boxEndCondition ? - options.boxEndCondition : ol.interaction.DragBox.defaultBoxEndCondition; -}; -ol.inherits(ol.interaction.DragBox, ol.interaction.Pointer); - - -/** - * The default condition for determining whether the boxend event - * should fire. - * @param {ol.MapBrowserEvent} mapBrowserEvent The originating MapBrowserEvent - * leading to the box end. - * @param {ol.Pixel} startPixel The starting pixel of the box. - * @param {ol.Pixel} endPixel The end pixel of the box. - * @return {boolean} Whether or not the boxend condition should be fired. - * @this {ol.interaction.DragBox} - */ -ol.interaction.DragBox.defaultBoxEndCondition = function(mapBrowserEvent, startPixel, endPixel) { - var width = endPixel[0] - startPixel[0]; - var height = endPixel[1] - startPixel[1]; - return width * width + height * height >= this.minArea_; -}; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @this {ol.interaction.DragBox} - * @private - */ -ol.interaction.DragBox.handleDragEvent_ = function(mapBrowserEvent) { - if (!ol.events.condition.mouseOnly(mapBrowserEvent)) { - return; - } - - this.box_.setPixels(this.startPixel_, mapBrowserEvent.pixel); - - this.dispatchEvent(new ol.interaction.DragBox.Event(ol.interaction.DragBox.EventType_.BOXDRAG, - mapBrowserEvent.coordinate, mapBrowserEvent)); -}; - - -/** - * Returns geometry of last drawn box. - * @return {ol.geom.Polygon} Geometry. - * @api - */ -ol.interaction.DragBox.prototype.getGeometry = function() { - return this.box_.getGeometry(); -}; - - -/** - * To be overridden by child classes. - * FIXME: use constructor option instead of relying on overriding. - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @protected - */ -ol.interaction.DragBox.prototype.onBoxEnd = ol.nullFunction; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Stop drag sequence? - * @this {ol.interaction.DragBox} - * @private - */ -ol.interaction.DragBox.handleUpEvent_ = function(mapBrowserEvent) { - if (!ol.events.condition.mouseOnly(mapBrowserEvent)) { - return true; - } - - this.box_.setMap(null); - - if (this.boxEndCondition_(mapBrowserEvent, - this.startPixel_, mapBrowserEvent.pixel)) { - this.onBoxEnd(mapBrowserEvent); - this.dispatchEvent(new ol.interaction.DragBox.Event(ol.interaction.DragBox.EventType_.BOXEND, - mapBrowserEvent.coordinate, mapBrowserEvent)); - } - return false; -}; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Start drag sequence? - * @this {ol.interaction.DragBox} - * @private - */ -ol.interaction.DragBox.handleDownEvent_ = function(mapBrowserEvent) { - if (!ol.events.condition.mouseOnly(mapBrowserEvent)) { - return false; - } - - if (ol.events.condition.mouseActionButton(mapBrowserEvent) && - this.condition_(mapBrowserEvent)) { - this.startPixel_ = mapBrowserEvent.pixel; - this.box_.setMap(mapBrowserEvent.map); - this.box_.setPixels(this.startPixel_, this.startPixel_); - this.dispatchEvent(new ol.interaction.DragBox.Event(ol.interaction.DragBox.EventType_.BOXSTART, - mapBrowserEvent.coordinate, mapBrowserEvent)); - return true; - } else { - return false; - } -}; - - -/** - * @enum {string} - * @private - */ -ol.interaction.DragBox.EventType_ = { - /** - * Triggered upon drag box start. - * @event ol.interaction.DragBox.Event#boxstart - * @api - */ - BOXSTART: 'boxstart', - - /** - * Triggered on drag when box is active. - * @event ol.interaction.DragBox.Event#boxdrag - * @api - */ - BOXDRAG: 'boxdrag', - - /** - * Triggered upon drag box end. - * @event ol.interaction.DragBox.Event#boxend - * @api - */ - BOXEND: 'boxend' -}; - - -/** - * @classdesc - * Events emitted by {@link ol.interaction.DragBox} instances are instances of - * this type. - * - * @param {string} type The event type. - * @param {ol.Coordinate} coordinate The event coordinate. - * @param {ol.MapBrowserEvent} mapBrowserEvent Originating event. - * @extends {ol.events.Event} - * @constructor - * @implements {oli.DragBoxEvent} - */ -ol.interaction.DragBox.Event = function(type, coordinate, mapBrowserEvent) { - ol.events.Event.call(this, type); - - /** - * The coordinate of the drag event. - * @const - * @type {ol.Coordinate} - * @api - */ - this.coordinate = coordinate; - - /** - * @const - * @type {ol.MapBrowserEvent} - * @api - */ - this.mapBrowserEvent = mapBrowserEvent; - -}; -ol.inherits(ol.interaction.DragBox.Event, ol.events.Event); - -goog.provide('ol.interaction.DragZoom'); - -goog.require('ol'); -goog.require('ol.easing'); -goog.require('ol.events.condition'); -goog.require('ol.extent'); -goog.require('ol.interaction.DragBox'); - - -/** - * @classdesc - * Allows the user to zoom the map by clicking and dragging on the map, - * normally combined with an {@link ol.events.condition} that limits - * it to when a key, shift by default, is held down. - * - * To change the style of the box, use CSS and the `.ol-dragzoom` selector, or - * your custom one configured with `className`. - * - * @constructor - * @extends {ol.interaction.DragBox} - * @param {olx.interaction.DragZoomOptions=} opt_options Options. - * @api - */ -ol.interaction.DragZoom = function(opt_options) { - var options = opt_options ? opt_options : {}; - - var condition = options.condition ? - options.condition : ol.events.condition.shiftKeyOnly; - - /** - * @private - * @type {number} - */ - this.duration_ = options.duration !== undefined ? options.duration : 200; - - /** - * @private - * @type {boolean} - */ - this.out_ = options.out !== undefined ? options.out : false; - - ol.interaction.DragBox.call(this, { - condition: condition, - className: options.className || 'ol-dragzoom' - }); - -}; -ol.inherits(ol.interaction.DragZoom, ol.interaction.DragBox); - - -/** - * @inheritDoc - */ -ol.interaction.DragZoom.prototype.onBoxEnd = function() { - var map = this.getMap(); - - var view = /** @type {!ol.View} */ (map.getView()); - - var size = /** @type {!ol.Size} */ (map.getSize()); - - var extent = this.getGeometry().getExtent(); - - if (this.out_) { - var mapExtent = view.calculateExtent(size); - var boxPixelExtent = ol.extent.createOrUpdateFromCoordinates([ - map.getPixelFromCoordinate(ol.extent.getBottomLeft(extent)), - map.getPixelFromCoordinate(ol.extent.getTopRight(extent))]); - var factor = view.getResolutionForExtent(boxPixelExtent, size); - - ol.extent.scaleFromCenter(mapExtent, 1 / factor); - extent = mapExtent; - } - - var resolution = view.constrainResolution( - view.getResolutionForExtent(extent, size)); - - var center = ol.extent.getCenter(extent); - center = view.constrainCenter(center); - - view.animate({ - resolution: resolution, - center: center, - duration: this.duration_, - easing: ol.easing.easeOut - }); - -}; - -goog.provide('ol.events.KeyCode'); - -/** - * @enum {number} - * @const - */ -ol.events.KeyCode = { - LEFT: 37, - UP: 38, - RIGHT: 39, - DOWN: 40 -}; - -goog.provide('ol.interaction.KeyboardPan'); - -goog.require('ol'); -goog.require('ol.coordinate'); -goog.require('ol.events.EventType'); -goog.require('ol.events.KeyCode'); -goog.require('ol.events.condition'); -goog.require('ol.interaction.Interaction'); - - -/** - * @classdesc - * Allows the user to pan the map using keyboard arrows. - * Note that, although this interaction is by default included in maps, - * the keys can only be used when browser focus is on the element to which - * the keyboard events are attached. By default, this is the map div, - * though you can change this with the `keyboardEventTarget` in - * {@link ol.Map}. `document` never loses focus but, for any other element, - * focus will have to be on, and returned to, this element if the keys are to - * function. - * See also {@link ol.interaction.KeyboardZoom}. - * - * @constructor - * @extends {ol.interaction.Interaction} - * @param {olx.interaction.KeyboardPanOptions=} opt_options Options. - * @api - */ -ol.interaction.KeyboardPan = function(opt_options) { - - ol.interaction.Interaction.call(this, { - handleEvent: ol.interaction.KeyboardPan.handleEvent - }); - - var options = opt_options || {}; - - /** - * @private - * @param {ol.MapBrowserEvent} mapBrowserEvent Browser event. - * @return {boolean} Combined condition result. - */ - this.defaultCondition_ = function(mapBrowserEvent) { - return ol.events.condition.noModifierKeys(mapBrowserEvent) && - ol.events.condition.targetNotEditable(mapBrowserEvent); - }; - - /** - * @private - * @type {ol.EventsConditionType} - */ - this.condition_ = options.condition !== undefined ? - options.condition : this.defaultCondition_; - - /** - * @private - * @type {number} - */ - this.duration_ = options.duration !== undefined ? options.duration : 100; - - /** - * @private - * @type {number} - */ - this.pixelDelta_ = options.pixelDelta !== undefined ? - options.pixelDelta : 128; - -}; -ol.inherits(ol.interaction.KeyboardPan, ol.interaction.Interaction); - -/** - * Handles the {@link ol.MapBrowserEvent map browser event} if it was a - * `KeyEvent`, and decides the direction to pan to (if an arrow key was - * pressed). - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} `false` to stop event propagation. - * @this {ol.interaction.KeyboardPan} - * @api - */ -ol.interaction.KeyboardPan.handleEvent = function(mapBrowserEvent) { - var stopEvent = false; - if (mapBrowserEvent.type == ol.events.EventType.KEYDOWN) { - var keyEvent = mapBrowserEvent.originalEvent; - var keyCode = keyEvent.keyCode; - if (this.condition_(mapBrowserEvent) && - (keyCode == ol.events.KeyCode.DOWN || - keyCode == ol.events.KeyCode.LEFT || - keyCode == ol.events.KeyCode.RIGHT || - keyCode == ol.events.KeyCode.UP)) { - var map = mapBrowserEvent.map; - var view = map.getView(); - var mapUnitsDelta = view.getResolution() * this.pixelDelta_; - var deltaX = 0, deltaY = 0; - if (keyCode == ol.events.KeyCode.DOWN) { - deltaY = -mapUnitsDelta; - } else if (keyCode == ol.events.KeyCode.LEFT) { - deltaX = -mapUnitsDelta; - } else if (keyCode == ol.events.KeyCode.RIGHT) { - deltaX = mapUnitsDelta; - } else { - deltaY = mapUnitsDelta; - } - var delta = [deltaX, deltaY]; - ol.coordinate.rotate(delta, view.getRotation()); - ol.interaction.Interaction.pan(view, delta, this.duration_); - mapBrowserEvent.preventDefault(); - stopEvent = true; - } - } - return !stopEvent; -}; - -goog.provide('ol.interaction.KeyboardZoom'); - -goog.require('ol'); -goog.require('ol.events.EventType'); -goog.require('ol.events.condition'); -goog.require('ol.interaction.Interaction'); - - -/** - * @classdesc - * Allows the user to zoom the map using keyboard + and -. - * Note that, although this interaction is by default included in maps, - * the keys can only be used when browser focus is on the element to which - * the keyboard events are attached. By default, this is the map div, - * though you can change this with the `keyboardEventTarget` in - * {@link ol.Map}. `document` never loses focus but, for any other element, - * focus will have to be on, and returned to, this element if the keys are to - * function. - * See also {@link ol.interaction.KeyboardPan}. - * - * @constructor - * @param {olx.interaction.KeyboardZoomOptions=} opt_options Options. - * @extends {ol.interaction.Interaction} - * @api - */ -ol.interaction.KeyboardZoom = function(opt_options) { - - ol.interaction.Interaction.call(this, { - handleEvent: ol.interaction.KeyboardZoom.handleEvent - }); - - var options = opt_options ? opt_options : {}; - - /** - * @private - * @type {ol.EventsConditionType} - */ - this.condition_ = options.condition ? options.condition : - ol.events.condition.targetNotEditable; - - /** - * @private - * @type {number} - */ - this.delta_ = options.delta ? options.delta : 1; - - /** - * @private - * @type {number} - */ - this.duration_ = options.duration !== undefined ? options.duration : 100; - -}; -ol.inherits(ol.interaction.KeyboardZoom, ol.interaction.Interaction); - - -/** - * Handles the {@link ol.MapBrowserEvent map browser event} if it was a - * `KeyEvent`, and decides whether to zoom in or out (depending on whether the - * key pressed was '+' or '-'). - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} `false` to stop event propagation. - * @this {ol.interaction.KeyboardZoom} - * @api - */ -ol.interaction.KeyboardZoom.handleEvent = function(mapBrowserEvent) { - var stopEvent = false; - if (mapBrowserEvent.type == ol.events.EventType.KEYDOWN || - mapBrowserEvent.type == ol.events.EventType.KEYPRESS) { - var keyEvent = mapBrowserEvent.originalEvent; - var charCode = keyEvent.charCode; - if (this.condition_(mapBrowserEvent) && - (charCode == '+'.charCodeAt(0) || charCode == '-'.charCodeAt(0))) { - var map = mapBrowserEvent.map; - var delta = (charCode == '+'.charCodeAt(0)) ? this.delta_ : -this.delta_; - var view = map.getView(); - ol.interaction.Interaction.zoomByDelta( - view, delta, undefined, this.duration_); - mapBrowserEvent.preventDefault(); - stopEvent = true; - } - } - return !stopEvent; -}; - -goog.provide('ol.interaction.MouseWheelZoom'); - -goog.require('ol'); -goog.require('ol.ViewHint'); -goog.require('ol.easing'); -goog.require('ol.events.EventType'); -goog.require('ol.has'); -goog.require('ol.interaction.Interaction'); -goog.require('ol.math'); - - -/** - * @classdesc - * Allows the user to zoom the map by scrolling the mouse wheel. - * - * @constructor - * @extends {ol.interaction.Interaction} - * @param {olx.interaction.MouseWheelZoomOptions=} opt_options Options. - * @api - */ -ol.interaction.MouseWheelZoom = function(opt_options) { - - ol.interaction.Interaction.call(this, { - handleEvent: ol.interaction.MouseWheelZoom.handleEvent - }); - - var options = opt_options || {}; - - /** - * @private - * @type {number} - */ - this.delta_ = 0; - - /** - * @private - * @type {number} - */ - this.duration_ = options.duration !== undefined ? options.duration : 250; - - /** - * @private - * @type {number} - */ - this.timeout_ = options.timeout !== undefined ? options.timeout : 80; - - /** - * @private - * @type {boolean} - */ - this.useAnchor_ = options.useAnchor !== undefined ? options.useAnchor : true; - - /** - * @private - * @type {boolean} - */ - this.constrainResolution_ = options.constrainResolution || false; - - /** - * @private - * @type {?ol.Coordinate} - */ - this.lastAnchor_ = null; - - /** - * @private - * @type {number|undefined} - */ - this.startTime_ = undefined; - - /** - * @private - * @type {number|undefined} - */ - this.timeoutId_ = undefined; - - /** - * @private - * @type {ol.interaction.MouseWheelZoom.Mode_|undefined} - */ - this.mode_ = undefined; - - /** - * Trackpad events separated by this delay will be considered separate - * interactions. - * @type {number} - */ - this.trackpadEventGap_ = 400; - - /** - * @type {number|undefined} - */ - this.trackpadTimeoutId_ = undefined; - - /** - * The number of delta values per zoom level - * @private - * @type {number} - */ - this.trackpadDeltaPerZoom_ = 300; - - /** - * The zoom factor by which scroll zooming is allowed to exceed the limits. - * @private - * @type {number} - */ - this.trackpadZoomBuffer_ = 1.5; - -}; -ol.inherits(ol.interaction.MouseWheelZoom, ol.interaction.Interaction); - - -/** - * Handles the {@link ol.MapBrowserEvent map browser event} (if it was a - * mousewheel-event) and eventually zooms the map. - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} Allow event propagation. - * @this {ol.interaction.MouseWheelZoom} - * @api - */ -ol.interaction.MouseWheelZoom.handleEvent = function(mapBrowserEvent) { - var type = mapBrowserEvent.type; - if (type !== ol.events.EventType.WHEEL && type !== ol.events.EventType.MOUSEWHEEL) { - return true; - } - - mapBrowserEvent.preventDefault(); - - var map = mapBrowserEvent.map; - var wheelEvent = /** @type {WheelEvent} */ (mapBrowserEvent.originalEvent); - - if (this.useAnchor_) { - this.lastAnchor_ = mapBrowserEvent.coordinate; - } - - // Delta normalisation inspired by - // https://github.com/mapbox/mapbox-gl-js/blob/001c7b9/js/ui/handler/scroll_zoom.js - var delta; - if (mapBrowserEvent.type == ol.events.EventType.WHEEL) { - delta = wheelEvent.deltaY; - if (ol.has.FIREFOX && - wheelEvent.deltaMode === WheelEvent.DOM_DELTA_PIXEL) { - delta /= ol.has.DEVICE_PIXEL_RATIO; - } - if (wheelEvent.deltaMode === WheelEvent.DOM_DELTA_LINE) { - delta *= 40; - } - } else if (mapBrowserEvent.type == ol.events.EventType.MOUSEWHEEL) { - delta = -wheelEvent.wheelDeltaY; - if (ol.has.SAFARI) { - delta /= 3; - } - } - - if (delta === 0) { - return false; - } - - var now = Date.now(); - - if (this.startTime_ === undefined) { - this.startTime_ = now; - } - - if (!this.mode_ || now - this.startTime_ > this.trackpadEventGap_) { - this.mode_ = Math.abs(delta) < 4 ? - ol.interaction.MouseWheelZoom.Mode_.TRACKPAD : - ol.interaction.MouseWheelZoom.Mode_.WHEEL; - } - - if (this.mode_ === ol.interaction.MouseWheelZoom.Mode_.TRACKPAD) { - var view = map.getView(); - if (this.trackpadTimeoutId_) { - clearTimeout(this.trackpadTimeoutId_); - } else { - view.setHint(ol.ViewHint.INTERACTING, 1); - } - this.trackpadTimeoutId_ = setTimeout(this.decrementInteractingHint_.bind(this), this.trackpadEventGap_); - var resolution = view.getResolution() * Math.pow(2, delta / this.trackpadDeltaPerZoom_); - var minResolution = view.getMinResolution(); - var maxResolution = view.getMaxResolution(); - var rebound = 0; - if (resolution < minResolution) { - resolution = Math.max(resolution, minResolution / this.trackpadZoomBuffer_); - rebound = 1; - } else if (resolution > maxResolution) { - resolution = Math.min(resolution, maxResolution * this.trackpadZoomBuffer_); - rebound = -1; - } - if (this.lastAnchor_) { - var center = view.calculateCenterZoom(resolution, this.lastAnchor_); - view.setCenter(view.constrainCenter(center)); - } - view.setResolution(resolution); - - if (rebound === 0 && this.constrainResolution_) { - view.animate({ - resolution: view.constrainResolution(resolution, delta > 0 ? -1 : 1), - easing: ol.easing.easeOut, - anchor: this.lastAnchor_, - duration: this.duration_ - }); - } - - if (rebound > 0) { - view.animate({ - resolution: minResolution, - easing: ol.easing.easeOut, - anchor: this.lastAnchor_, - duration: 500 - }); - } else if (rebound < 0) { - view.animate({ - resolution: maxResolution, - easing: ol.easing.easeOut, - anchor: this.lastAnchor_, - duration: 500 - }); - } - this.startTime_ = now; - return false; - } - - this.delta_ += delta; - - var timeLeft = Math.max(this.timeout_ - (now - this.startTime_), 0); - - clearTimeout(this.timeoutId_); - this.timeoutId_ = setTimeout(this.handleWheelZoom_.bind(this, map), timeLeft); - - return false; -}; - - -/** - * @private - */ -ol.interaction.MouseWheelZoom.prototype.decrementInteractingHint_ = function() { - this.trackpadTimeoutId_ = undefined; - var view = this.getMap().getView(); - view.setHint(ol.ViewHint.INTERACTING, -1); -}; - - -/** - * @private - * @param {ol.PluggableMap} map Map. - */ -ol.interaction.MouseWheelZoom.prototype.handleWheelZoom_ = function(map) { - var view = map.getView(); - if (view.getAnimating()) { - view.cancelAnimations(); - } - var maxDelta = ol.MOUSEWHEELZOOM_MAXDELTA; - var delta = ol.math.clamp(this.delta_, -maxDelta, maxDelta); - ol.interaction.Interaction.zoomByDelta(view, -delta, this.lastAnchor_, - this.duration_); - this.mode_ = undefined; - this.delta_ = 0; - this.lastAnchor_ = null; - this.startTime_ = undefined; - this.timeoutId_ = undefined; -}; - - -/** - * Enable or disable using the mouse's location as an anchor when zooming - * @param {boolean} useAnchor true to zoom to the mouse's location, false - * to zoom to the center of the map - * @api - */ -ol.interaction.MouseWheelZoom.prototype.setMouseAnchor = function(useAnchor) { - this.useAnchor_ = useAnchor; - if (!useAnchor) { - this.lastAnchor_ = null; - } -}; - - -/** - * @enum {string} - * @private - */ -ol.interaction.MouseWheelZoom.Mode_ = { - TRACKPAD: 'trackpad', - WHEEL: 'wheel' -}; - -goog.provide('ol.interaction.PinchRotate'); - -goog.require('ol'); -goog.require('ol.ViewHint'); -goog.require('ol.functions'); -goog.require('ol.interaction.Interaction'); -goog.require('ol.interaction.Pointer'); -goog.require('ol.RotationConstraint'); - - -/** - * @classdesc - * Allows the user to rotate the map by twisting with two fingers - * on a touch screen. - * - * @constructor - * @extends {ol.interaction.Pointer} - * @param {olx.interaction.PinchRotateOptions=} opt_options Options. - * @api - */ -ol.interaction.PinchRotate = function(opt_options) { - - ol.interaction.Pointer.call(this, { - handleDownEvent: ol.interaction.PinchRotate.handleDownEvent_, - handleDragEvent: ol.interaction.PinchRotate.handleDragEvent_, - handleUpEvent: ol.interaction.PinchRotate.handleUpEvent_ - }); - - var options = opt_options || {}; - - /** - * @private - * @type {ol.Coordinate} - */ - this.anchor_ = null; - - /** - * @private - * @type {number|undefined} - */ - this.lastAngle_ = undefined; - - /** - * @private - * @type {boolean} - */ - this.rotating_ = false; - - /** - * @private - * @type {number} - */ - this.rotationDelta_ = 0.0; - - /** - * @private - * @type {number} - */ - this.threshold_ = options.threshold !== undefined ? options.threshold : 0.3; - - /** - * @private - * @type {number} - */ - this.duration_ = options.duration !== undefined ? options.duration : 250; - -}; -ol.inherits(ol.interaction.PinchRotate, ol.interaction.Pointer); - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @this {ol.interaction.PinchRotate} - * @private - */ -ol.interaction.PinchRotate.handleDragEvent_ = function(mapBrowserEvent) { - var rotationDelta = 0.0; - - var touch0 = this.targetPointers[0]; - var touch1 = this.targetPointers[1]; - - // angle between touches - var angle = Math.atan2( - touch1.clientY - touch0.clientY, - touch1.clientX - touch0.clientX); - - if (this.lastAngle_ !== undefined) { - var delta = angle - this.lastAngle_; - this.rotationDelta_ += delta; - if (!this.rotating_ && - Math.abs(this.rotationDelta_) > this.threshold_) { - this.rotating_ = true; - } - rotationDelta = delta; - } - this.lastAngle_ = angle; - - var map = mapBrowserEvent.map; - var view = map.getView(); - if (view.getConstraints().rotation === ol.RotationConstraint.disable) { - return; - } - - // rotate anchor point. - // FIXME: should be the intersection point between the lines: - // touch0,touch1 and previousTouch0,previousTouch1 - var viewportPosition = map.getViewport().getBoundingClientRect(); - var centroid = ol.interaction.Pointer.centroid(this.targetPointers); - centroid[0] -= viewportPosition.left; - centroid[1] -= viewportPosition.top; - this.anchor_ = map.getCoordinateFromPixel(centroid); - - // rotate - if (this.rotating_) { - var rotation = view.getRotation(); - map.render(); - ol.interaction.Interaction.rotateWithoutConstraints(view, - rotation + rotationDelta, this.anchor_); - } -}; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Stop drag sequence? - * @this {ol.interaction.PinchRotate} - * @private - */ -ol.interaction.PinchRotate.handleUpEvent_ = function(mapBrowserEvent) { - if (this.targetPointers.length < 2) { - var map = mapBrowserEvent.map; - var view = map.getView(); - view.setHint(ol.ViewHint.INTERACTING, -1); - if (this.rotating_) { - var rotation = view.getRotation(); - ol.interaction.Interaction.rotate( - view, rotation, this.anchor_, this.duration_); - } - return false; - } else { - return true; - } -}; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Start drag sequence? - * @this {ol.interaction.PinchRotate} - * @private - */ -ol.interaction.PinchRotate.handleDownEvent_ = function(mapBrowserEvent) { - if (this.targetPointers.length >= 2) { - var map = mapBrowserEvent.map; - this.anchor_ = null; - this.lastAngle_ = undefined; - this.rotating_ = false; - this.rotationDelta_ = 0.0; - if (!this.handlingDownUpSequence) { - map.getView().setHint(ol.ViewHint.INTERACTING, 1); - } - return true; - } else { - return false; - } -}; - - -/** - * @inheritDoc - */ -ol.interaction.PinchRotate.prototype.shouldStopEvent = ol.functions.FALSE; - -goog.provide('ol.interaction.PinchZoom'); - -goog.require('ol'); -goog.require('ol.ViewHint'); -goog.require('ol.functions'); -goog.require('ol.interaction.Interaction'); -goog.require('ol.interaction.Pointer'); - - -/** - * @classdesc - * Allows the user to zoom the map by pinching with two fingers - * on a touch screen. - * - * @constructor - * @extends {ol.interaction.Pointer} - * @param {olx.interaction.PinchZoomOptions=} opt_options Options. - * @api - */ -ol.interaction.PinchZoom = function(opt_options) { - - ol.interaction.Pointer.call(this, { - handleDownEvent: ol.interaction.PinchZoom.handleDownEvent_, - handleDragEvent: ol.interaction.PinchZoom.handleDragEvent_, - handleUpEvent: ol.interaction.PinchZoom.handleUpEvent_ - }); - - var options = opt_options ? opt_options : {}; - - /** - * @private - * @type {boolean} - */ - this.constrainResolution_ = options.constrainResolution || false; - - /** - * @private - * @type {ol.Coordinate} - */ - this.anchor_ = null; - - /** - * @private - * @type {number} - */ - this.duration_ = options.duration !== undefined ? options.duration : 400; - - /** - * @private - * @type {number|undefined} - */ - this.lastDistance_ = undefined; - - /** - * @private - * @type {number} - */ - this.lastScaleDelta_ = 1; - -}; -ol.inherits(ol.interaction.PinchZoom, ol.interaction.Pointer); - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @this {ol.interaction.PinchZoom} - * @private - */ -ol.interaction.PinchZoom.handleDragEvent_ = function(mapBrowserEvent) { - var scaleDelta = 1.0; - - var touch0 = this.targetPointers[0]; - var touch1 = this.targetPointers[1]; - var dx = touch0.clientX - touch1.clientX; - var dy = touch0.clientY - touch1.clientY; - - // distance between touches - var distance = Math.sqrt(dx * dx + dy * dy); - - if (this.lastDistance_ !== undefined) { - scaleDelta = this.lastDistance_ / distance; - } - this.lastDistance_ = distance; - - - var map = mapBrowserEvent.map; - var view = map.getView(); - var resolution = view.getResolution(); - var maxResolution = view.getMaxResolution(); - var minResolution = view.getMinResolution(); - var newResolution = resolution * scaleDelta; - if (newResolution > maxResolution) { - scaleDelta = maxResolution / resolution; - newResolution = maxResolution; - } else if (newResolution < minResolution) { - scaleDelta = minResolution / resolution; - newResolution = minResolution; - } - - if (scaleDelta != 1.0) { - this.lastScaleDelta_ = scaleDelta; - } - - // scale anchor point. - var viewportPosition = map.getViewport().getBoundingClientRect(); - var centroid = ol.interaction.Pointer.centroid(this.targetPointers); - centroid[0] -= viewportPosition.left; - centroid[1] -= viewportPosition.top; - this.anchor_ = map.getCoordinateFromPixel(centroid); - - // scale, bypass the resolution constraint - map.render(); - ol.interaction.Interaction.zoomWithoutConstraints(view, newResolution, this.anchor_); -}; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Stop drag sequence? - * @this {ol.interaction.PinchZoom} - * @private - */ -ol.interaction.PinchZoom.handleUpEvent_ = function(mapBrowserEvent) { - if (this.targetPointers.length < 2) { - var map = mapBrowserEvent.map; - var view = map.getView(); - view.setHint(ol.ViewHint.INTERACTING, -1); - var resolution = view.getResolution(); - if (this.constrainResolution_ || - resolution < view.getMinResolution() || - resolution > view.getMaxResolution()) { - // Zoom to final resolution, with an animation, and provide a - // direction not to zoom out/in if user was pinching in/out. - // Direction is > 0 if pinching out, and < 0 if pinching in. - var direction = this.lastScaleDelta_ - 1; - ol.interaction.Interaction.zoom(view, resolution, - this.anchor_, this.duration_, direction); - } - return false; - } else { - return true; - } -}; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Start drag sequence? - * @this {ol.interaction.PinchZoom} - * @private - */ -ol.interaction.PinchZoom.handleDownEvent_ = function(mapBrowserEvent) { - if (this.targetPointers.length >= 2) { - var map = mapBrowserEvent.map; - this.anchor_ = null; - this.lastDistance_ = undefined; - this.lastScaleDelta_ = 1; - if (!this.handlingDownUpSequence) { - map.getView().setHint(ol.ViewHint.INTERACTING, 1); - } - return true; - } else { - return false; - } -}; - - -/** - * @inheritDoc - */ -ol.interaction.PinchZoom.prototype.shouldStopEvent = ol.functions.FALSE; - -goog.provide('ol.interaction'); - -goog.require('ol.Collection'); -goog.require('ol.Kinetic'); -goog.require('ol.interaction.DoubleClickZoom'); -goog.require('ol.interaction.DragPan'); -goog.require('ol.interaction.DragRotate'); -goog.require('ol.interaction.DragZoom'); -goog.require('ol.interaction.KeyboardPan'); -goog.require('ol.interaction.KeyboardZoom'); -goog.require('ol.interaction.MouseWheelZoom'); -goog.require('ol.interaction.PinchRotate'); -goog.require('ol.interaction.PinchZoom'); - - -/** - * Set of interactions included in maps by default. Specific interactions can be - * excluded by setting the appropriate option to false in the constructor - * options, but the order of the interactions is fixed. If you want to specify - * a different order for interactions, you will need to create your own - * {@link ol.interaction.Interaction} instances and insert them into a - * {@link ol.Collection} in the order you want before creating your - * {@link ol.Map} instance. The default set of interactions, in sequence, is: - * * {@link ol.interaction.DragRotate} - * * {@link ol.interaction.DoubleClickZoom} - * * {@link ol.interaction.DragPan} - * * {@link ol.interaction.PinchRotate} - * * {@link ol.interaction.PinchZoom} - * * {@link ol.interaction.KeyboardPan} - * * {@link ol.interaction.KeyboardZoom} - * * {@link ol.interaction.MouseWheelZoom} - * * {@link ol.interaction.DragZoom} - * - * @param {olx.interaction.DefaultsOptions=} opt_options Defaults options. - * @return {ol.Collection.<ol.interaction.Interaction>} A collection of - * interactions to be used with the ol.Map constructor's interactions option. - * @api - */ -ol.interaction.defaults = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - var interactions = new ol.Collection(); - - var kinetic = new ol.Kinetic(-0.005, 0.05, 100); - - var altShiftDragRotate = options.altShiftDragRotate !== undefined ? - options.altShiftDragRotate : true; - if (altShiftDragRotate) { - interactions.push(new ol.interaction.DragRotate()); - } - - var doubleClickZoom = options.doubleClickZoom !== undefined ? - options.doubleClickZoom : true; - if (doubleClickZoom) { - interactions.push(new ol.interaction.DoubleClickZoom({ - delta: options.zoomDelta, - duration: options.zoomDuration - })); - } - - var dragPan = options.dragPan !== undefined ? options.dragPan : true; - if (dragPan) { - interactions.push(new ol.interaction.DragPan({ - kinetic: kinetic - })); - } - - var pinchRotate = options.pinchRotate !== undefined ? options.pinchRotate : - true; - if (pinchRotate) { - interactions.push(new ol.interaction.PinchRotate()); - } - - var pinchZoom = options.pinchZoom !== undefined ? options.pinchZoom : true; - if (pinchZoom) { - interactions.push(new ol.interaction.PinchZoom({ - constrainResolution: options.constrainResolution, - duration: options.zoomDuration - })); - } - - var keyboard = options.keyboard !== undefined ? options.keyboard : true; - if (keyboard) { - interactions.push(new ol.interaction.KeyboardPan()); - interactions.push(new ol.interaction.KeyboardZoom({ - delta: options.zoomDelta, - duration: options.zoomDuration - })); - } - - var mouseWheelZoom = options.mouseWheelZoom !== undefined ? - options.mouseWheelZoom : true; - if (mouseWheelZoom) { - interactions.push(new ol.interaction.MouseWheelZoom({ - constrainResolution: options.constrainResolution, - duration: options.zoomDuration - })); - } - - var shiftDragZoom = options.shiftDragZoom !== undefined ? - options.shiftDragZoom : true; - if (shiftDragZoom) { - interactions.push(new ol.interaction.DragZoom({ - duration: options.zoomDuration - })); - } - - return interactions; - -}; - -goog.provide('ol.LayerType'); - -/** - * A layer type used when creating layer renderers. - * @enum {string} - */ -ol.LayerType = { - IMAGE: 'IMAGE', - TILE: 'TILE', - VECTOR_TILE: 'VECTOR_TILE', - VECTOR: 'VECTOR' -}; - -goog.provide('ol.render.Event'); - -goog.require('ol'); -goog.require('ol.events.Event'); - - -/** - * @constructor - * @extends {ol.events.Event} - * @implements {oli.render.Event} - * @param {ol.render.EventType} type Type. - * @param {ol.render.VectorContext=} opt_vectorContext Vector context. - * @param {olx.FrameState=} opt_frameState Frame state. - * @param {?CanvasRenderingContext2D=} opt_context Context. - * @param {?ol.webgl.Context=} opt_glContext WebGL Context. - */ -ol.render.Event = function( - type, opt_vectorContext, opt_frameState, opt_context, - opt_glContext) { - - ol.events.Event.call(this, type); - - /** - * For canvas, this is an instance of {@link ol.render.canvas.Immediate}. - * @type {ol.render.VectorContext|undefined} - * @api - */ - this.vectorContext = opt_vectorContext; - - /** - * An object representing the current render frame state. - * @type {olx.FrameState|undefined} - * @api - */ - this.frameState = opt_frameState; - - /** - * Canvas context. Only available when a Canvas renderer is used, null - * otherwise. - * @type {CanvasRenderingContext2D|null|undefined} - * @api - */ - this.context = opt_context; - - /** - * WebGL context. Only available when a WebGL renderer is used, null - * otherwise. - * @type {ol.webgl.Context|null|undefined} - * @api - */ - this.glContext = opt_glContext; - -}; -ol.inherits(ol.render.Event, ol.events.Event); - -goog.provide('ol.render.EventType'); - -/** - * @enum {string} - */ -ol.render.EventType = { - /** - * @event ol.render.Event#postcompose - * @api - */ - POSTCOMPOSE: 'postcompose', - /** - * @event ol.render.Event#precompose - * @api - */ - PRECOMPOSE: 'precompose', - /** - * @event ol.render.Event#render - * @api - */ - RENDER: 'render' -}; - -goog.provide('ol.render.canvas'); - - -/** - * @const - * @type {string} - */ -ol.render.canvas.defaultFont = '10px sans-serif'; - - -/** - * @const - * @type {ol.Color} - */ -ol.render.canvas.defaultFillStyle = [0, 0, 0, 1]; - - -/** - * @const - * @type {string} - */ -ol.render.canvas.defaultLineCap = 'round'; - - -/** - * @const - * @type {Array.<number>} - */ -ol.render.canvas.defaultLineDash = []; - - -/** - * @const - * @type {number} - */ -ol.render.canvas.defaultLineDashOffset = 0; - - -/** - * @const - * @type {string} - */ -ol.render.canvas.defaultLineJoin = 'round'; - - -/** - * @const - * @type {number} - */ -ol.render.canvas.defaultMiterLimit = 10; - - -/** - * @const - * @type {ol.Color} - */ -ol.render.canvas.defaultStrokeStyle = [0, 0, 0, 1]; - - -/** - * @const - * @type {string} - */ -ol.render.canvas.defaultTextAlign = 'center'; - - -/** - * @const - * @type {string} - */ -ol.render.canvas.defaultTextBaseline = 'middle'; - - -/** - * @const - * @type {number} - */ -ol.render.canvas.defaultLineWidth = 1; - - -/** - * @param {CanvasRenderingContext2D} context Context. - * @param {number} rotation Rotation. - * @param {number} offsetX X offset. - * @param {number} offsetY Y offset. - */ -ol.render.canvas.rotateAtOffset = function(context, rotation, offsetX, offsetY) { - if (rotation !== 0) { - context.translate(offsetX, offsetY); - context.rotate(rotation); - context.translate(-offsetX, -offsetY); - } -}; - -goog.provide('ol.color'); - -goog.require('ol.asserts'); -goog.require('ol.math'); - - -/** - * This RegExp matches # followed by 3 or 6 hex digits. - * @const - * @type {RegExp} - * @private - */ -ol.color.HEX_COLOR_RE_ = /^#(?:[0-9a-f]{3}){1,2}$/i; - - -/** - * Regular expression for matching potential named color style strings. - * @const - * @type {RegExp} - * @private - */ -ol.color.NAMED_COLOR_RE_ = /^([a-z]*)$/i; - - -/** - * Return the color as an array. This function maintains a cache of calculated - * arrays which means the result should not be modified. - * @param {ol.Color|string} color Color. - * @return {ol.Color} Color. - * @api - */ -ol.color.asArray = function(color) { - if (Array.isArray(color)) { - return color; - } else { - return ol.color.fromString(/** @type {string} */ (color)); - } -}; - - -/** - * Return the color as an rgba string. - * @param {ol.Color|string} color Color. - * @return {string} Rgba string. - * @api - */ -ol.color.asString = function(color) { - if (typeof color === 'string') { - return color; - } else { - return ol.color.toString(color); - } -}; - -/** - * Return named color as an rgba string. - * @param {string} color Named color. - * @return {string} Rgb string. - */ -ol.color.fromNamed = function(color) { - var el = document.createElement('div'); - el.style.color = color; - document.body.appendChild(el); - var rgb = getComputedStyle(el).color; - document.body.removeChild(el); - return rgb; -}; - - -/** - * @param {string} s String. - * @return {ol.Color} Color. - */ -ol.color.fromString = ( - function() { - - // We maintain a small cache of parsed strings. To provide cheap LRU-like - // semantics, whenever the cache grows too large we simply delete an - // arbitrary 25% of the entries. - - /** - * @const - * @type {number} - */ - var MAX_CACHE_SIZE = 1024; - - /** - * @type {Object.<string, ol.Color>} - */ - var cache = {}; - - /** - * @type {number} - */ - var cacheSize = 0; - - return ( - /** - * @param {string} s String. - * @return {ol.Color} Color. - */ - function(s) { - var color; - if (cache.hasOwnProperty(s)) { - color = cache[s]; - } else { - if (cacheSize >= MAX_CACHE_SIZE) { - var i = 0; - var key; - for (key in cache) { - if ((i++ & 3) === 0) { - delete cache[key]; - --cacheSize; - } - } - } - color = ol.color.fromStringInternal_(s); - cache[s] = color; - ++cacheSize; - } - return color; - }); - - })(); - - -/** - * @param {string} s String. - * @private - * @return {ol.Color} Color. - */ -ol.color.fromStringInternal_ = function(s) { - var r, g, b, a, color, parts; - - if (ol.color.NAMED_COLOR_RE_.exec(s)) { - s = ol.color.fromNamed(s); - } - - if (ol.color.HEX_COLOR_RE_.exec(s)) { // hex - var n = s.length - 1; // number of hex digits - ol.asserts.assert(n == 3 || n == 6, 54); // Hex color should have 3 or 6 digits - var d = n == 3 ? 1 : 2; // number of digits per channel - r = parseInt(s.substr(1 + 0 * d, d), 16); - g = parseInt(s.substr(1 + 1 * d, d), 16); - b = parseInt(s.substr(1 + 2 * d, d), 16); - if (d == 1) { - r = (r << 4) + r; - g = (g << 4) + g; - b = (b << 4) + b; - } - a = 1; - color = [r, g, b, a]; - } else if (s.indexOf('rgba(') == 0) { // rgba() - parts = s.slice(5, -1).split(',').map(Number); - color = ol.color.normalize(parts); - } else if (s.indexOf('rgb(') == 0) { // rgb() - parts = s.slice(4, -1).split(',').map(Number); - parts.push(1); - color = ol.color.normalize(parts); - } else { - ol.asserts.assert(false, 14); // Invalid color - } - return /** @type {ol.Color} */ (color); -}; - - -/** - * @param {ol.Color} color Color. - * @param {ol.Color=} opt_color Color. - * @return {ol.Color} Clamped color. - */ -ol.color.normalize = function(color, opt_color) { - var result = opt_color || []; - result[0] = ol.math.clamp((color[0] + 0.5) | 0, 0, 255); - result[1] = ol.math.clamp((color[1] + 0.5) | 0, 0, 255); - result[2] = ol.math.clamp((color[2] + 0.5) | 0, 0, 255); - result[3] = ol.math.clamp(color[3], 0, 1); - return result; -}; - - -/** - * @param {ol.Color} color Color. - * @return {string} String. - */ -ol.color.toString = function(color) { - var r = color[0]; - if (r != (r | 0)) { - r = (r + 0.5) | 0; - } - var g = color[1]; - if (g != (g | 0)) { - g = (g + 0.5) | 0; - } - var b = color[2]; - if (b != (b | 0)) { - b = (b + 0.5) | 0; - } - var a = color[3] === undefined ? 1 : color[3]; - return 'rgba(' + r + ',' + g + ',' + b + ',' + a + ')'; -}; - -goog.provide('ol.colorlike'); - -goog.require('ol.color'); - - -/** - * @param {ol.Color|ol.ColorLike} color Color. - * @return {ol.ColorLike} The color as an ol.ColorLike - * @api - */ -ol.colorlike.asColorLike = function(color) { - if (ol.colorlike.isColorLike(color)) { - return /** @type {string|CanvasPattern|CanvasGradient} */ (color); - } else { - return ol.color.asString(/** @type {ol.Color} */ (color)); - } -}; - - -/** - * @param {?} color The value that is potentially an ol.ColorLike - * @return {boolean} Whether the color is an ol.ColorLike - */ -ol.colorlike.isColorLike = function(color) { - return ( - typeof color === 'string' || - color instanceof CanvasPattern || - color instanceof CanvasGradient - ); -}; - -goog.provide('ol.render.VectorContext'); - - -/** - * Context for drawing geometries. A vector context is available on render - * events and does not need to be constructed directly. - * @constructor - * @abstract - * @struct - * @api - */ -ol.render.VectorContext = function() { -}; - - -/** - * Render a geometry with a custom renderer. - * - * @param {ol.geom.SimpleGeometry} geometry Geometry. - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @param {Function} renderer Renderer. - */ -ol.render.VectorContext.prototype.drawCustom = function(geometry, feature, renderer) {}; - - -/** - * Render a geometry. - * - * @param {ol.geom.Geometry} geometry The geometry to render. - */ -ol.render.VectorContext.prototype.drawGeometry = function(geometry) {}; - - -/** - * Set the rendering style. - * - * @param {ol.style.Style} style The rendering style. - */ -ol.render.VectorContext.prototype.setStyle = function(style) {}; - - -/** - * @param {ol.geom.Circle} circleGeometry Circle geometry. - * @param {ol.Feature} feature Feature. - */ -ol.render.VectorContext.prototype.drawCircle = function(circleGeometry, feature) {}; - - -/** - * @param {ol.Feature} feature Feature. - * @param {ol.style.Style} style Style. - */ -ol.render.VectorContext.prototype.drawFeature = function(feature, style) {}; - - -/** - * @param {ol.geom.GeometryCollection} geometryCollectionGeometry Geometry - * collection. - * @param {ol.Feature} feature Feature. - */ -ol.render.VectorContext.prototype.drawGeometryCollection = function(geometryCollectionGeometry, feature) {}; - - -/** - * @param {ol.geom.LineString|ol.render.Feature} lineStringGeometry Line - * string geometry. - * @param {ol.Feature|ol.render.Feature} feature Feature. - */ -ol.render.VectorContext.prototype.drawLineString = function(lineStringGeometry, feature) {}; - - -/** - * @param {ol.geom.MultiLineString|ol.render.Feature} multiLineStringGeometry - * MultiLineString geometry. - * @param {ol.Feature|ol.render.Feature} feature Feature. - */ -ol.render.VectorContext.prototype.drawMultiLineString = function(multiLineStringGeometry, feature) {}; - - -/** - * @param {ol.geom.MultiPoint|ol.render.Feature} multiPointGeometry MultiPoint - * geometry. - * @param {ol.Feature|ol.render.Feature} feature Feature. - */ -ol.render.VectorContext.prototype.drawMultiPoint = function(multiPointGeometry, feature) {}; - - -/** - * @param {ol.geom.MultiPolygon} multiPolygonGeometry MultiPolygon geometry. - * @param {ol.Feature|ol.render.Feature} feature Feature. - */ -ol.render.VectorContext.prototype.drawMultiPolygon = function(multiPolygonGeometry, feature) {}; - - -/** - * @param {ol.geom.Point|ol.render.Feature} pointGeometry Point geometry. - * @param {ol.Feature|ol.render.Feature} feature Feature. - */ -ol.render.VectorContext.prototype.drawPoint = function(pointGeometry, feature) {}; - - -/** - * @param {ol.geom.Polygon|ol.render.Feature} polygonGeometry Polygon - * geometry. - * @param {ol.Feature|ol.render.Feature} feature Feature. - */ -ol.render.VectorContext.prototype.drawPolygon = function(polygonGeometry, feature) {}; - - -/** - * @param {ol.geom.Geometry|ol.render.Feature} geometry Geometry. - * @param {ol.Feature|ol.render.Feature} feature Feature. - */ -ol.render.VectorContext.prototype.drawText = function(geometry, feature) {}; - - -/** - * @param {ol.style.Fill} fillStyle Fill style. - * @param {ol.style.Stroke} strokeStyle Stroke style. - */ -ol.render.VectorContext.prototype.setFillStrokeStyle = function(fillStyle, strokeStyle) {}; - - -/** - * @param {ol.style.Image} imageStyle Image style. - */ -ol.render.VectorContext.prototype.setImageStyle = function(imageStyle) {}; - - -/** - * @param {ol.style.Text} textStyle Text style. - */ -ol.render.VectorContext.prototype.setTextStyle = function(textStyle) {}; - -// FIXME test, especially polygons with holes and multipolygons -// FIXME need to handle large thick features (where pixel size matters) -// FIXME add offset and end to ol.geom.flat.transform.transform2D? - -goog.provide('ol.render.canvas.Immediate'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.colorlike'); -goog.require('ol.extent'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.SimpleGeometry'); -goog.require('ol.geom.flat.transform'); -goog.require('ol.has'); -goog.require('ol.render.VectorContext'); -goog.require('ol.render.canvas'); -goog.require('ol.transform'); - - -/** - * @classdesc - * A concrete subclass of {@link ol.render.VectorContext} that implements - * direct rendering of features and geometries to an HTML5 Canvas context. - * Instances of this class are created internally by the library and - * provided to application code as vectorContext member of the - * {@link ol.render.Event} object associated with postcompose, precompose and - * render events emitted by layers and maps. - * - * @constructor - * @extends {ol.render.VectorContext} - * @param {CanvasRenderingContext2D} context Context. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.Extent} extent Extent. - * @param {ol.Transform} transform Transform. - * @param {number} viewRotation View rotation. - * @struct - */ -ol.render.canvas.Immediate = function(context, pixelRatio, extent, transform, viewRotation) { - ol.render.VectorContext.call(this); - - /** - * @private - * @type {CanvasRenderingContext2D} - */ - this.context_ = context; - - /** - * @private - * @type {number} - */ - this.pixelRatio_ = pixelRatio; - - /** - * @private - * @type {ol.Extent} - */ - this.extent_ = extent; - - /** - * @private - * @type {ol.Transform} - */ - this.transform_ = transform; - - /** - * @private - * @type {number} - */ - this.viewRotation_ = viewRotation; - - /** - * @private - * @type {?ol.CanvasFillState} - */ - this.contextFillState_ = null; - - /** - * @private - * @type {?ol.CanvasStrokeState} - */ - this.contextStrokeState_ = null; - - /** - * @private - * @type {?ol.CanvasTextState} - */ - this.contextTextState_ = null; - - /** - * @private - * @type {?ol.CanvasFillState} - */ - this.fillState_ = null; - - /** - * @private - * @type {?ol.CanvasStrokeState} - */ - this.strokeState_ = null; - - /** - * @private - * @type {HTMLCanvasElement|HTMLVideoElement|Image} - */ - this.image_ = null; - - /** - * @private - * @type {number} - */ - this.imageAnchorX_ = 0; - - /** - * @private - * @type {number} - */ - this.imageAnchorY_ = 0; - - /** - * @private - * @type {number} - */ - this.imageHeight_ = 0; - - /** - * @private - * @type {number} - */ - this.imageOpacity_ = 0; - - /** - * @private - * @type {number} - */ - this.imageOriginX_ = 0; - - /** - * @private - * @type {number} - */ - this.imageOriginY_ = 0; - - /** - * @private - * @type {boolean} - */ - this.imageRotateWithView_ = false; - - /** - * @private - * @type {number} - */ - this.imageRotation_ = 0; - - /** - * @private - * @type {number} - */ - this.imageScale_ = 0; - - /** - * @private - * @type {boolean} - */ - this.imageSnapToPixel_ = false; - - /** - * @private - * @type {number} - */ - this.imageWidth_ = 0; - - /** - * @private - * @type {string} - */ - this.text_ = ''; - - /** - * @private - * @type {number} - */ - this.textOffsetX_ = 0; - - /** - * @private - * @type {number} - */ - this.textOffsetY_ = 0; - - /** - * @private - * @type {boolean} - */ - this.textRotateWithView_ = false; - - /** - * @private - * @type {number} - */ - this.textRotation_ = 0; - - /** - * @private - * @type {number} - */ - this.textScale_ = 0; - - /** - * @private - * @type {?ol.CanvasFillState} - */ - this.textFillState_ = null; - - /** - * @private - * @type {?ol.CanvasStrokeState} - */ - this.textStrokeState_ = null; - - /** - * @private - * @type {?ol.CanvasTextState} - */ - this.textState_ = null; - - /** - * @private - * @type {Array.<number>} - */ - this.pixelCoordinates_ = []; - - /** - * @private - * @type {ol.Transform} - */ - this.tmpLocalTransform_ = ol.transform.create(); - -}; -ol.inherits(ol.render.canvas.Immediate, ol.render.VectorContext); - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @private - */ -ol.render.canvas.Immediate.prototype.drawImages_ = function(flatCoordinates, offset, end, stride) { - if (!this.image_) { - return; - } - var pixelCoordinates = ol.geom.flat.transform.transform2D( - flatCoordinates, offset, end, 2, this.transform_, - this.pixelCoordinates_); - var context = this.context_; - var localTransform = this.tmpLocalTransform_; - var alpha = context.globalAlpha; - if (this.imageOpacity_ != 1) { - context.globalAlpha = alpha * this.imageOpacity_; - } - var rotation = this.imageRotation_; - if (this.imageRotateWithView_) { - rotation += this.viewRotation_; - } - var i, ii; - for (i = 0, ii = pixelCoordinates.length; i < ii; i += 2) { - var x = pixelCoordinates[i] - this.imageAnchorX_; - var y = pixelCoordinates[i + 1] - this.imageAnchorY_; - if (this.imageSnapToPixel_) { - x = Math.round(x); - y = Math.round(y); - } - if (rotation !== 0 || this.imageScale_ != 1) { - var centerX = x + this.imageAnchorX_; - var centerY = y + this.imageAnchorY_; - ol.transform.compose(localTransform, - centerX, centerY, - this.imageScale_, this.imageScale_, - rotation, - -centerX, -centerY); - context.setTransform.apply(context, localTransform); - } - context.drawImage(this.image_, this.imageOriginX_, this.imageOriginY_, - this.imageWidth_, this.imageHeight_, x, y, - this.imageWidth_, this.imageHeight_); - } - if (rotation !== 0 || this.imageScale_ != 1) { - context.setTransform(1, 0, 0, 1, 0, 0); - } - if (this.imageOpacity_ != 1) { - context.globalAlpha = alpha; - } -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @private - */ -ol.render.canvas.Immediate.prototype.drawText_ = function(flatCoordinates, offset, end, stride) { - if (!this.textState_ || this.text_ === '') { - return; - } - if (this.textFillState_) { - this.setContextFillState_(this.textFillState_); - } - if (this.textStrokeState_) { - this.setContextStrokeState_(this.textStrokeState_); - } - this.setContextTextState_(this.textState_); - var pixelCoordinates = ol.geom.flat.transform.transform2D( - flatCoordinates, offset, end, stride, this.transform_, - this.pixelCoordinates_); - var context = this.context_; - var rotation = this.textRotation_; - if (this.textRotateWithView_) { - rotation += this.viewRotation_; - } - for (; offset < end; offset += stride) { - var x = pixelCoordinates[offset] + this.textOffsetX_; - var y = pixelCoordinates[offset + 1] + this.textOffsetY_; - if (rotation !== 0 || this.textScale_ != 1) { - var localTransform = ol.transform.compose(this.tmpLocalTransform_, - x, y, - this.textScale_, this.textScale_, - rotation, - -x, -y); - context.setTransform.apply(context, localTransform); - } - if (this.textStrokeState_) { - context.strokeText(this.text_, x, y); - } - if (this.textFillState_) { - context.fillText(this.text_, x, y); - } - } - if (rotation !== 0 || this.textScale_ != 1) { - context.setTransform(1, 0, 0, 1, 0, 0); - } -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {boolean} close Close. - * @private - * @return {number} end End. - */ -ol.render.canvas.Immediate.prototype.moveToLineTo_ = function(flatCoordinates, offset, end, stride, close) { - var context = this.context_; - var pixelCoordinates = ol.geom.flat.transform.transform2D( - flatCoordinates, offset, end, stride, this.transform_, - this.pixelCoordinates_); - context.moveTo(pixelCoordinates[0], pixelCoordinates[1]); - var length = pixelCoordinates.length; - if (close) { - length -= 2; - } - for (var i = 2; i < length; i += 2) { - context.lineTo(pixelCoordinates[i], pixelCoordinates[i + 1]); - } - if (close) { - context.closePath(); - } - return end; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<number>} ends Ends. - * @param {number} stride Stride. - * @private - * @return {number} End. - */ -ol.render.canvas.Immediate.prototype.drawRings_ = function(flatCoordinates, offset, ends, stride) { - var i, ii; - for (i = 0, ii = ends.length; i < ii; ++i) { - offset = this.moveToLineTo_( - flatCoordinates, offset, ends[i], stride, true); - } - return offset; -}; - - -/** - * Render a circle geometry into the canvas. Rendering is immediate and uses - * the current fill and stroke styles. - * - * @param {ol.geom.Circle} geometry Circle geometry. - * @override - * @api - */ -ol.render.canvas.Immediate.prototype.drawCircle = function(geometry) { - if (!ol.extent.intersects(this.extent_, geometry.getExtent())) { - return; - } - if (this.fillState_ || this.strokeState_) { - if (this.fillState_) { - this.setContextFillState_(this.fillState_); - } - if (this.strokeState_) { - this.setContextStrokeState_(this.strokeState_); - } - var pixelCoordinates = ol.geom.SimpleGeometry.transform2D( - geometry, this.transform_, this.pixelCoordinates_); - var dx = pixelCoordinates[2] - pixelCoordinates[0]; - var dy = pixelCoordinates[3] - pixelCoordinates[1]; - var radius = Math.sqrt(dx * dx + dy * dy); - var context = this.context_; - context.beginPath(); - context.arc( - pixelCoordinates[0], pixelCoordinates[1], radius, 0, 2 * Math.PI); - if (this.fillState_) { - context.fill(); - } - if (this.strokeState_) { - context.stroke(); - } - } - if (this.text_ !== '') { - this.drawText_(geometry.getCenter(), 0, 2, 2); - } -}; - - -/** - * Set the rendering style. Note that since this is an immediate rendering API, - * any `zIndex` on the provided style will be ignored. - * - * @param {ol.style.Style} style The rendering style. - * @override - * @api - */ -ol.render.canvas.Immediate.prototype.setStyle = function(style) { - this.setFillStrokeStyle(style.getFill(), style.getStroke()); - this.setImageStyle(style.getImage()); - this.setTextStyle(style.getText()); -}; - - -/** - * Render a geometry into the canvas. Call - * {@link ol.render.canvas.Immediate#setStyle} first to set the rendering style. - * - * @param {ol.geom.Geometry|ol.render.Feature} geometry The geometry to render. - * @override - * @api - */ -ol.render.canvas.Immediate.prototype.drawGeometry = function(geometry) { - var type = geometry.getType(); - switch (type) { - case ol.geom.GeometryType.POINT: - this.drawPoint(/** @type {ol.geom.Point} */ (geometry)); - break; - case ol.geom.GeometryType.LINE_STRING: - this.drawLineString(/** @type {ol.geom.LineString} */ (geometry)); - break; - case ol.geom.GeometryType.POLYGON: - this.drawPolygon(/** @type {ol.geom.Polygon} */ (geometry)); - break; - case ol.geom.GeometryType.MULTI_POINT: - this.drawMultiPoint(/** @type {ol.geom.MultiPoint} */ (geometry)); - break; - case ol.geom.GeometryType.MULTI_LINE_STRING: - this.drawMultiLineString(/** @type {ol.geom.MultiLineString} */ (geometry)); - break; - case ol.geom.GeometryType.MULTI_POLYGON: - this.drawMultiPolygon(/** @type {ol.geom.MultiPolygon} */ (geometry)); - break; - case ol.geom.GeometryType.GEOMETRY_COLLECTION: - this.drawGeometryCollection(/** @type {ol.geom.GeometryCollection} */ (geometry)); - break; - case ol.geom.GeometryType.CIRCLE: - this.drawCircle(/** @type {ol.geom.Circle} */ (geometry)); - break; - default: - } -}; - - -/** - * Render a feature into the canvas. Note that any `zIndex` on the provided - * style will be ignored - features are rendered immediately in the order that - * this method is called. If you need `zIndex` support, you should be using an - * {@link ol.layer.Vector} instead. - * - * @param {ol.Feature} feature Feature. - * @param {ol.style.Style} style Style. - * @override - * @api - */ -ol.render.canvas.Immediate.prototype.drawFeature = function(feature, style) { - var geometry = style.getGeometryFunction()(feature); - if (!geometry || - !ol.extent.intersects(this.extent_, geometry.getExtent())) { - return; - } - this.setStyle(style); - this.drawGeometry(geometry); -}; - - -/** - * Render a GeometryCollection to the canvas. Rendering is immediate and - * uses the current styles appropriate for each geometry in the collection. - * - * @param {ol.geom.GeometryCollection} geometry Geometry collection. - * @override - */ -ol.render.canvas.Immediate.prototype.drawGeometryCollection = function(geometry) { - var geometries = geometry.getGeometriesArray(); - var i, ii; - for (i = 0, ii = geometries.length; i < ii; ++i) { - this.drawGeometry(geometries[i]); - } -}; - - -/** - * Render a Point geometry into the canvas. Rendering is immediate and uses - * the current style. - * - * @param {ol.geom.Point|ol.render.Feature} geometry Point geometry. - * @override - */ -ol.render.canvas.Immediate.prototype.drawPoint = function(geometry) { - var flatCoordinates = geometry.getFlatCoordinates(); - var stride = geometry.getStride(); - if (this.image_) { - this.drawImages_(flatCoordinates, 0, flatCoordinates.length, stride); - } - if (this.text_ !== '') { - this.drawText_(flatCoordinates, 0, flatCoordinates.length, stride); - } -}; - - -/** - * Render a MultiPoint geometry into the canvas. Rendering is immediate and - * uses the current style. - * - * @param {ol.geom.MultiPoint|ol.render.Feature} geometry MultiPoint geometry. - * @override - */ -ol.render.canvas.Immediate.prototype.drawMultiPoint = function(geometry) { - var flatCoordinates = geometry.getFlatCoordinates(); - var stride = geometry.getStride(); - if (this.image_) { - this.drawImages_(flatCoordinates, 0, flatCoordinates.length, stride); - } - if (this.text_ !== '') { - this.drawText_(flatCoordinates, 0, flatCoordinates.length, stride); - } -}; - - -/** - * Render a LineString into the canvas. Rendering is immediate and uses - * the current style. - * - * @param {ol.geom.LineString|ol.render.Feature} geometry LineString geometry. - * @override - */ -ol.render.canvas.Immediate.prototype.drawLineString = function(geometry) { - if (!ol.extent.intersects(this.extent_, geometry.getExtent())) { - return; - } - if (this.strokeState_) { - this.setContextStrokeState_(this.strokeState_); - var context = this.context_; - var flatCoordinates = geometry.getFlatCoordinates(); - context.beginPath(); - this.moveToLineTo_(flatCoordinates, 0, flatCoordinates.length, - geometry.getStride(), false); - context.stroke(); - } - if (this.text_ !== '') { - var flatMidpoint = geometry.getFlatMidpoint(); - this.drawText_(flatMidpoint, 0, 2, 2); - } -}; - - -/** - * Render a MultiLineString geometry into the canvas. Rendering is immediate - * and uses the current style. - * - * @param {ol.geom.MultiLineString|ol.render.Feature} geometry MultiLineString - * geometry. - * @override - */ -ol.render.canvas.Immediate.prototype.drawMultiLineString = function(geometry) { - var geometryExtent = geometry.getExtent(); - if (!ol.extent.intersects(this.extent_, geometryExtent)) { - return; - } - if (this.strokeState_) { - this.setContextStrokeState_(this.strokeState_); - var context = this.context_; - var flatCoordinates = geometry.getFlatCoordinates(); - var offset = 0; - var ends = geometry.getEnds(); - var stride = geometry.getStride(); - context.beginPath(); - var i, ii; - for (i = 0, ii = ends.length; i < ii; ++i) { - offset = this.moveToLineTo_( - flatCoordinates, offset, ends[i], stride, false); - } - context.stroke(); - } - if (this.text_ !== '') { - var flatMidpoints = geometry.getFlatMidpoints(); - this.drawText_(flatMidpoints, 0, flatMidpoints.length, 2); - } -}; - - -/** - * Render a Polygon geometry into the canvas. Rendering is immediate and uses - * the current style. - * - * @param {ol.geom.Polygon|ol.render.Feature} geometry Polygon geometry. - * @override - */ -ol.render.canvas.Immediate.prototype.drawPolygon = function(geometry) { - if (!ol.extent.intersects(this.extent_, geometry.getExtent())) { - return; - } - if (this.strokeState_ || this.fillState_) { - if (this.fillState_) { - this.setContextFillState_(this.fillState_); - } - if (this.strokeState_) { - this.setContextStrokeState_(this.strokeState_); - } - var context = this.context_; - context.beginPath(); - this.drawRings_(geometry.getOrientedFlatCoordinates(), - 0, geometry.getEnds(), geometry.getStride()); - if (this.fillState_) { - context.fill(); - } - if (this.strokeState_) { - context.stroke(); - } - } - if (this.text_ !== '') { - var flatInteriorPoint = geometry.getFlatInteriorPoint(); - this.drawText_(flatInteriorPoint, 0, 2, 2); - } -}; - - -/** - * Render MultiPolygon geometry into the canvas. Rendering is immediate and - * uses the current style. - * @param {ol.geom.MultiPolygon} geometry MultiPolygon geometry. - * @override - */ -ol.render.canvas.Immediate.prototype.drawMultiPolygon = function(geometry) { - if (!ol.extent.intersects(this.extent_, geometry.getExtent())) { - return; - } - if (this.strokeState_ || this.fillState_) { - if (this.fillState_) { - this.setContextFillState_(this.fillState_); - } - if (this.strokeState_) { - this.setContextStrokeState_(this.strokeState_); - } - var context = this.context_; - var flatCoordinates = geometry.getOrientedFlatCoordinates(); - var offset = 0; - var endss = geometry.getEndss(); - var stride = geometry.getStride(); - var i, ii; - context.beginPath(); - for (i = 0, ii = endss.length; i < ii; ++i) { - var ends = endss[i]; - offset = this.drawRings_(flatCoordinates, offset, ends, stride); - } - if (this.fillState_) { - context.fill(); - } - if (this.strokeState_) { - context.stroke(); - } - } - if (this.text_ !== '') { - var flatInteriorPoints = geometry.getFlatInteriorPoints(); - this.drawText_(flatInteriorPoints, 0, flatInteriorPoints.length, 2); - } -}; - - -/** - * @param {ol.CanvasFillState} fillState Fill state. - * @private - */ -ol.render.canvas.Immediate.prototype.setContextFillState_ = function(fillState) { - var context = this.context_; - var contextFillState = this.contextFillState_; - if (!contextFillState) { - context.fillStyle = fillState.fillStyle; - this.contextFillState_ = { - fillStyle: fillState.fillStyle - }; - } else { - if (contextFillState.fillStyle != fillState.fillStyle) { - contextFillState.fillStyle = context.fillStyle = fillState.fillStyle; - } - } -}; - - -/** - * @param {ol.CanvasStrokeState} strokeState Stroke state. - * @private - */ -ol.render.canvas.Immediate.prototype.setContextStrokeState_ = function(strokeState) { - var context = this.context_; - var contextStrokeState = this.contextStrokeState_; - if (!contextStrokeState) { - context.lineCap = strokeState.lineCap; - if (ol.has.CANVAS_LINE_DASH) { - context.setLineDash(strokeState.lineDash); - context.lineDashOffset = strokeState.lineDashOffset; - } - context.lineJoin = strokeState.lineJoin; - context.lineWidth = strokeState.lineWidth; - context.miterLimit = strokeState.miterLimit; - context.strokeStyle = strokeState.strokeStyle; - this.contextStrokeState_ = { - lineCap: strokeState.lineCap, - lineDash: strokeState.lineDash, - lineDashOffset: strokeState.lineDashOffset, - lineJoin: strokeState.lineJoin, - lineWidth: strokeState.lineWidth, - miterLimit: strokeState.miterLimit, - strokeStyle: strokeState.strokeStyle - }; - } else { - if (contextStrokeState.lineCap != strokeState.lineCap) { - contextStrokeState.lineCap = context.lineCap = strokeState.lineCap; - } - if (ol.has.CANVAS_LINE_DASH) { - if (!ol.array.equals( - contextStrokeState.lineDash, strokeState.lineDash)) { - context.setLineDash(contextStrokeState.lineDash = strokeState.lineDash); - } - if (contextStrokeState.lineDashOffset != strokeState.lineDashOffset) { - contextStrokeState.lineDashOffset = context.lineDashOffset = - strokeState.lineDashOffset; - } - } - if (contextStrokeState.lineJoin != strokeState.lineJoin) { - contextStrokeState.lineJoin = context.lineJoin = strokeState.lineJoin; - } - if (contextStrokeState.lineWidth != strokeState.lineWidth) { - contextStrokeState.lineWidth = context.lineWidth = strokeState.lineWidth; - } - if (contextStrokeState.miterLimit != strokeState.miterLimit) { - contextStrokeState.miterLimit = context.miterLimit = - strokeState.miterLimit; - } - if (contextStrokeState.strokeStyle != strokeState.strokeStyle) { - contextStrokeState.strokeStyle = context.strokeStyle = - strokeState.strokeStyle; - } - } -}; - - -/** - * @param {ol.CanvasTextState} textState Text state. - * @private - */ -ol.render.canvas.Immediate.prototype.setContextTextState_ = function(textState) { - var context = this.context_; - var contextTextState = this.contextTextState_; - var textAlign = textState.textAlign ? - textState.textAlign : ol.render.canvas.defaultTextAlign; - if (!contextTextState) { - context.font = textState.font; - context.textAlign = textAlign; - context.textBaseline = textState.textBaseline; - this.contextTextState_ = { - font: textState.font, - textAlign: textAlign, - textBaseline: textState.textBaseline - }; - } else { - if (contextTextState.font != textState.font) { - contextTextState.font = context.font = textState.font; - } - if (contextTextState.textAlign != textAlign) { - contextTextState.textAlign = textAlign; - } - if (contextTextState.textBaseline != textState.textBaseline) { - contextTextState.textBaseline = context.textBaseline = - textState.textBaseline; - } - } -}; - - -/** - * Set the fill and stroke style for subsequent draw operations. To clear - * either fill or stroke styles, pass null for the appropriate parameter. - * - * @param {ol.style.Fill} fillStyle Fill style. - * @param {ol.style.Stroke} strokeStyle Stroke style. - * @override - */ -ol.render.canvas.Immediate.prototype.setFillStrokeStyle = function(fillStyle, strokeStyle) { - if (!fillStyle) { - this.fillState_ = null; - } else { - var fillStyleColor = fillStyle.getColor(); - this.fillState_ = { - fillStyle: ol.colorlike.asColorLike(fillStyleColor ? - fillStyleColor : ol.render.canvas.defaultFillStyle) - }; - } - if (!strokeStyle) { - this.strokeState_ = null; - } else { - var strokeStyleColor = strokeStyle.getColor(); - var strokeStyleLineCap = strokeStyle.getLineCap(); - var strokeStyleLineDash = strokeStyle.getLineDash(); - var strokeStyleLineDashOffset = strokeStyle.getLineDashOffset(); - var strokeStyleLineJoin = strokeStyle.getLineJoin(); - var strokeStyleWidth = strokeStyle.getWidth(); - var strokeStyleMiterLimit = strokeStyle.getMiterLimit(); - this.strokeState_ = { - lineCap: strokeStyleLineCap !== undefined ? - strokeStyleLineCap : ol.render.canvas.defaultLineCap, - lineDash: strokeStyleLineDash ? - strokeStyleLineDash : ol.render.canvas.defaultLineDash, - lineDashOffset: strokeStyleLineDashOffset ? - strokeStyleLineDashOffset : ol.render.canvas.defaultLineDashOffset, - lineJoin: strokeStyleLineJoin !== undefined ? - strokeStyleLineJoin : ol.render.canvas.defaultLineJoin, - lineWidth: this.pixelRatio_ * (strokeStyleWidth !== undefined ? - strokeStyleWidth : ol.render.canvas.defaultLineWidth), - miterLimit: strokeStyleMiterLimit !== undefined ? - strokeStyleMiterLimit : ol.render.canvas.defaultMiterLimit, - strokeStyle: ol.colorlike.asColorLike(strokeStyleColor ? - strokeStyleColor : ol.render.canvas.defaultStrokeStyle) - }; - } -}; - - -/** - * Set the image style for subsequent draw operations. Pass null to remove - * the image style. - * - * @param {ol.style.Image} imageStyle Image style. - * @override - */ -ol.render.canvas.Immediate.prototype.setImageStyle = function(imageStyle) { - if (!imageStyle) { - this.image_ = null; - } else { - var imageAnchor = imageStyle.getAnchor(); - // FIXME pixel ratio - var imageImage = imageStyle.getImage(1); - var imageOrigin = imageStyle.getOrigin(); - var imageSize = imageStyle.getSize(); - this.imageAnchorX_ = imageAnchor[0]; - this.imageAnchorY_ = imageAnchor[1]; - this.imageHeight_ = imageSize[1]; - this.image_ = imageImage; - this.imageOpacity_ = imageStyle.getOpacity(); - this.imageOriginX_ = imageOrigin[0]; - this.imageOriginY_ = imageOrigin[1]; - this.imageRotateWithView_ = imageStyle.getRotateWithView(); - this.imageRotation_ = imageStyle.getRotation(); - this.imageScale_ = imageStyle.getScale() * this.pixelRatio_; - this.imageSnapToPixel_ = imageStyle.getSnapToPixel(); - this.imageWidth_ = imageSize[0]; - } -}; - - -/** - * Set the text style for subsequent draw operations. Pass null to - * remove the text style. - * - * @param {ol.style.Text} textStyle Text style. - * @override - */ -ol.render.canvas.Immediate.prototype.setTextStyle = function(textStyle) { - if (!textStyle) { - this.text_ = ''; - } else { - var textFillStyle = textStyle.getFill(); - if (!textFillStyle) { - this.textFillState_ = null; - } else { - var textFillStyleColor = textFillStyle.getColor(); - this.textFillState_ = { - fillStyle: ol.colorlike.asColorLike(textFillStyleColor ? - textFillStyleColor : ol.render.canvas.defaultFillStyle) - }; - } - var textStrokeStyle = textStyle.getStroke(); - if (!textStrokeStyle) { - this.textStrokeState_ = null; - } else { - var textStrokeStyleColor = textStrokeStyle.getColor(); - var textStrokeStyleLineCap = textStrokeStyle.getLineCap(); - var textStrokeStyleLineDash = textStrokeStyle.getLineDash(); - var textStrokeStyleLineDashOffset = textStrokeStyle.getLineDashOffset(); - var textStrokeStyleLineJoin = textStrokeStyle.getLineJoin(); - var textStrokeStyleWidth = textStrokeStyle.getWidth(); - var textStrokeStyleMiterLimit = textStrokeStyle.getMiterLimit(); - this.textStrokeState_ = { - lineCap: textStrokeStyleLineCap !== undefined ? - textStrokeStyleLineCap : ol.render.canvas.defaultLineCap, - lineDash: textStrokeStyleLineDash ? - textStrokeStyleLineDash : ol.render.canvas.defaultLineDash, - lineDashOffset: textStrokeStyleLineDashOffset ? - textStrokeStyleLineDashOffset : ol.render.canvas.defaultLineDashOffset, - lineJoin: textStrokeStyleLineJoin !== undefined ? - textStrokeStyleLineJoin : ol.render.canvas.defaultLineJoin, - lineWidth: textStrokeStyleWidth !== undefined ? - textStrokeStyleWidth : ol.render.canvas.defaultLineWidth, - miterLimit: textStrokeStyleMiterLimit !== undefined ? - textStrokeStyleMiterLimit : ol.render.canvas.defaultMiterLimit, - strokeStyle: ol.colorlike.asColorLike(textStrokeStyleColor ? - textStrokeStyleColor : ol.render.canvas.defaultStrokeStyle) - }; - } - var textFont = textStyle.getFont(); - var textOffsetX = textStyle.getOffsetX(); - var textOffsetY = textStyle.getOffsetY(); - var textRotateWithView = textStyle.getRotateWithView(); - var textRotation = textStyle.getRotation(); - var textScale = textStyle.getScale(); - var textText = textStyle.getText(); - var textTextAlign = textStyle.getTextAlign(); - var textTextBaseline = textStyle.getTextBaseline(); - this.textState_ = { - font: textFont !== undefined ? - textFont : ol.render.canvas.defaultFont, - textAlign: textTextAlign !== undefined ? - textTextAlign : ol.render.canvas.defaultTextAlign, - textBaseline: textTextBaseline !== undefined ? - textTextBaseline : ol.render.canvas.defaultTextBaseline - }; - this.text_ = textText !== undefined ? textText : ''; - this.textOffsetX_ = - textOffsetX !== undefined ? (this.pixelRatio_ * textOffsetX) : 0; - this.textOffsetY_ = - textOffsetY !== undefined ? (this.pixelRatio_ * textOffsetY) : 0; - this.textRotateWithView_ = textRotateWithView !== undefined ? textRotateWithView : false; - this.textRotation_ = textRotation !== undefined ? textRotation : 0; - this.textScale_ = this.pixelRatio_ * (textScale !== undefined ? - textScale : 1); - } -}; - -goog.provide('ol.ImageState'); - -/** - * @enum {number} - */ -ol.ImageState = { - IDLE: 0, - LOADING: 1, - LOADED: 2, - ERROR: 3 -}; - -goog.provide('ol.renderer.Layer'); - -goog.require('ol'); -goog.require('ol.ImageState'); -goog.require('ol.Observable'); -goog.require('ol.TileState'); -goog.require('ol.asserts'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.functions'); -goog.require('ol.source.State'); - - -/** - * @constructor - * @extends {ol.Observable} - * @param {ol.layer.Layer} layer Layer. - * @struct - */ -ol.renderer.Layer = function(layer) { - - ol.Observable.call(this); - - /** - * @private - * @type {ol.layer.Layer} - */ - this.layer_ = layer; - - -}; -ol.inherits(ol.renderer.Layer, ol.Observable); - - -/** - * @param {ol.Coordinate} coordinate Coordinate. - * @param {olx.FrameState} frameState Frame state. - * @param {number} hitTolerance Hit tolerance in pixels. - * @param {function(this: S, (ol.Feature|ol.render.Feature), ol.layer.Layer): T} - * callback Feature callback. - * @param {S} thisArg Value to use as `this` when executing `callback`. - * @return {T|undefined} Callback result. - * @template S,T - */ -ol.renderer.Layer.prototype.forEachFeatureAtCoordinate = ol.nullFunction; - - -/** - * @param {ol.Coordinate} coordinate Coordinate. - * @param {olx.FrameState} frameState Frame state. - * @return {boolean} Is there a feature at the given coordinate? - */ -ol.renderer.Layer.prototype.hasFeatureAtCoordinate = ol.functions.FALSE; - - -/** - * Create a function that adds loaded tiles to the tile lookup. - * @param {ol.source.Tile} source Tile source. - * @param {ol.proj.Projection} projection Projection of the tiles. - * @param {Object.<number, Object.<string, ol.Tile>>} tiles Lookup of loaded - * tiles by zoom level. - * @return {function(number, ol.TileRange):boolean} A function that can be - * called with a zoom level and a tile range to add loaded tiles to the - * lookup. - * @protected - */ -ol.renderer.Layer.prototype.createLoadedTileFinder = function(source, projection, tiles) { - return ( - /** - * @param {number} zoom Zoom level. - * @param {ol.TileRange} tileRange Tile range. - * @return {boolean} The tile range is fully loaded. - */ - function(zoom, tileRange) { - function callback(tile) { - if (!tiles[zoom]) { - tiles[zoom] = {}; - } - tiles[zoom][tile.tileCoord.toString()] = tile; - } - return source.forEachLoadedTile(projection, zoom, tileRange, callback); - }); -}; - - -/** - * @return {ol.layer.Layer} Layer. - */ -ol.renderer.Layer.prototype.getLayer = function() { - return this.layer_; -}; - - -/** - * Handle changes in image state. - * @param {ol.events.Event} event Image change event. - * @private - */ -ol.renderer.Layer.prototype.handleImageChange_ = function(event) { - var image = /** @type {ol.Image} */ (event.target); - if (image.getState() === ol.ImageState.LOADED) { - this.renderIfReadyAndVisible(); - } -}; - - -/** - * Load the image if not already loaded, and register the image change - * listener if needed. - * @param {ol.ImageBase} image Image. - * @return {boolean} `true` if the image is already loaded, `false` - * otherwise. - * @protected - */ -ol.renderer.Layer.prototype.loadImage = function(image) { - var imageState = image.getState(); - if (imageState != ol.ImageState.LOADED && - imageState != ol.ImageState.ERROR) { - ol.events.listen(image, ol.events.EventType.CHANGE, - this.handleImageChange_, this); - } - if (imageState == ol.ImageState.IDLE) { - image.load(); - imageState = image.getState(); - } - return imageState == ol.ImageState.LOADED; -}; - - -/** - * @protected - */ -ol.renderer.Layer.prototype.renderIfReadyAndVisible = function() { - var layer = this.getLayer(); - if (layer.getVisible() && layer.getSourceState() == ol.source.State.READY) { - this.changed(); - } -}; - - -/** - * @param {olx.FrameState} frameState Frame state. - * @param {ol.source.Tile} tileSource Tile source. - * @protected - */ -ol.renderer.Layer.prototype.scheduleExpireCache = function(frameState, tileSource) { - if (tileSource.canExpireCache()) { - /** - * @param {ol.source.Tile} tileSource Tile source. - * @param {ol.PluggableMap} map Map. - * @param {olx.FrameState} frameState Frame state. - */ - var postRenderFunction = function(tileSource, map, frameState) { - var tileSourceKey = ol.getUid(tileSource).toString(); - if (tileSourceKey in frameState.usedTiles) { - tileSource.expireCache(frameState.viewState.projection, - frameState.usedTiles[tileSourceKey]); - } - }.bind(null, tileSource); - - frameState.postRenderFunctions.push( - /** @type {ol.PostRenderFunction} */ (postRenderFunction) - ); - } -}; - - -/** - * @param {Object.<string, ol.Attribution>} attributionsSet Attributions - * set (target). - * @param {Array.<ol.Attribution>} attributions Attributions (source). - * @protected - */ -ol.renderer.Layer.prototype.updateAttributions = function(attributionsSet, attributions) { - if (attributions) { - var attribution, i, ii; - for (i = 0, ii = attributions.length; i < ii; ++i) { - attribution = attributions[i]; - attributionsSet[ol.getUid(attribution).toString()] = attribution; - } - } -}; - - -/** - * @param {olx.FrameState} frameState Frame state. - * @param {ol.source.Source} source Source. - * @protected - */ -ol.renderer.Layer.prototype.updateLogos = function(frameState, source) { - var logo = source.getLogo(); - if (logo !== undefined) { - if (typeof logo === 'string') { - frameState.logos[logo] = ''; - } else if (logo) { - ol.asserts.assert(typeof logo.href == 'string', 44); // `logo.href` should be a string. - ol.asserts.assert(typeof logo.src == 'string', 45); // `logo.src` should be a string. - frameState.logos[logo.src] = logo.href; - } - } -}; - - -/** - * @param {Object.<string, Object.<string, ol.TileRange>>} usedTiles Used tiles. - * @param {ol.source.Tile} tileSource Tile source. - * @param {number} z Z. - * @param {ol.TileRange} tileRange Tile range. - * @protected - */ -ol.renderer.Layer.prototype.updateUsedTiles = function(usedTiles, tileSource, z, tileRange) { - // FIXME should we use tilesToDrawByZ instead? - var tileSourceKey = ol.getUid(tileSource).toString(); - var zKey = z.toString(); - if (tileSourceKey in usedTiles) { - if (zKey in usedTiles[tileSourceKey]) { - usedTiles[tileSourceKey][zKey].extend(tileRange); - } else { - usedTiles[tileSourceKey][zKey] = tileRange; - } - } else { - usedTiles[tileSourceKey] = {}; - usedTiles[tileSourceKey][zKey] = tileRange; - } -}; - - -/** - * Manage tile pyramid. - * This function performs a number of functions related to the tiles at the - * current zoom and lower zoom levels: - * - registers idle tiles in frameState.wantedTiles so that they are not - * discarded by the tile queue - * - enqueues missing tiles - * @param {olx.FrameState} frameState Frame state. - * @param {ol.source.Tile} tileSource Tile source. - * @param {ol.tilegrid.TileGrid} tileGrid Tile grid. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.proj.Projection} projection Projection. - * @param {ol.Extent} extent Extent. - * @param {number} currentZ Current Z. - * @param {number} preload Load low resolution tiles up to 'preload' levels. - * @param {function(this: T, ol.Tile)=} opt_tileCallback Tile callback. - * @param {T=} opt_this Object to use as `this` in `opt_tileCallback`. - * @protected - * @template T - */ -ol.renderer.Layer.prototype.manageTilePyramid = function( - frameState, tileSource, tileGrid, pixelRatio, projection, extent, - currentZ, preload, opt_tileCallback, opt_this) { - var tileSourceKey = ol.getUid(tileSource).toString(); - if (!(tileSourceKey in frameState.wantedTiles)) { - frameState.wantedTiles[tileSourceKey] = {}; - } - var wantedTiles = frameState.wantedTiles[tileSourceKey]; - var tileQueue = frameState.tileQueue; - var minZoom = tileGrid.getMinZoom(); - var tile, tileRange, tileResolution, x, y, z; - for (z = minZoom; z <= currentZ; ++z) { - tileRange = tileGrid.getTileRangeForExtentAndZ(extent, z, tileRange); - tileResolution = tileGrid.getResolution(z); - for (x = tileRange.minX; x <= tileRange.maxX; ++x) { - for (y = tileRange.minY; y <= tileRange.maxY; ++y) { - if (currentZ - z <= preload) { - tile = tileSource.getTile(z, x, y, pixelRatio, projection); - if (tile.getState() == ol.TileState.IDLE) { - wantedTiles[tile.getKey()] = true; - if (!tileQueue.isKeyQueued(tile.getKey())) { - tileQueue.enqueue([tile, tileSourceKey, - tileGrid.getTileCoordCenter(tile.tileCoord), tileResolution]); - } - } - if (opt_tileCallback !== undefined) { - opt_tileCallback.call(opt_this, tile); - } - } else { - tileSource.useTile(z, x, y, projection); - } - } - } - } -}; - -goog.provide('ol.renderer.canvas.Layer'); - -goog.require('ol'); -goog.require('ol.extent'); -goog.require('ol.functions'); -goog.require('ol.render.Event'); -goog.require('ol.render.EventType'); -goog.require('ol.render.canvas'); -goog.require('ol.render.canvas.Immediate'); -goog.require('ol.renderer.Layer'); -goog.require('ol.transform'); - - -/** - * @constructor - * @abstract - * @extends {ol.renderer.Layer} - * @param {ol.layer.Layer} layer Layer. - */ -ol.renderer.canvas.Layer = function(layer) { - - ol.renderer.Layer.call(this, layer); - - /** - * @protected - * @type {number} - */ - this.renderedResolution; - - /** - * @private - * @type {ol.Transform} - */ - this.transform_ = ol.transform.create(); - -}; -ol.inherits(ol.renderer.canvas.Layer, ol.renderer.Layer); - - -/** - * @param {CanvasRenderingContext2D} context Context. - * @param {olx.FrameState} frameState Frame state. - * @param {ol.Extent} extent Clip extent. - * @protected - */ -ol.renderer.canvas.Layer.prototype.clip = function(context, frameState, extent) { - var pixelRatio = frameState.pixelRatio; - var width = frameState.size[0] * pixelRatio; - var height = frameState.size[1] * pixelRatio; - var rotation = frameState.viewState.rotation; - var topLeft = ol.extent.getTopLeft(/** @type {ol.Extent} */ (extent)); - var topRight = ol.extent.getTopRight(/** @type {ol.Extent} */ (extent)); - var bottomRight = ol.extent.getBottomRight(/** @type {ol.Extent} */ (extent)); - var bottomLeft = ol.extent.getBottomLeft(/** @type {ol.Extent} */ (extent)); - - ol.transform.apply(frameState.coordinateToPixelTransform, topLeft); - ol.transform.apply(frameState.coordinateToPixelTransform, topRight); - ol.transform.apply(frameState.coordinateToPixelTransform, bottomRight); - ol.transform.apply(frameState.coordinateToPixelTransform, bottomLeft); - - context.save(); - ol.render.canvas.rotateAtOffset(context, -rotation, width / 2, height / 2); - context.beginPath(); - context.moveTo(topLeft[0] * pixelRatio, topLeft[1] * pixelRatio); - context.lineTo(topRight[0] * pixelRatio, topRight[1] * pixelRatio); - context.lineTo(bottomRight[0] * pixelRatio, bottomRight[1] * pixelRatio); - context.lineTo(bottomLeft[0] * pixelRatio, bottomLeft[1] * pixelRatio); - context.clip(); - ol.render.canvas.rotateAtOffset(context, rotation, width / 2, height / 2); -}; - - -/** - * @param {ol.render.EventType} type Event type. - * @param {CanvasRenderingContext2D} context Context. - * @param {olx.FrameState} frameState Frame state. - * @param {ol.Transform=} opt_transform Transform. - * @private - */ -ol.renderer.canvas.Layer.prototype.dispatchComposeEvent_ = function(type, context, frameState, opt_transform) { - var layer = this.getLayer(); - if (layer.hasListener(type)) { - var width = frameState.size[0] * frameState.pixelRatio; - var height = frameState.size[1] * frameState.pixelRatio; - var rotation = frameState.viewState.rotation; - ol.render.canvas.rotateAtOffset(context, -rotation, width / 2, height / 2); - var transform = opt_transform !== undefined ? - opt_transform : this.getTransform(frameState, 0); - var render = new ol.render.canvas.Immediate( - context, frameState.pixelRatio, frameState.extent, transform, - frameState.viewState.rotation); - var composeEvent = new ol.render.Event(type, render, frameState, - context, null); - layer.dispatchEvent(composeEvent); - ol.render.canvas.rotateAtOffset(context, rotation, width / 2, height / 2); - } -}; - - -/** - * @param {ol.Coordinate} coordinate Coordinate. - * @param {olx.FrameState} frameState FrameState. - * @param {function(this: S, ol.layer.Layer, (Uint8ClampedArray|Uint8Array)): T} callback Layer - * callback. - * @param {S} thisArg Value to use as `this` when executing `callback`. - * @return {T|undefined} Callback result. - * @template S,T,U - */ -ol.renderer.canvas.Layer.prototype.forEachLayerAtCoordinate = function(coordinate, frameState, callback, thisArg) { - var hasFeature = this.forEachFeatureAtCoordinate( - coordinate, frameState, 0, ol.functions.TRUE, this); - - if (hasFeature) { - return callback.call(thisArg, this.getLayer(), null); - } else { - return undefined; - } -}; - - -/** - * @param {CanvasRenderingContext2D} context Context. - * @param {olx.FrameState} frameState Frame state. - * @param {ol.LayerState} layerState Layer state. - * @param {ol.Transform=} opt_transform Transform. - * @protected - */ -ol.renderer.canvas.Layer.prototype.postCompose = function(context, frameState, layerState, opt_transform) { - this.dispatchComposeEvent_(ol.render.EventType.POSTCOMPOSE, context, - frameState, opt_transform); -}; - - -/** - * @param {CanvasRenderingContext2D} context Context. - * @param {olx.FrameState} frameState Frame state. - * @param {ol.Transform=} opt_transform Transform. - * @protected - */ -ol.renderer.canvas.Layer.prototype.preCompose = function(context, frameState, opt_transform) { - this.dispatchComposeEvent_(ol.render.EventType.PRECOMPOSE, context, - frameState, opt_transform); -}; - - -/** - * @param {CanvasRenderingContext2D} context Context. - * @param {olx.FrameState} frameState Frame state. - * @param {ol.Transform=} opt_transform Transform. - * @protected - */ -ol.renderer.canvas.Layer.prototype.dispatchRenderEvent = function(context, frameState, opt_transform) { - this.dispatchComposeEvent_(ol.render.EventType.RENDER, context, - frameState, opt_transform); -}; - - -/** - * @param {olx.FrameState} frameState Frame state. - * @param {number} offsetX Offset on the x-axis in view coordinates. - * @protected - * @return {!ol.Transform} Transform. - */ -ol.renderer.canvas.Layer.prototype.getTransform = function(frameState, offsetX) { - var viewState = frameState.viewState; - var pixelRatio = frameState.pixelRatio; - var dx1 = pixelRatio * frameState.size[0] / 2; - var dy1 = pixelRatio * frameState.size[1] / 2; - var sx = pixelRatio / viewState.resolution; - var sy = -sx; - var angle = -viewState.rotation; - var dx2 = -viewState.center[0] + offsetX; - var dy2 = -viewState.center[1]; - return ol.transform.compose(this.transform_, dx1, dy1, sx, sy, angle, dx2, dy2); -}; - - -/** - * @abstract - * @param {olx.FrameState} frameState Frame state. - * @param {ol.LayerState} layerState Layer state. - * @param {CanvasRenderingContext2D} context Context. - */ -ol.renderer.canvas.Layer.prototype.composeFrame = function(frameState, layerState, context) {}; - -/** - * @abstract - * @param {olx.FrameState} frameState Frame state. - * @param {ol.LayerState} layerState Layer state. - * @return {boolean} whether composeFrame should be called. - */ -ol.renderer.canvas.Layer.prototype.prepareFrame = function(frameState, layerState) {}; - -goog.provide('ol.renderer.canvas.IntermediateCanvas'); - -goog.require('ol'); -goog.require('ol.coordinate'); -goog.require('ol.dom'); -goog.require('ol.extent'); -goog.require('ol.renderer.canvas.Layer'); -goog.require('ol.transform'); - - -/** - * @constructor - * @abstract - * @extends {ol.renderer.canvas.Layer} - * @param {ol.layer.Layer} layer Layer. - */ -ol.renderer.canvas.IntermediateCanvas = function(layer) { - - ol.renderer.canvas.Layer.call(this, layer); - - /** - * @protected - * @type {ol.Transform} - */ - this.coordinateToCanvasPixelTransform = ol.transform.create(); - - /** - * @private - * @type {CanvasRenderingContext2D} - */ - this.hitCanvasContext_ = null; - -}; -ol.inherits(ol.renderer.canvas.IntermediateCanvas, ol.renderer.canvas.Layer); - - -/** - * @inheritDoc - */ -ol.renderer.canvas.IntermediateCanvas.prototype.composeFrame = function(frameState, layerState, context) { - - this.preCompose(context, frameState); - - var image = this.getImage(); - if (image) { - - // clipped rendering if layer extent is set - var extent = layerState.extent; - var clipped = extent !== undefined && - !ol.extent.containsExtent(extent, frameState.extent) && - ol.extent.intersects(extent, frameState.extent); - if (clipped) { - this.clip(context, frameState, /** @type {ol.Extent} */ (extent)); - } - - var imageTransform = this.getImageTransform(); - // for performance reasons, context.save / context.restore is not used - // to save and restore the transformation matrix and the opacity. - // see http://jsperf.com/context-save-restore-versus-variable - var alpha = context.globalAlpha; - context.globalAlpha = layerState.opacity; - - // for performance reasons, context.setTransform is only used - // when the view is rotated. see http://jsperf.com/canvas-transform - var dx = imageTransform[4]; - var dy = imageTransform[5]; - var dw = image.width * imageTransform[0]; - var dh = image.height * imageTransform[3]; - context.drawImage(image, 0, 0, +image.width, +image.height, - Math.round(dx), Math.round(dy), Math.round(dw), Math.round(dh)); - context.globalAlpha = alpha; - - if (clipped) { - context.restore(); - } - } - - this.postCompose(context, frameState, layerState); -}; - - -/** - * @abstract - * @return {HTMLCanvasElement|HTMLVideoElement|Image} Canvas. - */ -ol.renderer.canvas.IntermediateCanvas.prototype.getImage = function() {}; - - -/** - * @abstract - * @return {!ol.Transform} Image transform. - */ -ol.renderer.canvas.IntermediateCanvas.prototype.getImageTransform = function() {}; - - -/** - * @inheritDoc - */ -ol.renderer.canvas.IntermediateCanvas.prototype.forEachFeatureAtCoordinate = function(coordinate, frameState, hitTolerance, callback, thisArg) { - var layer = this.getLayer(); - var source = layer.getSource(); - var resolution = frameState.viewState.resolution; - var rotation = frameState.viewState.rotation; - var skippedFeatureUids = frameState.skippedFeatureUids; - return source.forEachFeatureAtCoordinate( - coordinate, resolution, rotation, hitTolerance, skippedFeatureUids, - /** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @return {?} Callback result. - */ - function(feature) { - return callback.call(thisArg, feature, layer); - }); -}; - - -/** - * @inheritDoc - */ -ol.renderer.canvas.IntermediateCanvas.prototype.forEachLayerAtCoordinate = function(coordinate, frameState, callback, thisArg) { - if (!this.getImage()) { - return undefined; - } - - if (this.getLayer().getSource().forEachFeatureAtCoordinate !== ol.nullFunction) { - // for ImageVector sources use the original hit-detection logic, - // so that for example also transparent polygons are detected - return ol.renderer.canvas.Layer.prototype.forEachLayerAtCoordinate.apply(this, arguments); - } else { - var pixel = ol.transform.apply(this.coordinateToCanvasPixelTransform, coordinate.slice()); - ol.coordinate.scale(pixel, frameState.viewState.resolution / this.renderedResolution); - - if (!this.hitCanvasContext_) { - this.hitCanvasContext_ = ol.dom.createCanvasContext2D(1, 1); - } - - this.hitCanvasContext_.clearRect(0, 0, 1, 1); - this.hitCanvasContext_.drawImage(this.getImage(), pixel[0], pixel[1], 1, 1, 0, 0, 1, 1); - - var imageData = this.hitCanvasContext_.getImageData(0, 0, 1, 1).data; - if (imageData[3] > 0) { - return callback.call(thisArg, this.getLayer(), imageData); - } else { - return undefined; - } - } -}; - -goog.provide('ol.renderer.canvas.ImageLayer'); - -goog.require('ol'); -goog.require('ol.LayerType'); -goog.require('ol.ViewHint'); -goog.require('ol.extent'); -goog.require('ol.renderer.Type'); -goog.require('ol.renderer.canvas.IntermediateCanvas'); -goog.require('ol.transform'); - - -/** - * @constructor - * @extends {ol.renderer.canvas.IntermediateCanvas} - * @param {ol.layer.Image} imageLayer Single image layer. - * @api - */ -ol.renderer.canvas.ImageLayer = function(imageLayer) { - - ol.renderer.canvas.IntermediateCanvas.call(this, imageLayer); - - /** - * @private - * @type {?ol.ImageBase} - */ - this.image_ = null; - - /** - * @private - * @type {ol.Transform} - */ - this.imageTransform_ = ol.transform.create(); - -}; -ol.inherits(ol.renderer.canvas.ImageLayer, ol.renderer.canvas.IntermediateCanvas); - - -/** - * Determine if this renderer handles the provided layer. - * @param {ol.renderer.Type} type The renderer type. - * @param {ol.layer.Layer} layer The candidate layer. - * @return {boolean} The renderer can render the layer. - */ -ol.renderer.canvas.ImageLayer['handles'] = function(type, layer) { - return type === ol.renderer.Type.CANVAS && layer.getType() === ol.LayerType.IMAGE; -}; - - -/** - * Create a layer renderer. - * @param {ol.renderer.Map} mapRenderer The map renderer. - * @param {ol.layer.Layer} layer The layer to be rendererd. - * @return {ol.renderer.canvas.ImageLayer} The layer renderer. - */ -ol.renderer.canvas.ImageLayer['create'] = function(mapRenderer, layer) { - return new ol.renderer.canvas.ImageLayer(/** @type {ol.layer.Image} */ (layer)); -}; - - -/** - * @inheritDoc - */ -ol.renderer.canvas.ImageLayer.prototype.getImage = function() { - return !this.image_ ? null : this.image_.getImage(); -}; - - -/** - * @inheritDoc - */ -ol.renderer.canvas.ImageLayer.prototype.getImageTransform = function() { - return this.imageTransform_; -}; - - -/** - * @inheritDoc - */ -ol.renderer.canvas.ImageLayer.prototype.prepareFrame = function(frameState, layerState) { - - var pixelRatio = frameState.pixelRatio; - var size = frameState.size; - var viewState = frameState.viewState; - var viewCenter = viewState.center; - var viewResolution = viewState.resolution; - - var image; - var imageLayer = /** @type {ol.layer.Image} */ (this.getLayer()); - var imageSource = imageLayer.getSource(); - - var hints = frameState.viewHints; - - var renderedExtent = frameState.extent; - if (layerState.extent !== undefined) { - renderedExtent = ol.extent.getIntersection( - renderedExtent, layerState.extent); - } - - if (!hints[ol.ViewHint.ANIMATING] && !hints[ol.ViewHint.INTERACTING] && - !ol.extent.isEmpty(renderedExtent)) { - var projection = viewState.projection; - if (!ol.ENABLE_RASTER_REPROJECTION) { - var sourceProjection = imageSource.getProjection(); - if (sourceProjection) { - projection = sourceProjection; - } - } - image = imageSource.getImage( - renderedExtent, viewResolution, pixelRatio, projection); - if (image) { - var loaded = this.loadImage(image); - if (loaded) { - this.image_ = image; - } - } - } - - if (this.image_) { - image = this.image_; - var imageExtent = image.getExtent(); - var imageResolution = image.getResolution(); - var imagePixelRatio = image.getPixelRatio(); - var scale = pixelRatio * imageResolution / - (viewResolution * imagePixelRatio); - var transform = ol.transform.compose(this.imageTransform_, - pixelRatio * size[0] / 2, pixelRatio * size[1] / 2, - scale, scale, - 0, - imagePixelRatio * (imageExtent[0] - viewCenter[0]) / imageResolution, - imagePixelRatio * (viewCenter[1] - imageExtent[3]) / imageResolution); - ol.transform.compose(this.coordinateToCanvasPixelTransform, - pixelRatio * size[0] / 2 - transform[4], pixelRatio * size[1] / 2 - transform[5], - pixelRatio / viewResolution, -pixelRatio / viewResolution, - 0, - -viewCenter[0], -viewCenter[1]); - - this.updateAttributions(frameState.attributions, image.getAttributions()); - this.updateLogos(frameState, imageSource); - this.renderedResolution = imageResolution * pixelRatio / imagePixelRatio; - } - - return !!this.image_; -}; - -goog.provide('ol.layer.Layer'); - -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol'); -goog.require('ol.Object'); -goog.require('ol.layer.Base'); -goog.require('ol.layer.Property'); -goog.require('ol.obj'); -goog.require('ol.render.EventType'); -goog.require('ol.source.State'); - - -/** - * @classdesc - * Abstract base class; normally only used for creating subclasses and not - * instantiated in apps. - * A visual representation of raster or vector map data. - * Layers group together those properties that pertain to how the data is to be - * displayed, irrespective of the source of that data. - * - * Layers are usually added to a map with {@link ol.Map#addLayer}. Components - * like {@link ol.interaction.Select} use unmanaged layers internally. These - * unmanaged layers are associated with the map using - * {@link ol.layer.Layer#setMap} instead. - * - * A generic `change` event is fired when the state of the source changes. - * - * @constructor - * @abstract - * @extends {ol.layer.Base} - * @fires ol.render.Event - * @param {olx.layer.LayerOptions} options Layer options. - * @api - */ -ol.layer.Layer = function(options) { - - var baseOptions = ol.obj.assign({}, options); - delete baseOptions.source; - - ol.layer.Base.call(this, /** @type {olx.layer.BaseOptions} */ (baseOptions)); - - /** - * @private - * @type {?ol.EventsKey} - */ - this.mapPrecomposeKey_ = null; - - /** - * @private - * @type {?ol.EventsKey} - */ - this.mapRenderKey_ = null; - - /** - * @private - * @type {?ol.EventsKey} - */ - this.sourceChangeKey_ = null; - - if (options.map) { - this.setMap(options.map); - } - - ol.events.listen(this, - ol.Object.getChangeEventType(ol.layer.Property.SOURCE), - this.handleSourcePropertyChange_, this); - - var source = options.source ? options.source : null; - this.setSource(source); -}; -ol.inherits(ol.layer.Layer, ol.layer.Base); - - -/** - * Return `true` if the layer is visible, and if the passed resolution is - * between the layer's minResolution and maxResolution. The comparison is - * inclusive for `minResolution` and exclusive for `maxResolution`. - * @param {ol.LayerState} layerState Layer state. - * @param {number} resolution Resolution. - * @return {boolean} The layer is visible at the given resolution. - */ -ol.layer.Layer.visibleAtResolution = function(layerState, resolution) { - return layerState.visible && resolution >= layerState.minResolution && - resolution < layerState.maxResolution; -}; - - -/** - * @inheritDoc - */ -ol.layer.Layer.prototype.getLayersArray = function(opt_array) { - var array = opt_array ? opt_array : []; - array.push(this); - return array; -}; - - -/** - * @inheritDoc - */ -ol.layer.Layer.prototype.getLayerStatesArray = function(opt_states) { - var states = opt_states ? opt_states : []; - states.push(this.getLayerState()); - return states; -}; - - -/** - * Get the layer source. - * @return {ol.source.Source} The layer source (or `null` if not yet set). - * @observable - * @api - */ -ol.layer.Layer.prototype.getSource = function() { - var source = this.get(ol.layer.Property.SOURCE); - return /** @type {ol.source.Source} */ (source) || null; -}; - - -/** - * @inheritDoc - */ -ol.layer.Layer.prototype.getSourceState = function() { - var source = this.getSource(); - return !source ? ol.source.State.UNDEFINED : source.getState(); -}; - - -/** - * @private - */ -ol.layer.Layer.prototype.handleSourceChange_ = function() { - this.changed(); -}; - - -/** - * @private - */ -ol.layer.Layer.prototype.handleSourcePropertyChange_ = function() { - if (this.sourceChangeKey_) { - ol.events.unlistenByKey(this.sourceChangeKey_); - this.sourceChangeKey_ = null; - } - var source = this.getSource(); - if (source) { - this.sourceChangeKey_ = ol.events.listen(source, - ol.events.EventType.CHANGE, this.handleSourceChange_, this); - } - this.changed(); -}; - - -/** - * Sets the layer to be rendered on top of other layers on a map. The map will - * not manage this layer in its layers collection, and the callback in - * {@link ol.Map#forEachLayerAtPixel} will receive `null` as layer. This - * is useful for temporary layers. To remove an unmanaged layer from the map, - * use `#setMap(null)`. - * - * To add the layer to a map and have it managed by the map, use - * {@link ol.Map#addLayer} instead. - * @param {ol.PluggableMap} map Map. - * @api - */ -ol.layer.Layer.prototype.setMap = function(map) { - if (this.mapPrecomposeKey_) { - ol.events.unlistenByKey(this.mapPrecomposeKey_); - this.mapPrecomposeKey_ = null; - } - if (!map) { - this.changed(); - } - if (this.mapRenderKey_) { - ol.events.unlistenByKey(this.mapRenderKey_); - this.mapRenderKey_ = null; - } - if (map) { - this.mapPrecomposeKey_ = ol.events.listen( - map, ol.render.EventType.PRECOMPOSE, function(evt) { - var layerState = this.getLayerState(); - layerState.managed = false; - layerState.zIndex = Infinity; - evt.frameState.layerStatesArray.push(layerState); - evt.frameState.layerStates[ol.getUid(this)] = layerState; - }, this); - this.mapRenderKey_ = ol.events.listen( - this, ol.events.EventType.CHANGE, map.render, map); - this.changed(); - } -}; - - -/** - * Set the layer source. - * @param {ol.source.Source} source The layer source. - * @observable - * @api - */ -ol.layer.Layer.prototype.setSource = function(source) { - this.set(ol.layer.Property.SOURCE, source); -}; - -goog.provide('ol.style.IconImageCache'); - -goog.require('ol.color'); - - -/** - * @constructor - */ -ol.style.IconImageCache = function() { - - /** - * @type {Object.<string, ol.style.IconImage>} - * @private - */ - this.cache_ = {}; - - /** - * @type {number} - * @private - */ - this.cacheSize_ = 0; - - /** - * @const - * @type {number} - * @private - */ - this.maxCacheSize_ = 32; -}; - - -/** - * @param {string} src Src. - * @param {?string} crossOrigin Cross origin. - * @param {ol.Color} color Color. - * @return {string} Cache key. - */ -ol.style.IconImageCache.getKey = function(src, crossOrigin, color) { - var colorString = color ? ol.color.asString(color) : 'null'; - return crossOrigin + ':' + src + ':' + colorString; -}; - - -/** - * FIXME empty description for jsdoc - */ -ol.style.IconImageCache.prototype.clear = function() { - this.cache_ = {}; - this.cacheSize_ = 0; -}; - - -/** - * FIXME empty description for jsdoc - */ -ol.style.IconImageCache.prototype.expire = function() { - if (this.cacheSize_ > this.maxCacheSize_) { - var i = 0; - var key, iconImage; - for (key in this.cache_) { - iconImage = this.cache_[key]; - if ((i++ & 3) === 0 && !iconImage.hasListener()) { - delete this.cache_[key]; - --this.cacheSize_; - } - } - } -}; - - -/** - * @param {string} src Src. - * @param {?string} crossOrigin Cross origin. - * @param {ol.Color} color Color. - * @return {ol.style.IconImage} Icon image. - */ -ol.style.IconImageCache.prototype.get = function(src, crossOrigin, color) { - var key = ol.style.IconImageCache.getKey(src, crossOrigin, color); - return key in this.cache_ ? this.cache_[key] : null; -}; - - -/** - * @param {string} src Src. - * @param {?string} crossOrigin Cross origin. - * @param {ol.Color} color Color. - * @param {ol.style.IconImage} iconImage Icon image. - */ -ol.style.IconImageCache.prototype.set = function(src, crossOrigin, color, iconImage) { - var key = ol.style.IconImageCache.getKey(src, crossOrigin, color); - this.cache_[key] = iconImage; - ++this.cacheSize_; -}; - -goog.provide('ol.style'); - -goog.require('ol.style.IconImageCache'); - -ol.style.iconImageCache = new ol.style.IconImageCache(); - -goog.provide('ol.renderer.Map'); - -goog.require('ol'); -goog.require('ol.Disposable'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.extent'); -goog.require('ol.functions'); -goog.require('ol.layer.Layer'); -goog.require('ol.plugins'); -goog.require('ol.style'); -goog.require('ol.transform'); - - -/** - * @constructor - * @abstract - * @extends {ol.Disposable} - * @param {Element} container Container. - * @param {ol.PluggableMap} map Map. - * @struct - */ -ol.renderer.Map = function(container, map) { - - ol.Disposable.call(this); - - - /** - * @private - * @type {ol.PluggableMap} - */ - this.map_ = map; - - /** - * @private - * @type {Object.<string, ol.renderer.Layer>} - */ - this.layerRenderers_ = {}; - - /** - * @private - * @type {Object.<string, ol.EventsKey>} - */ - this.layerRendererListeners_ = {}; - -}; -ol.inherits(ol.renderer.Map, ol.Disposable); - - -/** - * @param {olx.FrameState} frameState FrameState. - * @protected - */ -ol.renderer.Map.prototype.calculateMatrices2D = function(frameState) { - var viewState = frameState.viewState; - var coordinateToPixelTransform = frameState.coordinateToPixelTransform; - var pixelToCoordinateTransform = frameState.pixelToCoordinateTransform; - - ol.transform.compose(coordinateToPixelTransform, - frameState.size[0] / 2, frameState.size[1] / 2, - 1 / viewState.resolution, -1 / viewState.resolution, - -viewState.rotation, - -viewState.center[0], -viewState.center[1]); - - ol.transform.invert( - ol.transform.setFromArray(pixelToCoordinateTransform, coordinateToPixelTransform)); -}; - - -/** - * @inheritDoc - */ -ol.renderer.Map.prototype.disposeInternal = function() { - for (var id in this.layerRenderers_) { - this.layerRenderers_[id].dispose(); - } -}; - - -/** - * @param {ol.PluggableMap} map Map. - * @param {olx.FrameState} frameState Frame state. - * @private - */ -ol.renderer.Map.expireIconCache_ = function(map, frameState) { - var cache = ol.style.iconImageCache; - cache.expire(); -}; - - -/** - * @param {ol.Coordinate} coordinate Coordinate. - * @param {olx.FrameState} frameState FrameState. - * @param {number} hitTolerance Hit tolerance in pixels. - * @param {function(this: S, (ol.Feature|ol.render.Feature), - * ol.layer.Layer): T} callback Feature callback. - * @param {S} thisArg Value to use as `this` when executing `callback`. - * @param {function(this: U, ol.layer.Layer): boolean} layerFilter Layer filter - * function, only layers which are visible and for which this function - * returns `true` will be tested for features. By default, all visible - * layers will be tested. - * @param {U} thisArg2 Value to use as `this` when executing `layerFilter`. - * @return {T|undefined} Callback result. - * @template S,T,U - */ -ol.renderer.Map.prototype.forEachFeatureAtCoordinate = function(coordinate, frameState, hitTolerance, callback, thisArg, - layerFilter, thisArg2) { - var result; - var viewState = frameState.viewState; - var viewResolution = viewState.resolution; - - /** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @param {ol.layer.Layer} layer Layer. - * @return {?} Callback result. - */ - function forEachFeatureAtCoordinate(feature, layer) { - var key = ol.getUid(feature).toString(); - var managed = frameState.layerStates[ol.getUid(layer)].managed; - if (!(key in frameState.skippedFeatureUids && !managed)) { - return callback.call(thisArg, feature, managed ? layer : null); - } - } - - var projection = viewState.projection; - - var translatedCoordinate = coordinate; - if (projection.canWrapX()) { - var projectionExtent = projection.getExtent(); - var worldWidth = ol.extent.getWidth(projectionExtent); - var x = coordinate[0]; - if (x < projectionExtent[0] || x > projectionExtent[2]) { - var worldsAway = Math.ceil((projectionExtent[0] - x) / worldWidth); - translatedCoordinate = [x + worldWidth * worldsAway, coordinate[1]]; - } - } - - var layerStates = frameState.layerStatesArray; - var numLayers = layerStates.length; - var i; - for (i = numLayers - 1; i >= 0; --i) { - var layerState = layerStates[i]; - var layer = layerState.layer; - if (ol.layer.Layer.visibleAtResolution(layerState, viewResolution) && - layerFilter.call(thisArg2, layer)) { - var layerRenderer = this.getLayerRenderer(layer); - if (layer.getSource()) { - result = layerRenderer.forEachFeatureAtCoordinate( - layer.getSource().getWrapX() ? translatedCoordinate : coordinate, - frameState, hitTolerance, forEachFeatureAtCoordinate, thisArg); - } - if (result) { - return result; - } - } - } - return undefined; -}; - - -/** - * @abstract - * @param {ol.Pixel} pixel Pixel. - * @param {olx.FrameState} frameState FrameState. - * @param {function(this: S, ol.layer.Layer, (Uint8ClampedArray|Uint8Array)): T} callback Layer - * callback. - * @param {S} thisArg Value to use as `this` when executing `callback`. - * @param {function(this: U, ol.layer.Layer): boolean} layerFilter Layer filter - * function, only layers which are visible and for which this function - * returns `true` will be tested for features. By default, all visible - * layers will be tested. - * @param {U} thisArg2 Value to use as `this` when executing `layerFilter`. - * @return {T|undefined} Callback result. - * @template S,T,U - */ -ol.renderer.Map.prototype.forEachLayerAtPixel = function(pixel, frameState, callback, thisArg, - layerFilter, thisArg2) {}; - - -/** - * @param {ol.Coordinate} coordinate Coordinate. - * @param {olx.FrameState} frameState FrameState. - * @param {number} hitTolerance Hit tolerance in pixels. - * @param {function(this: U, ol.layer.Layer): boolean} layerFilter Layer filter - * function, only layers which are visible and for which this function - * returns `true` will be tested for features. By default, all visible - * layers will be tested. - * @param {U} thisArg Value to use as `this` when executing `layerFilter`. - * @return {boolean} Is there a feature at the given coordinate? - * @template U - */ -ol.renderer.Map.prototype.hasFeatureAtCoordinate = function(coordinate, frameState, hitTolerance, layerFilter, thisArg) { - var hasFeature = this.forEachFeatureAtCoordinate( - coordinate, frameState, hitTolerance, ol.functions.TRUE, this, layerFilter, thisArg); - - return hasFeature !== undefined; -}; - - -/** - * @param {ol.layer.Layer} layer Layer. - * @protected - * @return {ol.renderer.Layer} Layer renderer. - */ -ol.renderer.Map.prototype.getLayerRenderer = function(layer) { - var layerKey = ol.getUid(layer).toString(); - if (layerKey in this.layerRenderers_) { - return this.layerRenderers_[layerKey]; - } else { - var layerRendererPlugins = ol.plugins.getLayerRendererPlugins(); - var renderer; - var type = this.getType(); - for (var i = 0, ii = layerRendererPlugins.length; i < ii; ++i) { - var plugin = layerRendererPlugins[i]; - if (plugin.handles(type, layer)) { - renderer = plugin.create(this, layer); - break; - } - } - if (renderer) { - this.layerRenderers_[layerKey] = renderer; - this.layerRendererListeners_[layerKey] = ol.events.listen(renderer, - ol.events.EventType.CHANGE, this.handleLayerRendererChange_, this); - } else { - throw new Error('Unable to create renderer for layer: ' + layer.getType()); - } - return renderer; - } -}; - - -/** - * @param {string} layerKey Layer key. - * @protected - * @return {ol.renderer.Layer} Layer renderer. - */ -ol.renderer.Map.prototype.getLayerRendererByKey = function(layerKey) { - return this.layerRenderers_[layerKey]; -}; - - -/** - * @protected - * @return {Object.<string, ol.renderer.Layer>} Layer renderers. - */ -ol.renderer.Map.prototype.getLayerRenderers = function() { - return this.layerRenderers_; -}; - - -/** - * @return {ol.PluggableMap} Map. - */ -ol.renderer.Map.prototype.getMap = function() { - return this.map_; -}; - - -/** - * @abstract - * @return {ol.renderer.Type} Type - */ -ol.renderer.Map.prototype.getType = function() {}; - - -/** - * Handle changes in a layer renderer. - * @private - */ -ol.renderer.Map.prototype.handleLayerRendererChange_ = function() { - this.map_.render(); -}; - - -/** - * @param {string} layerKey Layer key. - * @return {ol.renderer.Layer} Layer renderer. - * @private - */ -ol.renderer.Map.prototype.removeLayerRendererByKey_ = function(layerKey) { - var layerRenderer = this.layerRenderers_[layerKey]; - delete this.layerRenderers_[layerKey]; - - ol.events.unlistenByKey(this.layerRendererListeners_[layerKey]); - delete this.layerRendererListeners_[layerKey]; - - return layerRenderer; -}; - - -/** - * Render. - * @param {?olx.FrameState} frameState Frame state. - */ -ol.renderer.Map.prototype.renderFrame = ol.nullFunction; - - -/** - * @param {ol.PluggableMap} map Map. - * @param {olx.FrameState} frameState Frame state. - * @private - */ -ol.renderer.Map.prototype.removeUnusedLayerRenderers_ = function(map, frameState) { - var layerKey; - for (layerKey in this.layerRenderers_) { - if (!frameState || !(layerKey in frameState.layerStates)) { - this.removeLayerRendererByKey_(layerKey).dispose(); - } - } -}; - - -/** - * @param {olx.FrameState} frameState Frame state. - * @protected - */ -ol.renderer.Map.prototype.scheduleExpireIconCache = function(frameState) { - frameState.postRenderFunctions.push( - /** @type {ol.PostRenderFunction} */ (ol.renderer.Map.expireIconCache_) - ); -}; - - -/** - * @param {!olx.FrameState} frameState Frame state. - * @protected - */ -ol.renderer.Map.prototype.scheduleRemoveUnusedLayerRenderers = function(frameState) { - var layerKey; - for (layerKey in this.layerRenderers_) { - if (!(layerKey in frameState.layerStates)) { - frameState.postRenderFunctions.push( - /** @type {ol.PostRenderFunction} */ (this.removeUnusedLayerRenderers_.bind(this)) - ); - return; - } - } -}; - - -/** - * @param {ol.LayerState} state1 First layer state. - * @param {ol.LayerState} state2 Second layer state. - * @return {number} The zIndex difference. - */ -ol.renderer.Map.sortByZIndex = function(state1, state2) { - return state1.zIndex - state2.zIndex; -}; - -// FIXME offset panning - -goog.provide('ol.renderer.canvas.Map'); - -goog.require('ol.transform'); -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.css'); -goog.require('ol.dom'); -goog.require('ol.layer.Layer'); -goog.require('ol.render.Event'); -goog.require('ol.render.EventType'); -goog.require('ol.render.canvas'); -goog.require('ol.render.canvas.Immediate'); -goog.require('ol.renderer.Map'); -goog.require('ol.renderer.Type'); -goog.require('ol.source.State'); - - -/** - * @constructor - * @extends {ol.renderer.Map} - * @param {Element} container Container. - * @param {ol.PluggableMap} map Map. - * @api - */ -ol.renderer.canvas.Map = function(container, map) { - - ol.renderer.Map.call(this, container, map); - - /** - * @private - * @type {CanvasRenderingContext2D} - */ - this.context_ = ol.dom.createCanvasContext2D(); - - /** - * @private - * @type {HTMLCanvasElement} - */ - this.canvas_ = this.context_.canvas; - - this.canvas_.style.width = '100%'; - this.canvas_.style.height = '100%'; - this.canvas_.style.display = 'block'; - this.canvas_.className = ol.css.CLASS_UNSELECTABLE; - container.insertBefore(this.canvas_, container.childNodes[0] || null); - - /** - * @private - * @type {boolean} - */ - this.renderedVisible_ = true; - - /** - * @private - * @type {ol.Transform} - */ - this.transform_ = ol.transform.create(); - -}; -ol.inherits(ol.renderer.canvas.Map, ol.renderer.Map); - - -/** - * Determine if this renderer handles the provided layer. - * @param {ol.renderer.Type} type The renderer type. - * @return {boolean} The renderer can render the layer. - */ -ol.renderer.canvas.Map['handles'] = function(type) { - return type === ol.renderer.Type.CANVAS; -}; - - -/** - * Create the map renderer. - * @param {Element} container Container. - * @param {ol.PluggableMap} map Map. - * @return {ol.renderer.canvas.Map} The map renderer. - */ -ol.renderer.canvas.Map['create'] = function(container, map) { - return new ol.renderer.canvas.Map(container, map); -}; - - -/** - * @param {ol.render.EventType} type Event type. - * @param {olx.FrameState} frameState Frame state. - * @private - */ -ol.renderer.canvas.Map.prototype.dispatchComposeEvent_ = function(type, frameState) { - var map = this.getMap(); - var context = this.context_; - if (map.hasListener(type)) { - var extent = frameState.extent; - var pixelRatio = frameState.pixelRatio; - var viewState = frameState.viewState; - var rotation = viewState.rotation; - - var transform = this.getTransform(frameState); - - var vectorContext = new ol.render.canvas.Immediate(context, pixelRatio, - extent, transform, rotation); - var composeEvent = new ol.render.Event(type, vectorContext, - frameState, context, null); - map.dispatchEvent(composeEvent); - } -}; - - -/** - * @param {olx.FrameState} frameState Frame state. - * @protected - * @return {!ol.Transform} Transform. - */ -ol.renderer.canvas.Map.prototype.getTransform = function(frameState) { - var viewState = frameState.viewState; - var dx1 = this.canvas_.width / 2; - var dy1 = this.canvas_.height / 2; - var sx = frameState.pixelRatio / viewState.resolution; - var sy = -sx; - var angle = -viewState.rotation; - var dx2 = -viewState.center[0]; - var dy2 = -viewState.center[1]; - return ol.transform.compose(this.transform_, dx1, dy1, sx, sy, angle, dx2, dy2); -}; - - -/** - * @inheritDoc - */ -ol.renderer.canvas.Map.prototype.getType = function() { - return ol.renderer.Type.CANVAS; -}; - - -/** - * @inheritDoc - */ -ol.renderer.canvas.Map.prototype.renderFrame = function(frameState) { - - if (!frameState) { - if (this.renderedVisible_) { - this.canvas_.style.display = 'none'; - this.renderedVisible_ = false; - } - return; - } - - var context = this.context_; - var pixelRatio = frameState.pixelRatio; - var width = Math.round(frameState.size[0] * pixelRatio); - var height = Math.round(frameState.size[1] * pixelRatio); - if (this.canvas_.width != width || this.canvas_.height != height) { - this.canvas_.width = width; - this.canvas_.height = height; - } else { - context.clearRect(0, 0, width, height); - } - - var rotation = frameState.viewState.rotation; - - this.calculateMatrices2D(frameState); - - this.dispatchComposeEvent_(ol.render.EventType.PRECOMPOSE, frameState); - - var layerStatesArray = frameState.layerStatesArray; - ol.array.stableSort(layerStatesArray, ol.renderer.Map.sortByZIndex); - - if (rotation) { - context.save(); - ol.render.canvas.rotateAtOffset(context, rotation, width / 2, height / 2); - } - - var viewResolution = frameState.viewState.resolution; - var i, ii, layer, layerRenderer, layerState; - for (i = 0, ii = layerStatesArray.length; i < ii; ++i) { - layerState = layerStatesArray[i]; - layer = layerState.layer; - layerRenderer = /** @type {ol.renderer.canvas.Layer} */ (this.getLayerRenderer(layer)); - if (!ol.layer.Layer.visibleAtResolution(layerState, viewResolution) || - layerState.sourceState != ol.source.State.READY) { - continue; - } - if (layerRenderer.prepareFrame(frameState, layerState)) { - layerRenderer.composeFrame(frameState, layerState, context); - } - } - - if (rotation) { - context.restore(); - } - - this.dispatchComposeEvent_( - ol.render.EventType.POSTCOMPOSE, frameState); - - if (!this.renderedVisible_) { - this.canvas_.style.display = ''; - this.renderedVisible_ = true; - } - - this.scheduleRemoveUnusedLayerRenderers(frameState); - this.scheduleExpireIconCache(frameState); -}; - - -/** - * @inheritDoc - */ -ol.renderer.canvas.Map.prototype.forEachLayerAtPixel = function(pixel, frameState, callback, thisArg, - layerFilter, thisArg2) { - var result; - var viewState = frameState.viewState; - var viewResolution = viewState.resolution; - - var layerStates = frameState.layerStatesArray; - var numLayers = layerStates.length; - - var coordinate = ol.transform.apply( - frameState.pixelToCoordinateTransform, pixel.slice()); - - var i; - for (i = numLayers - 1; i >= 0; --i) { - var layerState = layerStates[i]; - var layer = layerState.layer; - if (ol.layer.Layer.visibleAtResolution(layerState, viewResolution) && - layerFilter.call(thisArg2, layer)) { - var layerRenderer = /** @type {ol.renderer.canvas.Layer} */ (this.getLayerRenderer(layer)); - result = layerRenderer.forEachLayerAtCoordinate( - coordinate, frameState, callback, thisArg); - if (result) { - return result; - } - } - } - return undefined; -}; - -goog.provide('ol.renderer.canvas.TileLayer'); - -goog.require('ol'); -goog.require('ol.LayerType'); -goog.require('ol.TileRange'); -goog.require('ol.TileState'); -goog.require('ol.ViewHint'); -goog.require('ol.dom'); -goog.require('ol.extent'); -goog.require('ol.renderer.Type'); -goog.require('ol.renderer.canvas.IntermediateCanvas'); -goog.require('ol.transform'); - - -/** - * @constructor - * @extends {ol.renderer.canvas.IntermediateCanvas} - * @param {ol.layer.Tile|ol.layer.VectorTile} tileLayer Tile layer. - * @api - */ -ol.renderer.canvas.TileLayer = function(tileLayer) { - - ol.renderer.canvas.IntermediateCanvas.call(this, tileLayer); - - /** - * @protected - * @type {CanvasRenderingContext2D} - */ - this.context = this.context === null ? null : ol.dom.createCanvasContext2D(); - - /** - * @private - * @type {number} - */ - this.oversampling_; - - /** - * @private - * @type {ol.Extent} - */ - this.renderedExtent_ = null; - - /** - * @protected - * @type {number} - */ - this.renderedRevision; - - /** - * @protected - * @type {!Array.<ol.Tile>} - */ - this.renderedTiles = []; - - /** - * @protected - * @type {ol.Extent} - */ - this.tmpExtent = ol.extent.createEmpty(); - - /** - * @private - * @type {ol.TileRange} - */ - this.tmpTileRange_ = new ol.TileRange(0, 0, 0, 0); - - /** - * @private - * @type {ol.Transform} - */ - this.imageTransform_ = ol.transform.create(); - - /** - * @protected - * @type {number} - */ - this.zDirection = 0; - -}; -ol.inherits(ol.renderer.canvas.TileLayer, ol.renderer.canvas.IntermediateCanvas); - - -/** - * Determine if this renderer handles the provided layer. - * @param {ol.renderer.Type} type The renderer type. - * @param {ol.layer.Layer} layer The candidate layer. - * @return {boolean} The renderer can render the layer. - */ -ol.renderer.canvas.TileLayer['handles'] = function(type, layer) { - return type === ol.renderer.Type.CANVAS && layer.getType() === ol.LayerType.TILE; -}; - - -/** - * Create a layer renderer. - * @param {ol.renderer.Map} mapRenderer The map renderer. - * @param {ol.layer.Layer} layer The layer to be rendererd. - * @return {ol.renderer.canvas.TileLayer} The layer renderer. - */ -ol.renderer.canvas.TileLayer['create'] = function(mapRenderer, layer) { - return new ol.renderer.canvas.TileLayer(/** @type {ol.layer.Tile} */ (layer)); -}; - - -/** - * @private - * @param {ol.Tile} tile Tile. - * @return {boolean} Tile is drawable. - */ -ol.renderer.canvas.TileLayer.prototype.isDrawableTile_ = function(tile) { - var tileState = tile.getState(); - var useInterimTilesOnError = this.getLayer().getUseInterimTilesOnError(); - return tileState == ol.TileState.LOADED || - tileState == ol.TileState.EMPTY || - tileState == ol.TileState.ERROR && !useInterimTilesOnError; -}; - -/** - * @inheritDoc - */ -ol.renderer.canvas.TileLayer.prototype.prepareFrame = function(frameState, layerState) { - - var pixelRatio = frameState.pixelRatio; - var size = frameState.size; - var viewState = frameState.viewState; - var projection = viewState.projection; - var viewResolution = viewState.resolution; - var viewCenter = viewState.center; - - var tileLayer = this.getLayer(); - var tileSource = /** @type {ol.source.Tile} */ (tileLayer.getSource()); - var sourceRevision = tileSource.getRevision(); - var tileGrid = tileSource.getTileGridForProjection(projection); - var z = tileGrid.getZForResolution(viewResolution, this.zDirection); - var tileResolution = tileGrid.getResolution(z); - var oversampling = Math.round(viewResolution / tileResolution) || 1; - var extent = frameState.extent; - - if (layerState.extent !== undefined) { - extent = ol.extent.getIntersection(extent, layerState.extent); - } - if (ol.extent.isEmpty(extent)) { - // Return false to prevent the rendering of the layer. - return false; - } - - var tileRange = tileGrid.getTileRangeForExtentAndZ(extent, z); - var imageExtent = tileGrid.getTileRangeExtent(z, tileRange); - - var tilePixelRatio = tileSource.getTilePixelRatio(pixelRatio); - - /** - * @type {Object.<number, Object.<string, ol.Tile>>} - */ - var tilesToDrawByZ = {}; - tilesToDrawByZ[z] = {}; - - var findLoadedTiles = this.createLoadedTileFinder( - tileSource, projection, tilesToDrawByZ); - - var tmpExtent = this.tmpExtent; - var tmpTileRange = this.tmpTileRange_; - var newTiles = false; - var tile, x, y; - for (x = tileRange.minX; x <= tileRange.maxX; ++x) { - for (y = tileRange.minY; y <= tileRange.maxY; ++y) { - tile = tileSource.getTile(z, x, y, pixelRatio, projection); - if (tile.getState() == ol.TileState.ERROR) { - if (!tileLayer.getUseInterimTilesOnError()) { - // When useInterimTilesOnError is false, we consider the error tile as loaded. - tile.setState(ol.TileState.LOADED); - } else if (tileLayer.getPreload() > 0) { - // Preloaded tiles for lower resolutions might have finished loading. - newTiles = true; - } - } - if (!this.isDrawableTile_(tile)) { - tile = tile.getInterimTile(); - } - if (this.isDrawableTile_(tile)) { - var uid = ol.getUid(this); - if (tile.getState() == ol.TileState.LOADED) { - tilesToDrawByZ[z][tile.tileCoord.toString()] = tile; - var inTransition = tile.inTransition(uid); - if (!newTiles && (inTransition || this.renderedTiles.indexOf(tile) === -1)) { - newTiles = true; - } - } - if (tile.getAlpha(uid, frameState.time) === 1) { - // don't look for alt tiles if alpha is 1 - continue; - } - } - - var childTileRange = tileGrid.getTileCoordChildTileRange( - tile.tileCoord, tmpTileRange, tmpExtent); - var covered = false; - if (childTileRange) { - covered = findLoadedTiles(z + 1, childTileRange); - } - if (!covered) { - tileGrid.forEachTileCoordParentTileRange( - tile.tileCoord, findLoadedTiles, null, tmpTileRange, tmpExtent); - } - - } - } - - var renderedResolution = tileResolution * pixelRatio / tilePixelRatio * oversampling; - var hints = frameState.viewHints; - var animatingOrInteracting = hints[ol.ViewHint.ANIMATING] || hints[ol.ViewHint.INTERACTING]; - if (!(this.renderedResolution && Date.now() - frameState.time > 16 && animatingOrInteracting) && ( - newTiles || - !(this.renderedExtent_ && ol.extent.containsExtent(this.renderedExtent_, extent)) || - this.renderedRevision != sourceRevision || - oversampling != this.oversampling_ || - !animatingOrInteracting && renderedResolution != this.renderedResolution - )) { - - var context = this.context; - if (context) { - var tilePixelSize = tileSource.getTilePixelSize(z, pixelRatio, projection); - var width = Math.round(tileRange.getWidth() * tilePixelSize[0] / oversampling); - var height = Math.round(tileRange.getHeight() * tilePixelSize[1] / oversampling); - var canvas = context.canvas; - if (canvas.width != width || canvas.height != height) { - this.oversampling_ = oversampling; - canvas.width = width; - canvas.height = height; - } else { - if (this.renderedExtent_ && !ol.extent.equals(imageExtent, this.renderedExtent_)) { - context.clearRect(0, 0, width, height); - } - oversampling = this.oversampling_; - } - } - - this.renderedTiles.length = 0; - /** @type {Array.<number>} */ - var zs = Object.keys(tilesToDrawByZ).map(Number); - zs.sort(function(a, b) { - if (a === z) { - return 1; - } else if (b === z) { - return -1; - } else { - return a > b ? 1 : a < b ? -1 : 0; - } - }); - var currentResolution, currentScale, currentTilePixelSize, currentZ, i, ii; - var tileExtent, tileGutter, tilesToDraw, w, h; - for (i = 0, ii = zs.length; i < ii; ++i) { - currentZ = zs[i]; - currentTilePixelSize = tileSource.getTilePixelSize(currentZ, pixelRatio, projection); - currentResolution = tileGrid.getResolution(currentZ); - currentScale = currentResolution / tileResolution; - tileGutter = tilePixelRatio * tileSource.getGutter(projection); - tilesToDraw = tilesToDrawByZ[currentZ]; - for (var tileCoordKey in tilesToDraw) { - tile = tilesToDraw[tileCoordKey]; - tileExtent = tileGrid.getTileCoordExtent(tile.getTileCoord(), tmpExtent); - x = (tileExtent[0] - imageExtent[0]) / tileResolution * tilePixelRatio / oversampling; - y = (imageExtent[3] - tileExtent[3]) / tileResolution * tilePixelRatio / oversampling; - w = currentTilePixelSize[0] * currentScale / oversampling; - h = currentTilePixelSize[1] * currentScale / oversampling; - this.drawTileImage(tile, frameState, layerState, x, y, w, h, tileGutter, z === currentZ); - this.renderedTiles.push(tile); - } - } - - this.renderedRevision = sourceRevision; - this.renderedResolution = tileResolution * pixelRatio / tilePixelRatio * oversampling; - this.renderedExtent_ = imageExtent; - } - - var scale = this.renderedResolution / viewResolution; - var transform = ol.transform.compose(this.imageTransform_, - pixelRatio * size[0] / 2, pixelRatio * size[1] / 2, - scale, scale, - 0, - (this.renderedExtent_[0] - viewCenter[0]) / this.renderedResolution * pixelRatio, - (viewCenter[1] - this.renderedExtent_[3]) / this.renderedResolution * pixelRatio); - ol.transform.compose(this.coordinateToCanvasPixelTransform, - pixelRatio * size[0] / 2 - transform[4], pixelRatio * size[1] / 2 - transform[5], - pixelRatio / viewResolution, -pixelRatio / viewResolution, - 0, - -viewCenter[0], -viewCenter[1]); - - - this.updateUsedTiles(frameState.usedTiles, tileSource, z, tileRange); - this.manageTilePyramid(frameState, tileSource, tileGrid, pixelRatio, - projection, extent, z, tileLayer.getPreload()); - this.scheduleExpireCache(frameState, tileSource); - this.updateLogos(frameState, tileSource); - - return this.renderedTiles.length > 0; -}; - - -/** - * @param {ol.Tile} tile Tile. - * @param {olx.FrameState} frameState Frame state. - * @param {ol.LayerState} layerState Layer state. - * @param {number} x Left of the tile. - * @param {number} y Top of the tile. - * @param {number} w Width of the tile. - * @param {number} h Height of the tile. - * @param {number} gutter Tile gutter. - * @param {boolean} transition Apply an alpha transition. - */ -ol.renderer.canvas.TileLayer.prototype.drawTileImage = function(tile, frameState, layerState, x, y, w, h, gutter, transition) { - var image = tile.getImage(this.getLayer()); - if (!image) { - return; - } - var uid = ol.getUid(this); - var alpha = transition ? tile.getAlpha(uid, frameState.time) : 1; - if (alpha === 1 && !this.getLayer().getSource().getOpaque(frameState.viewState.projection)) { - this.context.clearRect(x, y, w, h); - } - var alphaChanged = alpha !== this.context.globalAlpha; - if (alphaChanged) { - this.context.save(); - this.context.globalAlpha = alpha; - } - this.context.drawImage(image, gutter, gutter, - image.width - 2 * gutter, image.height - 2 * gutter, x, y, w, h); - - if (alphaChanged) { - this.context.restore(); - } - if (alpha !== 1) { - frameState.animate = true; - } else if (transition) { - tile.endTransition(uid); - } -}; - - -/** - * @inheritDoc - */ -ol.renderer.canvas.TileLayer.prototype.getImage = function() { - var context = this.context; - return context ? context.canvas : null; -}; - - -/** - * @function - * @return {ol.layer.Tile|ol.layer.VectorTile} - */ -ol.renderer.canvas.TileLayer.prototype.getLayer; - - -/** - * @inheritDoc - */ -ol.renderer.canvas.TileLayer.prototype.getImageTransform = function() { - return this.imageTransform_; -}; - -goog.provide('ol.render.ReplayGroup'); - - -/** - * Base class for replay groups. - * @constructor - * @abstract - */ -ol.render.ReplayGroup = function() {}; - - -/** - * @abstract - * @param {number|undefined} zIndex Z index. - * @param {ol.render.ReplayType} replayType Replay type. - * @return {ol.render.VectorContext} Replay. - */ -ol.render.ReplayGroup.prototype.getReplay = function(zIndex, replayType) {}; - - -/** - * @abstract - * @return {boolean} Is empty. - */ -ol.render.ReplayGroup.prototype.isEmpty = function() {}; - -goog.provide('ol.geom.flat.length'); - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @return {number} Length. - */ -ol.geom.flat.length.lineString = function(flatCoordinates, offset, end, stride) { - var x1 = flatCoordinates[offset]; - var y1 = flatCoordinates[offset + 1]; - var length = 0; - var i; - for (i = offset + stride; i < end; i += stride) { - var x2 = flatCoordinates[i]; - var y2 = flatCoordinates[i + 1]; - length += Math.sqrt((x2 - x1) * (x2 - x1) + (y2 - y1) * (y2 - y1)); - x1 = x2; - y1 = y2; - } - return length; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @return {number} Perimeter. - */ -ol.geom.flat.length.linearRing = function(flatCoordinates, offset, end, stride) { - var perimeter = - ol.geom.flat.length.lineString(flatCoordinates, offset, end, stride); - var dx = flatCoordinates[end - stride] - flatCoordinates[offset]; - var dy = flatCoordinates[end - stride + 1] - flatCoordinates[offset + 1]; - perimeter += Math.sqrt(dx * dx + dy * dy); - return perimeter; -}; - -goog.provide('ol.geom.flat.textpath'); - -goog.require('ol.math'); - - -/** - * @param {Array.<number>} flatCoordinates Path to put text on. - * @param {number} offset Start offset of the `flatCoordinates`. - * @param {number} end End offset of the `flatCoordinates`. - * @param {number} stride Stride. - * @param {string} text Text to place on the path. - * @param {function(string):number} measure Measure function returning the - * width of the character passed as 1st argument. - * @param {number} startM m along the path where the text starts. - * @param {number} maxAngle Max angle between adjacent chars in radians. - * @param {Array.<Array.<number>>=} opt_result Array that will be populated with the - * result. Each entry consists of an array of x, y and z of the char to draw. - * If provided, this array will not be truncated to the number of characters of - * the `text`. - * @return {Array.<Array.<number>>} The result array of null if `maxAngle` was - * exceeded. - */ -ol.geom.flat.textpath.lineString = function( - flatCoordinates, offset, end, stride, text, measure, startM, maxAngle, opt_result) { - var result = opt_result ? opt_result : []; - - // Keep text upright - var reverse = flatCoordinates[offset] > flatCoordinates[end - stride]; - - var numChars = text.length; - - var x1 = flatCoordinates[offset]; - var y1 = flatCoordinates[offset + 1]; - offset += stride; - var x2 = flatCoordinates[offset]; - var y2 = flatCoordinates[offset + 1]; - var segmentM = 0; - var segmentLength = Math.sqrt(Math.pow(x2 - x1, 2) + Math.pow(y2 - y1, 2)); - - var index, previousAngle; - for (var i = 0; i < numChars; ++i) { - index = reverse ? numChars - i - 1 : i; - var char = text[index]; - var charLength = measure(char); - var charM = startM + charLength / 2; - while (offset < end - stride && segmentM + segmentLength < charM) { - x1 = x2; - y1 = y2; - offset += stride; - x2 = flatCoordinates[offset]; - y2 = flatCoordinates[offset + 1]; - segmentM += segmentLength; - segmentLength = Math.sqrt(Math.pow(x2 - x1, 2) + Math.pow(y2 - y1, 2)); - } - var segmentPos = charM - segmentM; - var angle = Math.atan2(y2 - y1, x2 - x1); - if (reverse) { - angle += angle > 0 ? -Math.PI : Math.PI; - } - if (previousAngle !== undefined) { - var delta = angle - previousAngle; - delta += (delta > Math.PI) ? -2 * Math.PI : (delta < -Math.PI) ? 2 * Math.PI : 0; - if (Math.abs(delta) > maxAngle) { - return null; - } - } - previousAngle = angle; - var interpolate = segmentPos / segmentLength; - var x = ol.math.lerp(x1, x2, interpolate); - var y = ol.math.lerp(y1, y2, interpolate); - result[index] = [x, y, angle]; - startM += charLength; - } - return result; -}; - -goog.provide('ol.render.canvas.Instruction'); - -/** - * @enum {number} - */ -ol.render.canvas.Instruction = { - BEGIN_GEOMETRY: 0, - BEGIN_PATH: 1, - CIRCLE: 2, - CLOSE_PATH: 3, - CUSTOM: 4, - DRAW_CHARS: 5, - DRAW_IMAGE: 6, - END_GEOMETRY: 7, - FILL: 8, - MOVE_TO_LINE_TO: 9, - SET_FILL_STYLE: 10, - SET_STROKE_STYLE: 11, - STROKE: 12 -}; - -goog.provide('ol.render.canvas.Replay'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.extent'); -goog.require('ol.extent.Relationship'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.flat.inflate'); -goog.require('ol.geom.flat.length'); -goog.require('ol.geom.flat.textpath'); -goog.require('ol.geom.flat.transform'); -goog.require('ol.has'); -goog.require('ol.obj'); -goog.require('ol.render.VectorContext'); -goog.require('ol.render.canvas.Instruction'); -goog.require('ol.transform'); - - -/** - * @constructor - * @extends {ol.render.VectorContext} - * @param {number} tolerance Tolerance. - * @param {ol.Extent} maxExtent Maximum extent. - * @param {number} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @param {boolean} overlaps The replay can have overlapping geometries. - * @struct - */ -ol.render.canvas.Replay = function(tolerance, maxExtent, resolution, pixelRatio, overlaps) { - ol.render.VectorContext.call(this); - - /** - * @protected - * @type {number} - */ - this.tolerance = tolerance; - - /** - * @protected - * @const - * @type {ol.Extent} - */ - this.maxExtent = maxExtent; - - /** - * @protected - * @type {boolean} - */ - this.overlaps = overlaps; - - /** - * @protected - * @type {number} - */ - this.pixelRatio = pixelRatio; - - /** - * @protected - * @type {number} - */ - this.maxLineWidth = 0; - - /** - * @protected - * @const - * @type {number} - */ - this.resolution = resolution; - - /** - * @private - * @type {ol.Coordinate} - */ - this.fillOrigin_; - - /** - * @private - * @type {Array.<*>} - */ - this.beginGeometryInstruction1_ = null; - - /** - * @private - * @type {Array.<*>} - */ - this.beginGeometryInstruction2_ = null; - - /** - * @protected - * @type {Array.<*>} - */ - this.instructions = []; - - /** - * @protected - * @type {Array.<number>} - */ - this.coordinates = []; - - /** - * @private - * @type {Object.<number,ol.Coordinate|Array.<ol.Coordinate>|Array.<Array.<ol.Coordinate>>>} - */ - this.coordinateCache_ = {}; - - /** - * @private - * @type {!ol.Transform} - */ - this.renderedTransform_ = ol.transform.create(); - - /** - * @protected - * @type {Array.<*>} - */ - this.hitDetectionInstructions = []; - - /** - * @private - * @type {Array.<number>} - */ - this.pixelCoordinates_ = null; - - /** - * @private - * @type {!ol.Transform} - */ - this.tmpLocalTransform_ = ol.transform.create(); - - /** - * @private - * @type {!ol.Transform} - */ - this.resetTransform_ = ol.transform.create(); - - /** - * @private - * @type {Array.<Array.<number>>} - */ - this.chars_ = []; -}; -ol.inherits(ol.render.canvas.Replay, ol.render.VectorContext); - - -/** - * @param {CanvasRenderingContext2D} context Context. - * @param {number} x X. - * @param {number} y Y. - * @param {HTMLImageElement|HTMLCanvasElement|HTMLVideoElement} image Image. - * @param {number} anchorX Anchor X. - * @param {number} anchorY Anchor Y. - * @param {number} height Height. - * @param {number} opacity Opacity. - * @param {number} originX Origin X. - * @param {number} originY Origin Y. - * @param {number} rotation Rotation. - * @param {number} scale Scale. - * @param {boolean} snapToPixel Snap to pixel. - * @param {number} width Width. - */ -ol.render.canvas.Replay.prototype.replayImage_ = function(context, x, y, image, anchorX, anchorY, - height, opacity, originX, originY, rotation, scale, snapToPixel, width) { - var localTransform = this.tmpLocalTransform_; - anchorX *= scale; - anchorY *= scale; - x -= anchorX; - y -= anchorY; - if (snapToPixel) { - x = Math.round(x); - y = Math.round(y); - } - if (rotation !== 0) { - var centerX = x + anchorX; - var centerY = y + anchorY; - ol.transform.compose(localTransform, - centerX, centerY, 1, 1, rotation, -centerX, -centerY); - context.setTransform.apply(context, localTransform); - } - var alpha = context.globalAlpha; - if (opacity != 1) { - context.globalAlpha = alpha * opacity; - } - - var w = (width + originX > image.width) ? image.width - originX : width; - var h = (height + originY > image.height) ? image.height - originY : height; - - context.drawImage(image, originX, originY, w, h, x, y, w * scale, h * scale); - - if (opacity != 1) { - context.globalAlpha = alpha; - } - if (rotation !== 0) { - context.setTransform.apply(context, this.resetTransform_); - } -}; - - -/** - * @protected - * @param {Array.<number>} dashArray Dash array. - * @return {Array.<number>} Dash array with pixel ratio applied - */ -ol.render.canvas.Replay.prototype.applyPixelRatio = function(dashArray) { - var pixelRatio = this.pixelRatio; - return pixelRatio == 1 ? dashArray : dashArray.map(function(dash) { - return dash * pixelRatio; - }); -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {boolean} closed Last input coordinate equals first. - * @param {boolean} skipFirst Skip first coordinate. - * @protected - * @return {number} My end. - */ -ol.render.canvas.Replay.prototype.appendFlatCoordinates = function(flatCoordinates, offset, end, stride, closed, skipFirst) { - - var myEnd = this.coordinates.length; - var extent = this.getBufferedMaxExtent(); - if (skipFirst) { - offset += stride; - } - var lastCoord = [flatCoordinates[offset], flatCoordinates[offset + 1]]; - var nextCoord = [NaN, NaN]; - var skipped = true; - - var i, lastRel, nextRel; - for (i = offset + stride; i < end; i += stride) { - nextCoord[0] = flatCoordinates[i]; - nextCoord[1] = flatCoordinates[i + 1]; - nextRel = ol.extent.coordinateRelationship(extent, nextCoord); - if (nextRel !== lastRel) { - if (skipped) { - this.coordinates[myEnd++] = lastCoord[0]; - this.coordinates[myEnd++] = lastCoord[1]; - } - this.coordinates[myEnd++] = nextCoord[0]; - this.coordinates[myEnd++] = nextCoord[1]; - skipped = false; - } else if (nextRel === ol.extent.Relationship.INTERSECTING) { - this.coordinates[myEnd++] = nextCoord[0]; - this.coordinates[myEnd++] = nextCoord[1]; - skipped = false; - } else { - skipped = true; - } - lastCoord[0] = nextCoord[0]; - lastCoord[1] = nextCoord[1]; - lastRel = nextRel; - } - - // Last coordinate equals first or only one point to append: - if ((closed && skipped) || i === offset + stride) { - this.coordinates[myEnd++] = lastCoord[0]; - this.coordinates[myEnd++] = lastCoord[1]; - } - return myEnd; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<number>} ends Ends. - * @param {number} stride Stride. - * @param {Array.<number>} replayEnds Replay ends. - * @return {number} Offset. - */ -ol.render.canvas.Replay.prototype.drawCustomCoordinates_ = function(flatCoordinates, offset, ends, stride, replayEnds) { - for (var i = 0, ii = ends.length; i < ii; ++i) { - var end = ends[i]; - var replayEnd = this.appendFlatCoordinates(flatCoordinates, offset, end, stride, false, false); - replayEnds.push(replayEnd); - offset = end; - } - return offset; -}; - - -/** - * @inheritDoc. - */ -ol.render.canvas.Replay.prototype.drawCustom = function(geometry, feature, renderer) { - this.beginGeometry(geometry, feature); - var type = geometry.getType(); - var stride = geometry.getStride(); - var replayBegin = this.coordinates.length; - var flatCoordinates, replayEnd, replayEnds, replayEndss; - var offset; - if (type == ol.geom.GeometryType.MULTI_POLYGON) { - geometry = /** @type {ol.geom.MultiPolygon} */ (geometry); - flatCoordinates = geometry.getOrientedFlatCoordinates(); - replayEndss = []; - var endss = geometry.getEndss(); - offset = 0; - for (var i = 0, ii = endss.length; i < ii; ++i) { - var myEnds = []; - offset = this.drawCustomCoordinates_(flatCoordinates, offset, endss[i], stride, myEnds); - replayEndss.push(myEnds); - } - this.instructions.push([ol.render.canvas.Instruction.CUSTOM, - replayBegin, replayEndss, geometry, renderer, ol.geom.flat.inflate.coordinatesss]); - } else if (type == ol.geom.GeometryType.POLYGON || type == ol.geom.GeometryType.MULTI_LINE_STRING) { - replayEnds = []; - flatCoordinates = (type == ol.geom.GeometryType.POLYGON) ? - /** @type {ol.geom.Polygon} */ (geometry).getOrientedFlatCoordinates() : - geometry.getFlatCoordinates(); - offset = this.drawCustomCoordinates_(flatCoordinates, 0, - /** @type {ol.geom.Polygon|ol.geom.MultiLineString} */ (geometry).getEnds(), - stride, replayEnds); - this.instructions.push([ol.render.canvas.Instruction.CUSTOM, - replayBegin, replayEnds, geometry, renderer, ol.geom.flat.inflate.coordinatess]); - } else if (type == ol.geom.GeometryType.LINE_STRING || type == ol.geom.GeometryType.MULTI_POINT) { - flatCoordinates = geometry.getFlatCoordinates(); - replayEnd = this.appendFlatCoordinates( - flatCoordinates, 0, flatCoordinates.length, stride, false, false); - this.instructions.push([ol.render.canvas.Instruction.CUSTOM, - replayBegin, replayEnd, geometry, renderer, ol.geom.flat.inflate.coordinates]); - } else if (type == ol.geom.GeometryType.POINT) { - flatCoordinates = geometry.getFlatCoordinates(); - this.coordinates.push(flatCoordinates[0], flatCoordinates[1]); - replayEnd = this.coordinates.length; - this.instructions.push([ol.render.canvas.Instruction.CUSTOM, - replayBegin, replayEnd, geometry, renderer]); - } - this.endGeometry(geometry, feature); -}; - - -/** - * @protected - * @param {ol.geom.Geometry|ol.render.Feature} geometry Geometry. - * @param {ol.Feature|ol.render.Feature} feature Feature. - */ -ol.render.canvas.Replay.prototype.beginGeometry = function(geometry, feature) { - this.beginGeometryInstruction1_ = - [ol.render.canvas.Instruction.BEGIN_GEOMETRY, feature, 0]; - this.instructions.push(this.beginGeometryInstruction1_); - this.beginGeometryInstruction2_ = - [ol.render.canvas.Instruction.BEGIN_GEOMETRY, feature, 0]; - this.hitDetectionInstructions.push(this.beginGeometryInstruction2_); -}; - - -/** - * @private - * @param {CanvasRenderingContext2D} context Context. - * @param {number} rotation Rotation. - */ -ol.render.canvas.Replay.prototype.fill_ = function(context, rotation) { - if (this.fillOrigin_) { - var origin = ol.transform.apply(this.renderedTransform_, this.fillOrigin_.slice()); - context.translate(origin[0], origin[1]); - context.rotate(rotation); - } - context.fill(); - if (this.fillOrigin_) { - context.setTransform.apply(context, this.resetTransform_); - } -}; - - -/** - * @private - * @param {CanvasRenderingContext2D} context Context. - * @param {ol.Transform} transform Transform. - * @param {number} viewRotation View rotation. - * @param {Object.<string, boolean>} skippedFeaturesHash Ids of features - * to skip. - * @param {Array.<*>} instructions Instructions array. - * @param {function((ol.Feature|ol.render.Feature)): T|undefined} - * featureCallback Feature callback. - * @param {ol.Extent=} opt_hitExtent Only check features that intersect this - * extent. - * @return {T|undefined} Callback result. - * @template T - */ -ol.render.canvas.Replay.prototype.replay_ = function( - context, transform, viewRotation, skippedFeaturesHash, - instructions, featureCallback, opt_hitExtent) { - /** @type {Array.<number>} */ - var pixelCoordinates; - if (this.pixelCoordinates_ && ol.array.equals(transform, this.renderedTransform_)) { - pixelCoordinates = this.pixelCoordinates_; - } else { - if (!this.pixelCoordinates_) { - this.pixelCoordinates_ = []; - } - pixelCoordinates = ol.geom.flat.transform.transform2D( - this.coordinates, 0, this.coordinates.length, 2, - transform, this.pixelCoordinates_); - ol.transform.setFromArray(this.renderedTransform_, transform); - } - var skipFeatures = !ol.obj.isEmpty(skippedFeaturesHash); - var i = 0; // instruction index - var ii = instructions.length; // end of instructions - var d = 0; // data index - var dd; // end of per-instruction data - var anchorX, anchorY, prevX, prevY, roundX, roundY; - var pendingFill = 0; - var pendingStroke = 0; - var coordinateCache = this.coordinateCache_; - - var state = /** @type {olx.render.State} */ ({ - context: context, - pixelRatio: this.pixelRatio, - resolution: this.resolution, - rotation: viewRotation - }); - - // When the batch size gets too big, performance decreases. 200 is a good - // balance between batch size and number of fill/stroke instructions. - var batchSize = - this.instructions != instructions || this.overlaps ? 0 : 200; - while (i < ii) { - var instruction = instructions[i]; - var type = /** @type {ol.render.canvas.Instruction} */ (instruction[0]); - var /** @type {ol.Feature|ol.render.Feature} */ feature, x, y; - switch (type) { - case ol.render.canvas.Instruction.BEGIN_GEOMETRY: - feature = /** @type {ol.Feature|ol.render.Feature} */ (instruction[1]); - if ((skipFeatures && - skippedFeaturesHash[ol.getUid(feature).toString()]) || - !feature.getGeometry()) { - i = /** @type {number} */ (instruction[2]); - } else if (opt_hitExtent !== undefined && !ol.extent.intersects( - opt_hitExtent, feature.getGeometry().getExtent())) { - i = /** @type {number} */ (instruction[2]) + 1; - } else { - ++i; - } - break; - case ol.render.canvas.Instruction.BEGIN_PATH: - if (pendingFill > batchSize) { - this.fill_(context, viewRotation); - pendingFill = 0; - } - if (pendingStroke > batchSize) { - context.stroke(); - pendingStroke = 0; - } - if (!pendingFill && !pendingStroke) { - context.beginPath(); - prevX = prevY = NaN; - } - ++i; - break; - case ol.render.canvas.Instruction.CIRCLE: - d = /** @type {number} */ (instruction[1]); - var x1 = pixelCoordinates[d]; - var y1 = pixelCoordinates[d + 1]; - var x2 = pixelCoordinates[d + 2]; - var y2 = pixelCoordinates[d + 3]; - var dx = x2 - x1; - var dy = y2 - y1; - var r = Math.sqrt(dx * dx + dy * dy); - context.moveTo(x1 + r, y1); - context.arc(x1, y1, r, 0, 2 * Math.PI, true); - ++i; - break; - case ol.render.canvas.Instruction.CLOSE_PATH: - context.closePath(); - ++i; - break; - case ol.render.canvas.Instruction.CUSTOM: - d = /** @type {number} */ (instruction[1]); - dd = instruction[2]; - var geometry = /** @type {ol.geom.SimpleGeometry} */ (instruction[3]); - var renderer = instruction[4]; - var fn = instruction.length == 6 ? instruction[5] : undefined; - state.geometry = geometry; - state.feature = feature; - if (!(i in coordinateCache)) { - coordinateCache[i] = []; - } - var coords = coordinateCache[i]; - if (fn) { - fn(pixelCoordinates, d, dd, 2, coords); - } else { - coords[0] = pixelCoordinates[d]; - coords[1] = pixelCoordinates[d + 1]; - coords.length = 2; - } - renderer(coords, state); - ++i; - break; - case ol.render.canvas.Instruction.DRAW_IMAGE: - d = /** @type {number} */ (instruction[1]); - dd = /** @type {number} */ (instruction[2]); - var image = /** @type {HTMLCanvasElement|HTMLVideoElement|Image} */ - (instruction[3]); - // Remaining arguments in DRAW_IMAGE are in alphabetical order - anchorX = /** @type {number} */ (instruction[4]); - anchorY = /** @type {number} */ (instruction[5]); - var height = /** @type {number} */ (instruction[6]); - var opacity = /** @type {number} */ (instruction[7]); - var originX = /** @type {number} */ (instruction[8]); - var originY = /** @type {number} */ (instruction[9]); - var rotateWithView = /** @type {boolean} */ (instruction[10]); - var rotation = /** @type {number} */ (instruction[11]); - var scale = /** @type {number} */ (instruction[12]); - var snapToPixel = /** @type {boolean} */ (instruction[13]); - var width = /** @type {number} */ (instruction[14]); - - if (rotateWithView) { - rotation += viewRotation; - } - for (; d < dd; d += 2) { - this.replayImage_(context, pixelCoordinates[d], pixelCoordinates[d + 1], - image, anchorX, anchorY, height, opacity, originX, originY, - rotation, scale, snapToPixel, width); - } - ++i; - break; - case ol.render.canvas.Instruction.DRAW_CHARS: - var begin = /** @type {number} */ (instruction[1]); - var end = /** @type {number} */ (instruction[2]); - var images = /** @type {Array.<HTMLCanvasElement>} */ (instruction[3]); - // Remaining arguments in DRAW_CHARS are in alphabetical order - var baseline = /** @type {number} */ (instruction[4]); - var exceedLength = /** @type {number} */ (instruction[5]); - var maxAngle = /** @type {number} */ (instruction[6]); - var measure = /** @type {function(string):number} */ (instruction[7]); - var offsetY = /** @type {number} */ (instruction[8]); - var text = /** @type {string} */ (instruction[9]); - var align = /** @type {number} */ (instruction[10]); - var textScale = /** @type {number} */ (instruction[11]); - - var pathLength = ol.geom.flat.length.lineString(pixelCoordinates, begin, end, 2); - var textLength = measure(text); - if (exceedLength || textLength <= pathLength) { - var startM = (pathLength - textLength) * align; - var chars = ol.geom.flat.textpath.lineString( - pixelCoordinates, begin, end, 2, text, measure, startM, maxAngle, this.chars_); - var numChars = text.length; - if (chars) { - var fillHeight = images[images.length - 1].height; - for (var c = 0, cc = images.length; c < cc; ++c) { - var char = chars[c % numChars]; // x, y, rotation - var label = images[c]; - anchorX = label.width / 2; - anchorY = baseline * label.height + (0.5 - baseline) * (label.height - fillHeight) - offsetY; - this.replayImage_(context, char[0], char[1], label, anchorX, anchorY, - label.height, 1, 0, 0, char[2], textScale, false, label.width); - } - } - } - - ++i; - break; - case ol.render.canvas.Instruction.END_GEOMETRY: - if (featureCallback !== undefined) { - feature = /** @type {ol.Feature|ol.render.Feature} */ (instruction[1]); - var result = featureCallback(feature); - if (result) { - return result; - } - } - ++i; - break; - case ol.render.canvas.Instruction.FILL: - if (batchSize) { - pendingFill++; - } else { - this.fill_(context, viewRotation); - } - ++i; - break; - case ol.render.canvas.Instruction.MOVE_TO_LINE_TO: - d = /** @type {number} */ (instruction[1]); - dd = /** @type {number} */ (instruction[2]); - x = pixelCoordinates[d]; - y = pixelCoordinates[d + 1]; - roundX = (x + 0.5) | 0; - roundY = (y + 0.5) | 0; - if (roundX !== prevX || roundY !== prevY) { - context.moveTo(x, y); - prevX = roundX; - prevY = roundY; - } - for (d += 2; d < dd; d += 2) { - x = pixelCoordinates[d]; - y = pixelCoordinates[d + 1]; - roundX = (x + 0.5) | 0; - roundY = (y + 0.5) | 0; - if (d == dd - 2 || roundX !== prevX || roundY !== prevY) { - context.lineTo(x, y); - prevX = roundX; - prevY = roundY; - } - } - ++i; - break; - case ol.render.canvas.Instruction.SET_FILL_STYLE: - this.fillOrigin_ = instruction[2]; - - if (pendingFill) { - this.fill_(context, viewRotation); - pendingFill = 0; - if (pendingStroke) { - context.stroke(); - pendingStroke = 0; - } - } - - context.fillStyle = /** @type {ol.ColorLike} */ (instruction[1]); - ++i; - break; - case ol.render.canvas.Instruction.SET_STROKE_STYLE: - if (pendingStroke) { - context.stroke(); - pendingStroke = 0; - } - context.strokeStyle = /** @type {ol.ColorLike} */ (instruction[1]); - context.lineWidth = /** @type {number} */ (instruction[2]); - context.lineCap = /** @type {string} */ (instruction[3]); - context.lineJoin = /** @type {string} */ (instruction[4]); - context.miterLimit = /** @type {number} */ (instruction[5]); - if (ol.has.CANVAS_LINE_DASH) { - context.lineDashOffset = /** @type {number} */ (instruction[7]); - context.setLineDash(/** @type {Array.<number>} */ (instruction[6])); - } - ++i; - break; - case ol.render.canvas.Instruction.STROKE: - if (batchSize) { - pendingStroke++; - } else { - context.stroke(); - } - ++i; - break; - default: - ++i; // consume the instruction anyway, to avoid an infinite loop - break; - } - } - if (pendingFill) { - this.fill_(context, viewRotation); - } - if (pendingStroke) { - context.stroke(); - } - return undefined; -}; - - -/** - * @param {CanvasRenderingContext2D} context Context. - * @param {ol.Transform} transform Transform. - * @param {number} viewRotation View rotation. - * @param {Object.<string, boolean>} skippedFeaturesHash Ids of features - * to skip. - */ -ol.render.canvas.Replay.prototype.replay = function( - context, transform, viewRotation, skippedFeaturesHash) { - var instructions = this.instructions; - this.replay_(context, transform, viewRotation, - skippedFeaturesHash, instructions, undefined, undefined); -}; - - -/** - * @param {CanvasRenderingContext2D} context Context. - * @param {ol.Transform} transform Transform. - * @param {number} viewRotation View rotation. - * @param {Object.<string, boolean>} skippedFeaturesHash Ids of features - * to skip. - * @param {function((ol.Feature|ol.render.Feature)): T=} opt_featureCallback - * Feature callback. - * @param {ol.Extent=} opt_hitExtent Only check features that intersect this - * extent. - * @return {T|undefined} Callback result. - * @template T - */ -ol.render.canvas.Replay.prototype.replayHitDetection = function( - context, transform, viewRotation, skippedFeaturesHash, - opt_featureCallback, opt_hitExtent) { - var instructions = this.hitDetectionInstructions; - return this.replay_(context, transform, viewRotation, - skippedFeaturesHash, instructions, opt_featureCallback, opt_hitExtent); -}; - - -/** - * Reverse the hit detection instructions. - */ -ol.render.canvas.Replay.prototype.reverseHitDetectionInstructions = function() { - var hitDetectionInstructions = this.hitDetectionInstructions; - // step 1 - reverse array - hitDetectionInstructions.reverse(); - // step 2 - reverse instructions within geometry blocks - var i; - var n = hitDetectionInstructions.length; - var instruction; - var type; - var begin = -1; - for (i = 0; i < n; ++i) { - instruction = hitDetectionInstructions[i]; - type = /** @type {ol.render.canvas.Instruction} */ (instruction[0]); - if (type == ol.render.canvas.Instruction.END_GEOMETRY) { - begin = i; - } else if (type == ol.render.canvas.Instruction.BEGIN_GEOMETRY) { - instruction[2] = i; - ol.array.reverseSubArray(this.hitDetectionInstructions, begin, i); - begin = -1; - } - } -}; - - -/** - * @param {ol.geom.Geometry|ol.render.Feature} geometry Geometry. - * @param {ol.Feature|ol.render.Feature} feature Feature. - */ -ol.render.canvas.Replay.prototype.endGeometry = function(geometry, feature) { - this.beginGeometryInstruction1_[2] = this.instructions.length; - this.beginGeometryInstruction1_ = null; - this.beginGeometryInstruction2_[2] = this.hitDetectionInstructions.length; - this.beginGeometryInstruction2_ = null; - var endGeometryInstruction = - [ol.render.canvas.Instruction.END_GEOMETRY, feature]; - this.instructions.push(endGeometryInstruction); - this.hitDetectionInstructions.push(endGeometryInstruction); -}; - - -/** - * FIXME empty description for jsdoc - */ -ol.render.canvas.Replay.prototype.finish = ol.nullFunction; - - -/** - * Get the buffered rendering extent. Rendering will be clipped to the extent - * provided to the constructor. To account for symbolizers that may intersect - * this extent, we calculate a buffered extent (e.g. based on stroke width). - * @return {ol.Extent} The buffered rendering extent. - * @protected - */ -ol.render.canvas.Replay.prototype.getBufferedMaxExtent = function() { - return this.maxExtent; -}; - -goog.provide('ol.render.canvas.ImageReplay'); - -goog.require('ol'); -goog.require('ol.render.canvas.Instruction'); -goog.require('ol.render.canvas.Replay'); - - -/** - * @constructor - * @extends {ol.render.canvas.Replay} - * @param {number} tolerance Tolerance. - * @param {ol.Extent} maxExtent Maximum extent. - * @param {number} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @param {boolean} overlaps The replay can have overlapping geometries. - * @struct - */ -ol.render.canvas.ImageReplay = function(tolerance, maxExtent, resolution, pixelRatio, overlaps) { - ol.render.canvas.Replay.call(this, tolerance, maxExtent, resolution, pixelRatio, overlaps); - - /** - * @private - * @type {HTMLCanvasElement|HTMLVideoElement|Image} - */ - this.hitDetectionImage_ = null; - - /** - * @private - * @type {HTMLCanvasElement|HTMLVideoElement|Image} - */ - this.image_ = null; - - /** - * @private - * @type {number|undefined} - */ - this.anchorX_ = undefined; - - /** - * @private - * @type {number|undefined} - */ - this.anchorY_ = undefined; - - /** - * @private - * @type {number|undefined} - */ - this.height_ = undefined; - - /** - * @private - * @type {number|undefined} - */ - this.opacity_ = undefined; - - /** - * @private - * @type {number|undefined} - */ - this.originX_ = undefined; - - /** - * @private - * @type {number|undefined} - */ - this.originY_ = undefined; - - /** - * @private - * @type {boolean|undefined} - */ - this.rotateWithView_ = undefined; - - /** - * @private - * @type {number|undefined} - */ - this.rotation_ = undefined; - - /** - * @private - * @type {number|undefined} - */ - this.scale_ = undefined; - - /** - * @private - * @type {boolean|undefined} - */ - this.snapToPixel_ = undefined; - - /** - * @private - * @type {number|undefined} - */ - this.width_ = undefined; - -}; -ol.inherits(ol.render.canvas.ImageReplay, ol.render.canvas.Replay); - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @private - * @return {number} My end. - */ -ol.render.canvas.ImageReplay.prototype.drawCoordinates_ = function(flatCoordinates, offset, end, stride) { - return this.appendFlatCoordinates( - flatCoordinates, offset, end, stride, false, false); -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.ImageReplay.prototype.drawPoint = function(pointGeometry, feature) { - if (!this.image_) { - return; - } - this.beginGeometry(pointGeometry, feature); - var flatCoordinates = pointGeometry.getFlatCoordinates(); - var stride = pointGeometry.getStride(); - var myBegin = this.coordinates.length; - var myEnd = this.drawCoordinates_( - flatCoordinates, 0, flatCoordinates.length, stride); - this.instructions.push([ - ol.render.canvas.Instruction.DRAW_IMAGE, myBegin, myEnd, this.image_, - // Remaining arguments to DRAW_IMAGE are in alphabetical order - this.anchorX_, this.anchorY_, this.height_, this.opacity_, - this.originX_, this.originY_, this.rotateWithView_, this.rotation_, - this.scale_ * this.pixelRatio, this.snapToPixel_, this.width_ - ]); - this.hitDetectionInstructions.push([ - ol.render.canvas.Instruction.DRAW_IMAGE, myBegin, myEnd, - this.hitDetectionImage_, - // Remaining arguments to DRAW_IMAGE are in alphabetical order - this.anchorX_, this.anchorY_, this.height_, this.opacity_, - this.originX_, this.originY_, this.rotateWithView_, this.rotation_, - this.scale_, this.snapToPixel_, this.width_ - ]); - this.endGeometry(pointGeometry, feature); -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.ImageReplay.prototype.drawMultiPoint = function(multiPointGeometry, feature) { - if (!this.image_) { - return; - } - this.beginGeometry(multiPointGeometry, feature); - var flatCoordinates = multiPointGeometry.getFlatCoordinates(); - var stride = multiPointGeometry.getStride(); - var myBegin = this.coordinates.length; - var myEnd = this.drawCoordinates_( - flatCoordinates, 0, flatCoordinates.length, stride); - this.instructions.push([ - ol.render.canvas.Instruction.DRAW_IMAGE, myBegin, myEnd, this.image_, - // Remaining arguments to DRAW_IMAGE are in alphabetical order - this.anchorX_, this.anchorY_, this.height_, this.opacity_, - this.originX_, this.originY_, this.rotateWithView_, this.rotation_, - this.scale_ * this.pixelRatio, this.snapToPixel_, this.width_ - ]); - this.hitDetectionInstructions.push([ - ol.render.canvas.Instruction.DRAW_IMAGE, myBegin, myEnd, - this.hitDetectionImage_, - // Remaining arguments to DRAW_IMAGE are in alphabetical order - this.anchorX_, this.anchorY_, this.height_, this.opacity_, - this.originX_, this.originY_, this.rotateWithView_, this.rotation_, - this.scale_, this.snapToPixel_, this.width_ - ]); - this.endGeometry(multiPointGeometry, feature); -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.ImageReplay.prototype.finish = function() { - this.reverseHitDetectionInstructions(); - // FIXME this doesn't really protect us against further calls to draw*Geometry - this.anchorX_ = undefined; - this.anchorY_ = undefined; - this.hitDetectionImage_ = null; - this.image_ = null; - this.height_ = undefined; - this.scale_ = undefined; - this.opacity_ = undefined; - this.originX_ = undefined; - this.originY_ = undefined; - this.rotateWithView_ = undefined; - this.rotation_ = undefined; - this.snapToPixel_ = undefined; - this.width_ = undefined; -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.ImageReplay.prototype.setImageStyle = function(imageStyle) { - var anchor = imageStyle.getAnchor(); - var size = imageStyle.getSize(); - var hitDetectionImage = imageStyle.getHitDetectionImage(1); - var image = imageStyle.getImage(1); - var origin = imageStyle.getOrigin(); - this.anchorX_ = anchor[0]; - this.anchorY_ = anchor[1]; - this.hitDetectionImage_ = hitDetectionImage; - this.image_ = image; - this.height_ = size[1]; - this.opacity_ = imageStyle.getOpacity(); - this.originX_ = origin[0]; - this.originY_ = origin[1]; - this.rotateWithView_ = imageStyle.getRotateWithView(); - this.rotation_ = imageStyle.getRotation(); - this.scale_ = imageStyle.getScale(); - this.snapToPixel_ = imageStyle.getSnapToPixel(); - this.width_ = size[0]; -}; - -goog.provide('ol.render.canvas.LineStringReplay'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.colorlike'); -goog.require('ol.extent'); -goog.require('ol.render.canvas'); -goog.require('ol.render.canvas.Instruction'); -goog.require('ol.render.canvas.Replay'); - - -/** - * @constructor - * @extends {ol.render.canvas.Replay} - * @param {number} tolerance Tolerance. - * @param {ol.Extent} maxExtent Maximum extent. - * @param {number} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @param {boolean} overlaps The replay can have overlapping geometries. - * @struct - */ -ol.render.canvas.LineStringReplay = function(tolerance, maxExtent, resolution, pixelRatio, overlaps) { - - ol.render.canvas.Replay.call(this, tolerance, maxExtent, resolution, pixelRatio, overlaps); - - /** - * @private - * @type {ol.Extent} - */ - this.bufferedMaxExtent_ = null; - - /** - * @private - * @type {{currentStrokeStyle: (ol.ColorLike|undefined), - * currentLineCap: (string|undefined), - * currentLineDash: Array.<number>, - * currentLineDashOffset: (number|undefined), - * currentLineJoin: (string|undefined), - * currentLineWidth: (number|undefined), - * currentMiterLimit: (number|undefined), - * lastStroke: (number|undefined), - * strokeStyle: (ol.ColorLike|undefined), - * lineCap: (string|undefined), - * lineDash: Array.<number>, - * lineDashOffset: (number|undefined), - * lineJoin: (string|undefined), - * lineWidth: (number|undefined), - * miterLimit: (number|undefined)}|null} - */ - this.state_ = { - currentStrokeStyle: undefined, - currentLineCap: undefined, - currentLineDash: null, - currentLineDashOffset: undefined, - currentLineJoin: undefined, - currentLineWidth: undefined, - currentMiterLimit: undefined, - lastStroke: undefined, - strokeStyle: undefined, - lineCap: undefined, - lineDash: null, - lineDashOffset: undefined, - lineJoin: undefined, - lineWidth: undefined, - miterLimit: undefined - }; - -}; -ol.inherits(ol.render.canvas.LineStringReplay, ol.render.canvas.Replay); - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @private - * @return {number} end. - */ -ol.render.canvas.LineStringReplay.prototype.drawFlatCoordinates_ = function(flatCoordinates, offset, end, stride) { - var myBegin = this.coordinates.length; - var myEnd = this.appendFlatCoordinates( - flatCoordinates, offset, end, stride, false, false); - var moveToLineToInstruction = - [ol.render.canvas.Instruction.MOVE_TO_LINE_TO, myBegin, myEnd]; - this.instructions.push(moveToLineToInstruction); - this.hitDetectionInstructions.push(moveToLineToInstruction); - return end; -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.LineStringReplay.prototype.getBufferedMaxExtent = function() { - if (!this.bufferedMaxExtent_) { - this.bufferedMaxExtent_ = ol.extent.clone(this.maxExtent); - if (this.maxLineWidth > 0) { - var width = this.resolution * (this.maxLineWidth + 1) / 2; - ol.extent.buffer(this.bufferedMaxExtent_, width, this.bufferedMaxExtent_); - } - } - return this.bufferedMaxExtent_; -}; - - -/** - * @private - */ -ol.render.canvas.LineStringReplay.prototype.setStrokeStyle_ = function() { - var state = this.state_; - var strokeStyle = state.strokeStyle; - var lineCap = state.lineCap; - var lineDash = state.lineDash; - var lineDashOffset = state.lineDashOffset; - var lineJoin = state.lineJoin; - var lineWidth = state.lineWidth; - var miterLimit = state.miterLimit; - if (state.currentStrokeStyle != strokeStyle || - state.currentLineCap != lineCap || - !ol.array.equals(state.currentLineDash, lineDash) || - state.currentLineDashOffset != lineDashOffset || - state.currentLineJoin != lineJoin || - state.currentLineWidth != lineWidth || - state.currentMiterLimit != miterLimit) { - if (state.lastStroke != undefined && state.lastStroke != this.coordinates.length) { - this.instructions.push([ol.render.canvas.Instruction.STROKE]); - state.lastStroke = this.coordinates.length; - } - state.lastStroke = 0; - this.instructions.push([ - ol.render.canvas.Instruction.SET_STROKE_STYLE, - strokeStyle, lineWidth * this.pixelRatio, lineCap, lineJoin, miterLimit, - this.applyPixelRatio(lineDash), lineDashOffset * this.pixelRatio - ], [ - ol.render.canvas.Instruction.BEGIN_PATH - ]); - state.currentStrokeStyle = strokeStyle; - state.currentLineCap = lineCap; - state.currentLineDash = lineDash; - state.currentLineDashOffset = lineDashOffset; - state.currentLineJoin = lineJoin; - state.currentLineWidth = lineWidth; - state.currentMiterLimit = miterLimit; - } -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.LineStringReplay.prototype.drawLineString = function(lineStringGeometry, feature) { - var state = this.state_; - var strokeStyle = state.strokeStyle; - var lineWidth = state.lineWidth; - if (strokeStyle === undefined || lineWidth === undefined) { - return; - } - this.setStrokeStyle_(); - this.beginGeometry(lineStringGeometry, feature); - this.hitDetectionInstructions.push([ - ol.render.canvas.Instruction.SET_STROKE_STYLE, - state.strokeStyle, state.lineWidth, state.lineCap, state.lineJoin, - state.miterLimit, state.lineDash, state.lineDashOffset - ], [ - ol.render.canvas.Instruction.BEGIN_PATH - ]); - var flatCoordinates = lineStringGeometry.getFlatCoordinates(); - var stride = lineStringGeometry.getStride(); - this.drawFlatCoordinates_(flatCoordinates, 0, flatCoordinates.length, stride); - this.hitDetectionInstructions.push([ol.render.canvas.Instruction.STROKE]); - this.endGeometry(lineStringGeometry, feature); -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.LineStringReplay.prototype.drawMultiLineString = function(multiLineStringGeometry, feature) { - var state = this.state_; - var strokeStyle = state.strokeStyle; - var lineWidth = state.lineWidth; - if (strokeStyle === undefined || lineWidth === undefined) { - return; - } - this.setStrokeStyle_(); - this.beginGeometry(multiLineStringGeometry, feature); - this.hitDetectionInstructions.push([ - ol.render.canvas.Instruction.SET_STROKE_STYLE, - state.strokeStyle, state.lineWidth, state.lineCap, state.lineJoin, - state.miterLimit, state.lineDash, state.lineDashOffset - ], [ - ol.render.canvas.Instruction.BEGIN_PATH - ]); - var ends = multiLineStringGeometry.getEnds(); - var flatCoordinates = multiLineStringGeometry.getFlatCoordinates(); - var stride = multiLineStringGeometry.getStride(); - var offset = 0; - var i, ii; - for (i = 0, ii = ends.length; i < ii; ++i) { - offset = this.drawFlatCoordinates_( - flatCoordinates, offset, ends[i], stride); - } - this.hitDetectionInstructions.push([ol.render.canvas.Instruction.STROKE]); - this.endGeometry(multiLineStringGeometry, feature); -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.LineStringReplay.prototype.finish = function() { - var state = this.state_; - if (state.lastStroke != undefined && state.lastStroke != this.coordinates.length) { - this.instructions.push([ol.render.canvas.Instruction.STROKE]); - } - this.reverseHitDetectionInstructions(); - this.state_ = null; -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.LineStringReplay.prototype.setFillStrokeStyle = function(fillStyle, strokeStyle) { - var strokeStyleColor = strokeStyle.getColor(); - this.state_.strokeStyle = ol.colorlike.asColorLike(strokeStyleColor ? - strokeStyleColor : ol.render.canvas.defaultStrokeStyle); - var strokeStyleLineCap = strokeStyle.getLineCap(); - this.state_.lineCap = strokeStyleLineCap !== undefined ? - strokeStyleLineCap : ol.render.canvas.defaultLineCap; - var strokeStyleLineDash = strokeStyle.getLineDash(); - this.state_.lineDash = strokeStyleLineDash ? - strokeStyleLineDash : ol.render.canvas.defaultLineDash; - var strokeStyleLineDashOffset = strokeStyle.getLineDashOffset(); - this.state_.lineDashOffset = strokeStyleLineDashOffset ? - strokeStyleLineDashOffset : ol.render.canvas.defaultLineDashOffset; - var strokeStyleLineJoin = strokeStyle.getLineJoin(); - this.state_.lineJoin = strokeStyleLineJoin !== undefined ? - strokeStyleLineJoin : ol.render.canvas.defaultLineJoin; - var strokeStyleWidth = strokeStyle.getWidth(); - this.state_.lineWidth = strokeStyleWidth !== undefined ? - strokeStyleWidth : ol.render.canvas.defaultLineWidth; - var strokeStyleMiterLimit = strokeStyle.getMiterLimit(); - this.state_.miterLimit = strokeStyleMiterLimit !== undefined ? - strokeStyleMiterLimit : ol.render.canvas.defaultMiterLimit; - - if (this.state_.lineWidth > this.maxLineWidth) { - this.maxLineWidth = this.state_.lineWidth; - // invalidate the buffered max extent cache - this.bufferedMaxExtent_ = null; - } -}; - -goog.provide('ol.render.canvas.PolygonReplay'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.color'); -goog.require('ol.colorlike'); -goog.require('ol.extent'); -goog.require('ol.geom.flat.simplify'); -goog.require('ol.render.canvas'); -goog.require('ol.render.canvas.Instruction'); -goog.require('ol.render.canvas.Replay'); - - -/** - * @constructor - * @extends {ol.render.canvas.Replay} - * @param {number} tolerance Tolerance. - * @param {ol.Extent} maxExtent Maximum extent. - * @param {number} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @param {boolean} overlaps The replay can have overlapping geometries. - * @struct - */ -ol.render.canvas.PolygonReplay = function(tolerance, maxExtent, resolution, pixelRatio, overlaps) { - - ol.render.canvas.Replay.call(this, tolerance, maxExtent, resolution, pixelRatio, overlaps); - - /** - * @private - * @type {ol.Extent} - */ - this.bufferedMaxExtent_ = null; - - /** - * @private - * @type {{currentFillStyle: (ol.ColorLike|undefined), - * currentStrokeStyle: (ol.ColorLike|undefined), - * currentLineCap: (string|undefined), - * currentLineDash: Array.<number>, - * currentLineDashOffset: (number|undefined), - * currentLineJoin: (string|undefined), - * currentLineWidth: (number|undefined), - * currentMiterLimit: (number|undefined), - * fillStyle: (ol.ColorLike|undefined), - * strokeStyle: (ol.ColorLike|undefined), - * lineCap: (string|undefined), - * lineDash: Array.<number>, - * lineDashOffset: (number|undefined), - * lineJoin: (string|undefined), - * lineWidth: (number|undefined), - * miterLimit: (number|undefined)}|null} - */ - this.state_ = { - currentFillStyle: undefined, - currentStrokeStyle: undefined, - currentLineCap: undefined, - currentLineDash: null, - currentLineDashOffset: undefined, - currentLineJoin: undefined, - currentLineWidth: undefined, - currentMiterLimit: undefined, - fillStyle: undefined, - strokeStyle: undefined, - lineCap: undefined, - lineDash: null, - lineDashOffset: undefined, - lineJoin: undefined, - lineWidth: undefined, - miterLimit: undefined - }; - -}; -ol.inherits(ol.render.canvas.PolygonReplay, ol.render.canvas.Replay); - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<number>} ends Ends. - * @param {number} stride Stride. - * @private - * @return {number} End. - */ -ol.render.canvas.PolygonReplay.prototype.drawFlatCoordinatess_ = function(flatCoordinates, offset, ends, stride) { - var state = this.state_; - var fill = state.fillStyle !== undefined; - var stroke = state.strokeStyle != undefined; - var numEnds = ends.length; - var beginPathInstruction = [ol.render.canvas.Instruction.BEGIN_PATH]; - this.instructions.push(beginPathInstruction); - this.hitDetectionInstructions.push(beginPathInstruction); - for (var i = 0; i < numEnds; ++i) { - var end = ends[i]; - var myBegin = this.coordinates.length; - var myEnd = this.appendFlatCoordinates( - flatCoordinates, offset, end, stride, true, !stroke); - var moveToLineToInstruction = - [ol.render.canvas.Instruction.MOVE_TO_LINE_TO, myBegin, myEnd]; - this.instructions.push(moveToLineToInstruction); - this.hitDetectionInstructions.push(moveToLineToInstruction); - if (stroke) { - // Performance optimization: only call closePath() when we have a stroke. - // Otherwise the ring is closed already (see appendFlatCoordinates above). - var closePathInstruction = [ol.render.canvas.Instruction.CLOSE_PATH]; - this.instructions.push(closePathInstruction); - this.hitDetectionInstructions.push(closePathInstruction); - } - offset = end; - } - var fillInstruction = [ol.render.canvas.Instruction.FILL]; - this.hitDetectionInstructions.push(fillInstruction); - if (fill) { - this.instructions.push(fillInstruction); - } - if (stroke) { - var strokeInstruction = [ol.render.canvas.Instruction.STROKE]; - this.instructions.push(strokeInstruction); - this.hitDetectionInstructions.push(strokeInstruction); - } - return offset; -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.PolygonReplay.prototype.drawCircle = function(circleGeometry, feature) { - var state = this.state_; - var fillStyle = state.fillStyle; - var strokeStyle = state.strokeStyle; - if (fillStyle === undefined && strokeStyle === undefined) { - return; - } - this.setFillStrokeStyles_(circleGeometry); - this.beginGeometry(circleGeometry, feature); - // always fill the circle for hit detection - this.hitDetectionInstructions.push([ - ol.render.canvas.Instruction.SET_FILL_STYLE, - ol.color.asString(ol.render.canvas.defaultFillStyle) - ]); - if (state.strokeStyle !== undefined) { - this.hitDetectionInstructions.push([ - ol.render.canvas.Instruction.SET_STROKE_STYLE, - state.strokeStyle, state.lineWidth, state.lineCap, state.lineJoin, - state.miterLimit, state.lineDash, state.lineDashOffset - ]); - } - var flatCoordinates = circleGeometry.getFlatCoordinates(); - var stride = circleGeometry.getStride(); - var myBegin = this.coordinates.length; - this.appendFlatCoordinates( - flatCoordinates, 0, flatCoordinates.length, stride, false, false); - var beginPathInstruction = [ol.render.canvas.Instruction.BEGIN_PATH]; - var circleInstruction = [ol.render.canvas.Instruction.CIRCLE, myBegin]; - this.instructions.push(beginPathInstruction, circleInstruction); - this.hitDetectionInstructions.push(beginPathInstruction, circleInstruction); - var fillInstruction = [ol.render.canvas.Instruction.FILL]; - this.hitDetectionInstructions.push(fillInstruction); - if (state.fillStyle !== undefined) { - this.instructions.push(fillInstruction); - } - if (state.strokeStyle !== undefined) { - var strokeInstruction = [ol.render.canvas.Instruction.STROKE]; - this.instructions.push(strokeInstruction); - this.hitDetectionInstructions.push(strokeInstruction); - } - this.endGeometry(circleGeometry, feature); -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.PolygonReplay.prototype.drawPolygon = function(polygonGeometry, feature) { - var state = this.state_; - this.setFillStrokeStyles_(polygonGeometry); - this.beginGeometry(polygonGeometry, feature); - // always fill the polygon for hit detection - this.hitDetectionInstructions.push([ - ol.render.canvas.Instruction.SET_FILL_STYLE, - ol.color.asString(ol.render.canvas.defaultFillStyle)] - ); - if (state.strokeStyle !== undefined) { - this.hitDetectionInstructions.push([ - ol.render.canvas.Instruction.SET_STROKE_STYLE, - state.strokeStyle, state.lineWidth, state.lineCap, state.lineJoin, - state.miterLimit, state.lineDash, state.lineDashOffset - ]); - } - var ends = polygonGeometry.getEnds(); - var flatCoordinates = polygonGeometry.getOrientedFlatCoordinates(); - var stride = polygonGeometry.getStride(); - this.drawFlatCoordinatess_(flatCoordinates, 0, ends, stride); - this.endGeometry(polygonGeometry, feature); -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.PolygonReplay.prototype.drawMultiPolygon = function(multiPolygonGeometry, feature) { - var state = this.state_; - var fillStyle = state.fillStyle; - var strokeStyle = state.strokeStyle; - if (fillStyle === undefined && strokeStyle === undefined) { - return; - } - this.setFillStrokeStyles_(multiPolygonGeometry); - this.beginGeometry(multiPolygonGeometry, feature); - // always fill the multi-polygon for hit detection - this.hitDetectionInstructions.push([ - ol.render.canvas.Instruction.SET_FILL_STYLE, - ol.color.asString(ol.render.canvas.defaultFillStyle) - ]); - if (state.strokeStyle !== undefined) { - this.hitDetectionInstructions.push([ - ol.render.canvas.Instruction.SET_STROKE_STYLE, - state.strokeStyle, state.lineWidth, state.lineCap, state.lineJoin, - state.miterLimit, state.lineDash, state.lineDashOffset - ]); - } - var endss = multiPolygonGeometry.getEndss(); - var flatCoordinates = multiPolygonGeometry.getOrientedFlatCoordinates(); - var stride = multiPolygonGeometry.getStride(); - var offset = 0; - var i, ii; - for (i = 0, ii = endss.length; i < ii; ++i) { - offset = this.drawFlatCoordinatess_( - flatCoordinates, offset, endss[i], stride); - } - this.endGeometry(multiPolygonGeometry, feature); -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.PolygonReplay.prototype.finish = function() { - this.reverseHitDetectionInstructions(); - this.state_ = null; - // We want to preserve topology when drawing polygons. Polygons are - // simplified using quantization and point elimination. However, we might - // have received a mix of quantized and non-quantized geometries, so ensure - // that all are quantized by quantizing all coordinates in the batch. - var tolerance = this.tolerance; - if (tolerance !== 0) { - var coordinates = this.coordinates; - var i, ii; - for (i = 0, ii = coordinates.length; i < ii; ++i) { - coordinates[i] = ol.geom.flat.simplify.snap(coordinates[i], tolerance); - } - } -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.PolygonReplay.prototype.getBufferedMaxExtent = function() { - if (!this.bufferedMaxExtent_) { - this.bufferedMaxExtent_ = ol.extent.clone(this.maxExtent); - if (this.maxLineWidth > 0) { - var width = this.resolution * (this.maxLineWidth + 1) / 2; - ol.extent.buffer(this.bufferedMaxExtent_, width, this.bufferedMaxExtent_); - } - } - return this.bufferedMaxExtent_; -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.PolygonReplay.prototype.setFillStrokeStyle = function(fillStyle, strokeStyle) { - var state = this.state_; - if (fillStyle) { - var fillStyleColor = fillStyle.getColor(); - state.fillStyle = ol.colorlike.asColorLike(fillStyleColor ? - fillStyleColor : ol.render.canvas.defaultFillStyle); - } else { - state.fillStyle = undefined; - } - if (strokeStyle) { - var strokeStyleColor = strokeStyle.getColor(); - state.strokeStyle = ol.colorlike.asColorLike(strokeStyleColor ? - strokeStyleColor : ol.render.canvas.defaultStrokeStyle); - var strokeStyleLineCap = strokeStyle.getLineCap(); - state.lineCap = strokeStyleLineCap !== undefined ? - strokeStyleLineCap : ol.render.canvas.defaultLineCap; - var strokeStyleLineDash = strokeStyle.getLineDash(); - state.lineDash = strokeStyleLineDash ? - strokeStyleLineDash.slice() : ol.render.canvas.defaultLineDash; - var strokeStyleLineDashOffset = strokeStyle.getLineDashOffset(); - state.lineDashOffset = strokeStyleLineDashOffset ? - strokeStyleLineDashOffset : ol.render.canvas.defaultLineDashOffset; - var strokeStyleLineJoin = strokeStyle.getLineJoin(); - state.lineJoin = strokeStyleLineJoin !== undefined ? - strokeStyleLineJoin : ol.render.canvas.defaultLineJoin; - var strokeStyleWidth = strokeStyle.getWidth(); - state.lineWidth = strokeStyleWidth !== undefined ? - strokeStyleWidth : ol.render.canvas.defaultLineWidth; - var strokeStyleMiterLimit = strokeStyle.getMiterLimit(); - state.miterLimit = strokeStyleMiterLimit !== undefined ? - strokeStyleMiterLimit : ol.render.canvas.defaultMiterLimit; - - if (state.lineWidth > this.maxLineWidth) { - this.maxLineWidth = state.lineWidth; - // invalidate the buffered max extent cache - this.bufferedMaxExtent_ = null; - } - } else { - state.strokeStyle = undefined; - state.lineCap = undefined; - state.lineDash = null; - state.lineDashOffset = undefined; - state.lineJoin = undefined; - state.lineWidth = undefined; - state.miterLimit = undefined; - } -}; - - -/** - * @private - * @param {ol.geom.Geometry|ol.render.Feature} geometry Geometry. - */ -ol.render.canvas.PolygonReplay.prototype.setFillStrokeStyles_ = function(geometry) { - var state = this.state_; - var fillStyle = state.fillStyle; - var strokeStyle = state.strokeStyle; - var lineCap = state.lineCap; - var lineDash = state.lineDash; - var lineDashOffset = state.lineDashOffset; - var lineJoin = state.lineJoin; - var lineWidth = state.lineWidth; - var miterLimit = state.miterLimit; - if (fillStyle !== undefined && (typeof fillStyle !== 'string' || state.currentFillStyle != fillStyle)) { - var fillInstruction = [ol.render.canvas.Instruction.SET_FILL_STYLE, fillStyle]; - if (typeof fillStyle !== 'string') { - var fillExtent = geometry.getExtent(); - fillInstruction.push([fillExtent[0], fillExtent[3]]); - } - this.instructions.push(fillInstruction); - state.currentFillStyle = state.fillStyle; - } - if (strokeStyle !== undefined) { - if (state.currentStrokeStyle != strokeStyle || - state.currentLineCap != lineCap || - !ol.array.equals(state.currentLineDash, lineDash) || - state.currentLineDashOffset != lineDashOffset || - state.currentLineJoin != lineJoin || - state.currentLineWidth != lineWidth || - state.currentMiterLimit != miterLimit) { - this.instructions.push([ - ol.render.canvas.Instruction.SET_STROKE_STYLE, - strokeStyle, lineWidth * this.pixelRatio, lineCap, lineJoin, miterLimit, - this.applyPixelRatio(lineDash), lineDashOffset * this.pixelRatio - ]); - state.currentStrokeStyle = strokeStyle; - state.currentLineCap = lineCap; - state.currentLineDash = lineDash; - state.currentLineDashOffset = lineDashOffset; - state.currentLineJoin = lineJoin; - state.currentLineWidth = lineWidth; - state.currentMiterLimit = miterLimit; - } - } -}; - -goog.provide('ol.geom.flat.straightchunk'); - - -/** - * @param {number} maxAngle Maximum acceptable angle delta between segments. - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @return {Array.<number>} Start and end of the first suitable chunk of the - * given `flatCoordinates`. - */ -ol.geom.flat.straightchunk.lineString = function(maxAngle, flatCoordinates, offset, end, stride) { - var chunkStart = offset; - var chunkEnd = offset; - var chunkM = 0; - var m = 0; - var start = offset; - var acos, i, m12, m23, x1, y1, x12, y12, x23, y23; - for (i = offset; i < end; i += stride) { - var x2 = flatCoordinates[i]; - var y2 = flatCoordinates[i + 1]; - if (x1 !== undefined) { - x23 = x2 - x1; - y23 = y2 - y1; - m23 = Math.sqrt(x23 * x23 + y23 * y23); - if (x12 !== undefined) { - m += m12; - acos = Math.acos((x12 * x23 + y12 * y23) / (m12 * m23)); - if (acos > maxAngle) { - if (m > chunkM) { - chunkM = m; - chunkStart = start; - chunkEnd = i; - } - m = 0; - start = i - stride; - } - } - m12 = m23; - x12 = x23; - y12 = y23; - } - x1 = x2; - y1 = y2; - } - m += m23; - return m > chunkM ? [start, i] : [chunkStart, chunkEnd]; -}; - -goog.provide('ol.render.ReplayType'); - - -/** - * @enum {string} - */ -ol.render.ReplayType = { - CIRCLE: 'Circle', - DEFAULT: 'Default', - IMAGE: 'Image', - LINE_STRING: 'LineString', - POLYGON: 'Polygon', - TEXT: 'Text' -}; - -goog.provide('ol.render.replay'); - -goog.require('ol.render.ReplayType'); - - -/** - * @const - * @type {Array.<ol.render.ReplayType>} - */ -ol.render.replay.ORDER = [ - ol.render.ReplayType.POLYGON, - ol.render.ReplayType.CIRCLE, - ol.render.ReplayType.LINE_STRING, - ol.render.ReplayType.IMAGE, - ol.render.ReplayType.TEXT, - ol.render.ReplayType.DEFAULT -]; - -/** - * @const - * @enum {number} - */ -ol.render.replay.TEXT_ALIGN = {}; -ol.render.replay.TEXT_ALIGN['left'] = 0; -ol.render.replay.TEXT_ALIGN['end'] = 0; -ol.render.replay.TEXT_ALIGN['center'] = 0.5; -ol.render.replay.TEXT_ALIGN['right'] = 1; -ol.render.replay.TEXT_ALIGN['start'] = 1; -ol.render.replay.TEXT_ALIGN['top'] = 0; -ol.render.replay.TEXT_ALIGN['middle'] = 0.5; -ol.render.replay.TEXT_ALIGN['hanging'] = 0.2; -ol.render.replay.TEXT_ALIGN['alphabetic'] = 0.8; -ol.render.replay.TEXT_ALIGN['ideographic'] = 0.8; -ol.render.replay.TEXT_ALIGN['bottom'] = 1; - -goog.provide('ol.structs.LRUCache'); - -goog.require('ol.asserts'); - - -/** - * Implements a Least-Recently-Used cache where the keys do not conflict with - * Object's properties (e.g. 'hasOwnProperty' is not allowed as a key). Expiring - * items from the cache is the responsibility of the user. - * @constructor - * @struct - * @template T - * @param {number=} opt_highWaterMark High water mark. - */ -ol.structs.LRUCache = function(opt_highWaterMark) { - - /** - * @type {number} - */ - this.highWaterMark = opt_highWaterMark !== undefined ? opt_highWaterMark : 2048; - - /** - * @private - * @type {number} - */ - this.count_ = 0; - - /** - * @private - * @type {!Object.<string, ol.LRUCacheEntry>} - */ - this.entries_ = {}; - - /** - * @private - * @type {?ol.LRUCacheEntry} - */ - this.oldest_ = null; - - /** - * @private - * @type {?ol.LRUCacheEntry} - */ - this.newest_ = null; - -}; - - -/** - * @return {boolean} Can expire cache. - */ -ol.structs.LRUCache.prototype.canExpireCache = function() { - return this.getCount() > this.highWaterMark; -}; - - -/** - * FIXME empty description for jsdoc - */ -ol.structs.LRUCache.prototype.clear = function() { - this.count_ = 0; - this.entries_ = {}; - this.oldest_ = null; - this.newest_ = null; -}; - - -/** - * @param {string} key Key. - * @return {boolean} Contains key. - */ -ol.structs.LRUCache.prototype.containsKey = function(key) { - return this.entries_.hasOwnProperty(key); -}; - - -/** - * @param {function(this: S, T, string, ol.structs.LRUCache): ?} f The function - * to call for every entry from the oldest to the newer. This function takes - * 3 arguments (the entry value, the entry key and the LRUCache object). - * The return value is ignored. - * @param {S=} opt_this The object to use as `this` in `f`. - * @template S - */ -ol.structs.LRUCache.prototype.forEach = function(f, opt_this) { - var entry = this.oldest_; - while (entry) { - f.call(opt_this, entry.value_, entry.key_, this); - entry = entry.newer; - } -}; - - -/** - * @param {string} key Key. - * @return {T} Value. - */ -ol.structs.LRUCache.prototype.get = function(key) { - var entry = this.entries_[key]; - ol.asserts.assert(entry !== undefined, - 15); // Tried to get a value for a key that does not exist in the cache - if (entry === this.newest_) { - return entry.value_; - } else if (entry === this.oldest_) { - this.oldest_ = /** @type {ol.LRUCacheEntry} */ (this.oldest_.newer); - this.oldest_.older = null; - } else { - entry.newer.older = entry.older; - entry.older.newer = entry.newer; - } - entry.newer = null; - entry.older = this.newest_; - this.newest_.newer = entry; - this.newest_ = entry; - return entry.value_; -}; - - -/** - * Remove an entry from the cache. - * @param {string} key The entry key. - * @return {T} The removed entry. - */ -ol.structs.LRUCache.prototype.remove = function(key) { - var entry = this.entries_[key]; - ol.asserts.assert(entry !== undefined, 15); // Tried to get a value for a key that does not exist in the cache - if (entry === this.newest_) { - this.newest_ = /** @type {ol.LRUCacheEntry} */ (entry.older); - if (this.newest_) { - this.newest_.newer = null; - } - } else if (entry === this.oldest_) { - this.oldest_ = /** @type {ol.LRUCacheEntry} */ (entry.newer); - if (this.oldest_) { - this.oldest_.older = null; - } - } else { - entry.newer.older = entry.older; - entry.older.newer = entry.newer; - } - delete this.entries_[key]; - --this.count_; - return entry.value_; -}; - - -/** - * @return {number} Count. - */ -ol.structs.LRUCache.prototype.getCount = function() { - return this.count_; -}; - - -/** - * @return {Array.<string>} Keys. - */ -ol.structs.LRUCache.prototype.getKeys = function() { - var keys = new Array(this.count_); - var i = 0; - var entry; - for (entry = this.newest_; entry; entry = entry.older) { - keys[i++] = entry.key_; - } - return keys; -}; - - -/** - * @return {Array.<T>} Values. - */ -ol.structs.LRUCache.prototype.getValues = function() { - var values = new Array(this.count_); - var i = 0; - var entry; - for (entry = this.newest_; entry; entry = entry.older) { - values[i++] = entry.value_; - } - return values; -}; - - -/** - * @return {T} Last value. - */ -ol.structs.LRUCache.prototype.peekLast = function() { - return this.oldest_.value_; -}; - - -/** - * @return {string} Last key. - */ -ol.structs.LRUCache.prototype.peekLastKey = function() { - return this.oldest_.key_; -}; - - -/** - * Get the key of the newest item in the cache. Throws if the cache is empty. - * @return {string} The newest key. - */ -ol.structs.LRUCache.prototype.peekFirstKey = function() { - return this.newest_.key_; -}; - - -/** - * @return {T} value Value. - */ -ol.structs.LRUCache.prototype.pop = function() { - var entry = this.oldest_; - delete this.entries_[entry.key_]; - if (entry.newer) { - entry.newer.older = null; - } - this.oldest_ = /** @type {ol.LRUCacheEntry} */ (entry.newer); - if (!this.oldest_) { - this.newest_ = null; - } - --this.count_; - return entry.value_; -}; - - -/** - * @param {string} key Key. - * @param {T} value Value. - */ -ol.structs.LRUCache.prototype.replace = function(key, value) { - this.get(key); // update `newest_` - this.entries_[key].value_ = value; -}; - - -/** - * @param {string} key Key. - * @param {T} value Value. - */ -ol.structs.LRUCache.prototype.set = function(key, value) { - ol.asserts.assert(!(key in this.entries_), - 16); // Tried to set a value for a key that is used already - var entry = /** @type {ol.LRUCacheEntry} */ ({ - key_: key, - newer: null, - older: this.newest_, - value_: value - }); - if (!this.newest_) { - this.oldest_ = entry; - } else { - this.newest_.newer = entry; - } - this.newest_ = entry; - this.entries_[key] = entry; - ++this.count_; -}; - -goog.provide('ol.style.TextPlacement'); - - -/** - * Text placement. One of `'point'`, `'line'`. Default is `'point'`. Note that - * `'line'` requires the underlying geometry to be a {@link ol.geom.LineString}, - * {@link ol.geom.Polygon}, {@link ol.geom.MultiLineString} or - * {@link ol.geom.MultiPolygon}. - * @enum {string} - */ -ol.style.TextPlacement = { - POINT: 'point', - LINE: 'line' -}; - -goog.provide('ol.render.canvas.TextReplay'); - -goog.require('ol'); -goog.require('ol.colorlike'); -goog.require('ol.dom'); -goog.require('ol.geom.flat.straightchunk'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.has'); -goog.require('ol.render.canvas'); -goog.require('ol.render.canvas.Instruction'); -goog.require('ol.render.canvas.Replay'); -goog.require('ol.render.replay'); -goog.require('ol.structs.LRUCache'); -goog.require('ol.style.TextPlacement'); - - -/** - * @constructor - * @extends {ol.render.canvas.Replay} - * @param {number} tolerance Tolerance. - * @param {ol.Extent} maxExtent Maximum extent. - * @param {number} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @param {boolean} overlaps The replay can have overlapping geometries. - * @struct - */ -ol.render.canvas.TextReplay = function(tolerance, maxExtent, resolution, pixelRatio, overlaps) { - - ol.render.canvas.Replay.call(this, tolerance, maxExtent, resolution, pixelRatio, overlaps); - - /** - * @private - * @type {Array.<HTMLCanvasElement>} - */ - this.labels_ = null; - - /** - * @private - * @type {string} - */ - this.text_ = ''; - - /** - * @private - * @type {number} - */ - this.textOffsetX_ = 0; - - /** - * @private - * @type {number} - */ - this.textOffsetY_ = 0; - - /** - * @private - * @type {boolean|undefined} - */ - this.textRotateWithView_ = undefined; - - /** - * @private - * @type {number} - */ - this.textRotation_ = 0; - - /** - * @private - * @type {number} - */ - this.textScale_ = 0; - - /** - * @private - * @type {?ol.CanvasFillState} - */ - this.textFillState_ = null; - - /** - * @private - * @type {?ol.CanvasStrokeState} - */ - this.textStrokeState_ = null; - - /** - * @private - * @type {?ol.CanvasTextState} - */ - this.textState_ = null; - - /** - * @private - * @type {string} - */ - this.textKey_ = ''; - - /** - * @private - * @type {string} - */ - this.fillKey_ = ''; - - /** - * @private - * @type {string} - */ - this.strokeKey_ = ''; - - while (ol.render.canvas.TextReplay.labelCache_.canExpireCache()) { - ol.render.canvas.TextReplay.labelCache_.pop(); - } - -}; -ol.inherits(ol.render.canvas.TextReplay, ol.render.canvas.Replay); - - -/** - * @private - * @type {ol.structs.LRUCache.<HTMLCanvasElement>} - */ -ol.render.canvas.TextReplay.labelCache_ = new ol.structs.LRUCache(); - - -/** - * @param {string} font Font to use for measuring. - * @return {ol.Size} Measurement. - */ -ol.render.canvas.TextReplay.measureTextHeight = (function() { - var textContainer; - return function(font, lines, widths) { - if (!textContainer) { - textContainer = document.createElement('span'); - textContainer.textContent = 'M'; - textContainer.style.visibility = 'hidden'; - textContainer.style.whiteSpace = 'nowrap'; - } - textContainer.style.font = font; - document.body.appendChild(textContainer); - var height = textContainer.offsetHeight; - document.body.removeChild(textContainer); - return height; - }; -})(); - - -/** - * @this {Object} - * @param {CanvasRenderingContext2D} context Context. - * @param {number} pixelRatio Pixel ratio. - * @param {string} text Text. - * @return {number} Width. - */ -ol.render.canvas.TextReplay.getTextWidth = function(context, pixelRatio, text) { - var width = this[text]; - if (!width) { - this[text] = width = context.measureText(text).width; - } - return width * pixelRatio; -}; - - -/** - * @param {string} font Font to use for measuring. - * @param {Array.<string>} lines Lines to measure. - * @param {Array.<number>} widths Array will be populated with the widths of - * each line. - * @return {number} Width of the whole text. - */ -ol.render.canvas.TextReplay.measureTextWidths = (function() { - var context; - return function(font, lines, widths) { - if (!context) { - context = ol.dom.createCanvasContext2D(1, 1); - } - context.font = font; - var numLines = lines.length; - var width = 0; - var currentWidth, i; - for (i = 0; i < numLines; ++i) { - currentWidth = context.measureText(lines[i]).width; - width = Math.max(width, currentWidth); - widths.push(currentWidth); - } - return width; - }; -})(); - - -/** - * @inheritDoc - */ -ol.render.canvas.TextReplay.prototype.drawText = function(geometry, feature) { - var fillState = this.textFillState_; - var strokeState = this.textStrokeState_; - var textState = this.textState_; - if (this.text_ === '' || !textState || (!fillState && !strokeState)) { - return; - } - - var begin = this.coordinates.length; - - var geometryType = geometry.getType(); - var flatCoordinates = null; - var end = 2; - var stride = 2; - var i, ii; - - if (this.textState_.placement === ol.style.TextPlacement.LINE) { - var ends; - flatCoordinates = geometry.getFlatCoordinates(); - stride = geometry.getStride(); - if (geometryType == ol.geom.GeometryType.LINE_STRING) { - ends = [flatCoordinates.length]; - } else if (geometryType == ol.geom.GeometryType.MULTI_LINE_STRING) { - ends = geometry.getEnds(); - } else if (geometryType == ol.geom.GeometryType.POLYGON) { - ends = geometry.getEnds().slice(0, 1); - } else if (geometryType == ol.geom.GeometryType.MULTI_POLYGON) { - var endss = geometry.getEndss(); - ends = []; - for (i = 0, ii = endss.length; i < ii; ++i) { - ends.push(endss[i][0]); - } - } - this.beginGeometry(geometry, feature); - var textAlign = textState.textAlign; - var flatOffset = 0; - var flatEnd; - for (var o = 0, oo = ends.length; o < oo; ++o) { - if (textAlign == undefined) { - var range = ol.geom.flat.straightchunk.lineString( - textState.maxAngle, flatCoordinates, flatOffset, ends[o], stride); - flatOffset = range[0]; - flatEnd = range[1]; - } else { - flatEnd = ends[o]; - } - end = this.appendFlatCoordinates(flatCoordinates, flatOffset, flatEnd, stride, false, false); - flatOffset = ends[o]; - this.drawChars_(begin, end); - begin = end; - } - this.endGeometry(geometry, feature); - - } else { - var label = this.getImage_(this.text_, !!this.textFillState_, !!this.textStrokeState_); - var width = label.width / this.pixelRatio; - switch (geometryType) { - case ol.geom.GeometryType.POINT: - case ol.geom.GeometryType.MULTI_POINT: - flatCoordinates = geometry.getFlatCoordinates(); - end = flatCoordinates.length; - break; - case ol.geom.GeometryType.LINE_STRING: - flatCoordinates = /** @type {ol.geom.LineString} */ (geometry).getFlatMidpoint(); - break; - case ol.geom.GeometryType.CIRCLE: - flatCoordinates = /** @type {ol.geom.Circle} */ (geometry).getCenter(); - break; - case ol.geom.GeometryType.MULTI_LINE_STRING: - flatCoordinates = /** @type {ol.geom.MultiLineString} */ (geometry).getFlatMidpoints(); - end = flatCoordinates.length; - break; - case ol.geom.GeometryType.POLYGON: - flatCoordinates = /** @type {ol.geom.Polygon} */ (geometry).getFlatInteriorPoint(); - if (!textState.exceedLength && flatCoordinates[2] / this.resolution < width) { - return; - } - stride = 3; - break; - case ol.geom.GeometryType.MULTI_POLYGON: - var interiorPoints = /** @type {ol.geom.MultiPolygon} */ (geometry).getFlatInteriorPoints(); - flatCoordinates = []; - for (i = 0, ii = interiorPoints.length; i < ii; i += 3) { - if (textState.exceedLength || interiorPoints[i + 2] / this.resolution >= width) { - flatCoordinates.push(interiorPoints[i], interiorPoints[i + 1]); - } - } - end = flatCoordinates.length; - if (end == 0) { - return; - } - break; - default: - } - end = this.appendFlatCoordinates(flatCoordinates, 0, end, stride, false, false); - this.beginGeometry(geometry, feature); - this.drawTextImage_(label, begin, end); - this.endGeometry(geometry, feature); - } -}; - - -/** - * @private - * @param {string} text Text. - * @param {boolean} fill Fill. - * @param {boolean} stroke Stroke. - * @return {HTMLCanvasElement} Image. - */ -ol.render.canvas.TextReplay.prototype.getImage_ = function(text, fill, stroke) { - var label; - var key = (stroke ? this.strokeKey_ : '') + this.textKey_ + text + (fill ? this.fillKey_ : ''); - - var lines = text.split('\n'); - var numLines = lines.length; - if (!ol.render.canvas.TextReplay.labelCache_.containsKey(key)) { - var strokeState = this.textStrokeState_; - var fillState = this.textFillState_; - var textState = this.textState_; - var pixelRatio = this.pixelRatio; - var scale = this.textScale_ * pixelRatio; - var align = ol.render.replay.TEXT_ALIGN[textState.textAlign || ol.render.canvas.defaultTextAlign]; - var strokeWidth = stroke && strokeState.lineWidth ? strokeState.lineWidth : 0; - - var widths = []; - var width = ol.render.canvas.TextReplay.measureTextWidths(textState.font, lines, widths); - var lineHeight = ol.render.canvas.TextReplay.measureTextHeight(textState.font); - var height = lineHeight * numLines; - var renderWidth = (width + strokeWidth); - var context = ol.dom.createCanvasContext2D( - Math.ceil(renderWidth * scale), - Math.ceil((height + strokeWidth) * scale)); - label = context.canvas; - ol.render.canvas.TextReplay.labelCache_.set(key, label); - context.scale(scale, scale); - context.font = textState.font; - if (stroke) { - context.strokeStyle = strokeState.strokeStyle; - context.lineWidth = strokeWidth * (ol.has.SAFARI ? scale : 1); - context.lineCap = strokeState.lineCap; - context.lineJoin = strokeState.lineJoin; - context.miterLimit = strokeState.miterLimit; - if (ol.has.CANVAS_LINE_DASH) { - context.setLineDash(strokeState.lineDash); - context.lineDashOffset = strokeState.lineDashOffset; - } - } - if (fill) { - context.fillStyle = fillState.fillStyle; - } - context.textBaseline = 'top'; - context.textAlign = 'center'; - var leftRight = (0.5 - align); - var x = align * label.width / scale + leftRight * strokeWidth; - var i; - if (stroke) { - for (i = 0; i < numLines; ++i) { - context.strokeText(lines[i], x + leftRight * widths[i], 0.5 * strokeWidth + i * lineHeight); - } - } - if (fill) { - for (i = 0; i < numLines; ++i) { - context.fillText(lines[i], x + leftRight * widths[i], 0.5 * strokeWidth + i * lineHeight); - } - } - } - return ol.render.canvas.TextReplay.labelCache_.get(key); -}; - - -/** - * @private - * @param {HTMLCanvasElement} label Label. - * @param {number} begin Begin. - * @param {number} end End. - */ -ol.render.canvas.TextReplay.prototype.drawTextImage_ = function(label, begin, end) { - var textState = this.textState_; - var strokeState = this.textStrokeState_; - var pixelRatio = this.pixelRatio; - var align = ol.render.replay.TEXT_ALIGN[textState.textAlign || ol.render.canvas.defaultTextAlign]; - var baseline = ol.render.replay.TEXT_ALIGN[textState.textBaseline]; - var strokeWidth = strokeState && strokeState.lineWidth ? strokeState.lineWidth : 0; - - var anchorX = align * label.width / pixelRatio + 2 * (0.5 - align) * strokeWidth; - var anchorY = baseline * label.height / pixelRatio + 2 * (0.5 - baseline) * strokeWidth; - this.instructions.push([ol.render.canvas.Instruction.DRAW_IMAGE, begin, end, - label, (anchorX - this.textOffsetX_) * pixelRatio, (anchorY - this.textOffsetY_) * pixelRatio, - label.height, 1, 0, 0, this.textRotateWithView_, this.textRotation_, - 1, true, label.width - ]); - this.hitDetectionInstructions.push([ol.render.canvas.Instruction.DRAW_IMAGE, begin, end, - label, (anchorX - this.textOffsetX_) * pixelRatio, (anchorY - this.textOffsetY_) * pixelRatio, - label.height, 1, 0, 0, this.textRotateWithView_, this.textRotation_, - 1 / pixelRatio, true, label.width - ]); -}; - - -/** - * @private - * @param {number} begin Begin. - * @param {number} end End. - */ -ol.render.canvas.TextReplay.prototype.drawChars_ = function(begin, end) { - var pixelRatio = this.pixelRatio; - var strokeState = this.textStrokeState_; - var fill = !!this.textFillState_; - var stroke = !!strokeState; - var textState = this.textState_; - var baseline = ol.render.replay.TEXT_ALIGN[textState.textBaseline]; - - var labels = []; - var text = this.text_; - var numChars = this.text_.length; - var i; - - if (stroke) { - for (i = 0; i < numChars; ++i) { - labels.push(this.getImage_(text.charAt(i), false, stroke)); - } - } - if (fill) { - for (i = 0; i < numChars; ++i) { - labels.push(this.getImage_(text.charAt(i), fill, false)); - } - } - - var context = labels[0].getContext('2d'); - var offsetY = this.textOffsetY_ * pixelRatio; - var align = ol.render.replay.TEXT_ALIGN[textState.textAlign || ol.render.canvas.defaultTextAlign]; - var widths = {}; - this.instructions.push([ol.render.canvas.Instruction.DRAW_CHARS, - begin, end, labels, baseline, - textState.exceedLength, textState.maxAngle, - ol.render.canvas.TextReplay.getTextWidth.bind(widths, context, pixelRatio * this.textScale_), - offsetY, this.text_, align, 1 - ]); - this.hitDetectionInstructions.push([ol.render.canvas.Instruction.DRAW_CHARS, - begin, end, labels, baseline, - textState.exceedLength, textState.maxAngle, - ol.render.canvas.TextReplay.getTextWidth.bind(widths, context, this.textScale_), - offsetY, this.text_, align, 1 / pixelRatio - ]); -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.TextReplay.prototype.setTextStyle = function(textStyle) { - var textState, fillState, strokeState; - if (!textStyle) { - this.text_ = ''; - } else { - var textFillStyle = textStyle.getFill(); - if (!textFillStyle) { - fillState = this.textFillState_ = null; - } else { - var textFillStyleColor = textFillStyle.getColor(); - var fillStyle = ol.colorlike.asColorLike(textFillStyleColor ? - textFillStyleColor : ol.render.canvas.defaultFillStyle); - fillState = this.textFillState_; - if (!fillState) { - fillState = this.textFillState_ = /** @type {ol.CanvasFillState} */ ({}); - } - fillState.fillStyle = fillStyle; - } - var textStrokeStyle = textStyle.getStroke(); - if (!textStrokeStyle) { - strokeState = this.textStrokeState_ = null; - } else { - var textStrokeStyleColor = textStrokeStyle.getColor(); - var textStrokeStyleLineCap = textStrokeStyle.getLineCap(); - var textStrokeStyleLineDash = textStrokeStyle.getLineDash(); - var textStrokeStyleLineDashOffset = textStrokeStyle.getLineDashOffset(); - var textStrokeStyleLineJoin = textStrokeStyle.getLineJoin(); - var textStrokeStyleWidth = textStrokeStyle.getWidth(); - var textStrokeStyleMiterLimit = textStrokeStyle.getMiterLimit(); - var lineCap = textStrokeStyleLineCap !== undefined ? - textStrokeStyleLineCap : ol.render.canvas.defaultLineCap; - var lineDash = textStrokeStyleLineDash ? - textStrokeStyleLineDash.slice() : ol.render.canvas.defaultLineDash; - var lineDashOffset = textStrokeStyleLineDashOffset !== undefined ? - textStrokeStyleLineDashOffset : ol.render.canvas.defaultLineDashOffset; - var lineJoin = textStrokeStyleLineJoin !== undefined ? - textStrokeStyleLineJoin : ol.render.canvas.defaultLineJoin; - var lineWidth = textStrokeStyleWidth !== undefined ? - textStrokeStyleWidth : ol.render.canvas.defaultLineWidth; - var miterLimit = textStrokeStyleMiterLimit !== undefined ? - textStrokeStyleMiterLimit : ol.render.canvas.defaultMiterLimit; - var strokeStyle = ol.colorlike.asColorLike(textStrokeStyleColor ? - textStrokeStyleColor : ol.render.canvas.defaultStrokeStyle); - strokeState = this.textStrokeState_; - if (!strokeState) { - strokeState = this.textStrokeState_ = /** @type {ol.CanvasStrokeState} */ ({}); - } - strokeState.lineCap = lineCap; - strokeState.lineDash = lineDash; - strokeState.lineDashOffset = lineDashOffset; - strokeState.lineJoin = lineJoin; - strokeState.lineWidth = lineWidth; - strokeState.miterLimit = miterLimit; - strokeState.strokeStyle = strokeStyle; - } - var textFont = textStyle.getFont(); - var textOffsetX = textStyle.getOffsetX(); - var textOffsetY = textStyle.getOffsetY(); - var textRotateWithView = textStyle.getRotateWithView(); - var textRotation = textStyle.getRotation(); - var textScale = textStyle.getScale(); - var textText = textStyle.getText(); - var textTextAlign = textStyle.getTextAlign(); - var textTextBaseline = textStyle.getTextBaseline(); - var font = textFont !== undefined ? - textFont : ol.render.canvas.defaultFont; - var textAlign = textTextAlign; - var textBaseline = textTextBaseline !== undefined ? - textTextBaseline : ol.render.canvas.defaultTextBaseline; - textState = this.textState_; - if (!textState) { - textState = this.textState_ = /** @type {ol.CanvasTextState} */ ({}); - } - textState.exceedLength = textStyle.getExceedLength(); - textState.font = font; - textState.maxAngle = textStyle.getMaxAngle(); - textState.placement = textStyle.getPlacement(); - textState.textAlign = textAlign; - textState.textBaseline = textBaseline; - - this.text_ = textText !== undefined ? textText : ''; - this.textOffsetX_ = textOffsetX !== undefined ? textOffsetX : 0; - this.textOffsetY_ = textOffsetY !== undefined ? textOffsetY : 0; - this.textRotateWithView_ = textRotateWithView !== undefined ? textRotateWithView : false; - this.textRotation_ = textRotation !== undefined ? textRotation : 0; - this.textScale_ = textScale !== undefined ? textScale : 1; - - this.strokeKey_ = strokeState ? - (typeof strokeState.strokeStyle == 'string' ? strokeState.strokeStyle : ol.getUid(strokeState.strokeStyle)) + - strokeState.lineCap + strokeState.lineDashOffset + '|' + strokeState.lineWidth + - strokeState.lineJoin + strokeState.miterLimit + '[' + strokeState.lineDash.join() + ']' : - ''; - this.textKey_ = textState.font + (textState.textAlign || '?') + this.textScale_; - this.fillKey_ = fillState ? - (typeof fillState.fillStyle == 'string' ? fillState.fillStyle : ('|' + ol.getUid(fillState.fillStyle))) : - ''; - } -}; - -goog.provide('ol.render.canvas.ReplayGroup'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.dom'); -goog.require('ol.extent'); -goog.require('ol.geom.flat.transform'); -goog.require('ol.obj'); -goog.require('ol.render.ReplayGroup'); -goog.require('ol.render.canvas.Replay'); -goog.require('ol.render.canvas.ImageReplay'); -goog.require('ol.render.canvas.LineStringReplay'); -goog.require('ol.render.canvas.PolygonReplay'); -goog.require('ol.render.canvas.TextReplay'); -goog.require('ol.render.replay'); -goog.require('ol.transform'); - - -/** - * @constructor - * @extends {ol.render.ReplayGroup} - * @param {number} tolerance Tolerance. - * @param {ol.Extent} maxExtent Max extent. - * @param {number} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @param {boolean} overlaps The replay group can have overlapping geometries. - * @param {number=} opt_renderBuffer Optional rendering buffer. - * @struct - */ -ol.render.canvas.ReplayGroup = function( - tolerance, maxExtent, resolution, pixelRatio, overlaps, opt_renderBuffer) { - ol.render.ReplayGroup.call(this); - - /** - * @private - * @type {number} - */ - this.tolerance_ = tolerance; - - /** - * @private - * @type {ol.Extent} - */ - this.maxExtent_ = maxExtent; - - /** - * @private - * @type {boolean} - */ - this.overlaps_ = overlaps; - - /** - * @private - * @type {number} - */ - this.pixelRatio_ = pixelRatio; - - /** - * @private - * @type {number} - */ - this.resolution_ = resolution; - - /** - * @private - * @type {number|undefined} - */ - this.renderBuffer_ = opt_renderBuffer; - - /** - * @private - * @type {!Object.<string, - * Object.<ol.render.ReplayType, ol.render.canvas.Replay>>} - */ - this.replaysByZIndex_ = {}; - - /** - * @private - * @type {CanvasRenderingContext2D} - */ - this.hitDetectionContext_ = ol.dom.createCanvasContext2D(1, 1); - - /** - * @private - * @type {ol.Transform} - */ - this.hitDetectionTransform_ = ol.transform.create(); -}; -ol.inherits(ol.render.canvas.ReplayGroup, ol.render.ReplayGroup); - - -/** - * This cache is used for storing calculated pixel circles for increasing performance. - * It is a static property to allow each Replaygroup to access it. - * @type {Object.<number, Array.<Array.<(boolean|undefined)>>>} - * @private - */ -ol.render.canvas.ReplayGroup.circleArrayCache_ = { - 0: [[true]] -}; - - -/** - * This method fills a row in the array from the given coordinate to the - * middle with `true`. - * @param {Array.<Array.<(boolean|undefined)>>} array The array that will be altered. - * @param {number} x X coordinate. - * @param {number} y Y coordinate. - * @private - */ -ol.render.canvas.ReplayGroup.fillCircleArrayRowToMiddle_ = function(array, x, y) { - var i; - var radius = Math.floor(array.length / 2); - if (x >= radius) { - for (i = radius; i < x; i++) { - array[i][y] = true; - } - } else if (x < radius) { - for (i = x + 1; i < radius; i++) { - array[i][y] = true; - } - } -}; - - -/** - * This methods creates a circle inside a fitting array. Points inside the - * circle are marked by true, points on the outside are undefined. - * It uses the midpoint circle algorithm. - * A cache is used to increase performance. - * @param {number} radius Radius. - * @returns {Array.<Array.<(boolean|undefined)>>} An array with marked circle points. - * @private - */ -ol.render.canvas.ReplayGroup.getCircleArray_ = function(radius) { - if (ol.render.canvas.ReplayGroup.circleArrayCache_[radius] !== undefined) { - return ol.render.canvas.ReplayGroup.circleArrayCache_[radius]; - } - - var arraySize = radius * 2 + 1; - var arr = new Array(arraySize); - for (var i = 0; i < arraySize; i++) { - arr[i] = new Array(arraySize); - } - - var x = radius; - var y = 0; - var error = 0; - - while (x >= y) { - ol.render.canvas.ReplayGroup.fillCircleArrayRowToMiddle_(arr, radius + x, radius + y); - ol.render.canvas.ReplayGroup.fillCircleArrayRowToMiddle_(arr, radius + y, radius + x); - ol.render.canvas.ReplayGroup.fillCircleArrayRowToMiddle_(arr, radius - y, radius + x); - ol.render.canvas.ReplayGroup.fillCircleArrayRowToMiddle_(arr, radius - x, radius + y); - ol.render.canvas.ReplayGroup.fillCircleArrayRowToMiddle_(arr, radius - x, radius - y); - ol.render.canvas.ReplayGroup.fillCircleArrayRowToMiddle_(arr, radius - y, radius - x); - ol.render.canvas.ReplayGroup.fillCircleArrayRowToMiddle_(arr, radius + y, radius - x); - ol.render.canvas.ReplayGroup.fillCircleArrayRowToMiddle_(arr, radius + x, radius - y); - - y++; - error += 1 + 2 * y; - if (2 * (error - x) + 1 > 0) { - x -= 1; - error += 1 - 2 * x; - } - } - - ol.render.canvas.ReplayGroup.circleArrayCache_[radius] = arr; - return arr; -}; - - -/** - * @param {Array.<ol.render.ReplayType>} replays Replays. - * @return {boolean} Has replays of the provided types. - */ -ol.render.canvas.ReplayGroup.prototype.hasReplays = function(replays) { - for (var zIndex in this.replaysByZIndex_) { - var candidates = this.replaysByZIndex_[zIndex]; - for (var i = 0, ii = replays.length; i < ii; ++i) { - if (replays[i] in candidates) { - return true; - } - } - } - return false; -}; - - -/** - * FIXME empty description for jsdoc - */ -ol.render.canvas.ReplayGroup.prototype.finish = function() { - var zKey; - for (zKey in this.replaysByZIndex_) { - var replays = this.replaysByZIndex_[zKey]; - var replayKey; - for (replayKey in replays) { - replays[replayKey].finish(); - } - } -}; - - -/** - * @param {ol.Coordinate} coordinate Coordinate. - * @param {number} resolution Resolution. - * @param {number} rotation Rotation. - * @param {number} hitTolerance Hit tolerance in pixels. - * @param {Object.<string, boolean>} skippedFeaturesHash Ids of features - * to skip. - * @param {function((ol.Feature|ol.render.Feature)): T} callback Feature - * callback. - * @return {T|undefined} Callback result. - * @template T - */ -ol.render.canvas.ReplayGroup.prototype.forEachFeatureAtCoordinate = function( - coordinate, resolution, rotation, hitTolerance, skippedFeaturesHash, callback) { - - hitTolerance = Math.round(hitTolerance); - var contextSize = hitTolerance * 2 + 1; - var transform = ol.transform.compose(this.hitDetectionTransform_, - hitTolerance + 0.5, hitTolerance + 0.5, - 1 / resolution, -1 / resolution, - -rotation, - -coordinate[0], -coordinate[1]); - var context = this.hitDetectionContext_; - - if (context.canvas.width !== contextSize || context.canvas.height !== contextSize) { - context.canvas.width = contextSize; - context.canvas.height = contextSize; - } else { - context.clearRect(0, 0, contextSize, contextSize); - } - - /** - * @type {ol.Extent} - */ - var hitExtent; - if (this.renderBuffer_ !== undefined) { - hitExtent = ol.extent.createEmpty(); - ol.extent.extendCoordinate(hitExtent, coordinate); - ol.extent.buffer(hitExtent, resolution * (this.renderBuffer_ + hitTolerance), hitExtent); - } - - var mask = ol.render.canvas.ReplayGroup.getCircleArray_(hitTolerance); - - return this.replayHitDetection_(context, transform, rotation, - skippedFeaturesHash, - /** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @return {?} Callback result. - */ - function(feature) { - var imageData = context.getImageData(0, 0, contextSize, contextSize).data; - for (var i = 0; i < contextSize; i++) { - for (var j = 0; j < contextSize; j++) { - if (mask[i][j]) { - if (imageData[(j * contextSize + i) * 4 + 3] > 0) { - var result = callback(feature); - if (result) { - return result; - } else { - context.clearRect(0, 0, contextSize, contextSize); - return undefined; - } - } - } - } - } - }, hitExtent); -}; - - -/** - * @param {ol.Transform} transform Transform. - * @return {Array.<number>} Clip coordinates. - */ -ol.render.canvas.ReplayGroup.prototype.getClipCoords = function(transform) { - var maxExtent = this.maxExtent_; - var minX = maxExtent[0]; - var minY = maxExtent[1]; - var maxX = maxExtent[2]; - var maxY = maxExtent[3]; - var flatClipCoords = [minX, minY, minX, maxY, maxX, maxY, maxX, minY]; - ol.geom.flat.transform.transform2D( - flatClipCoords, 0, 8, 2, transform, flatClipCoords); - return flatClipCoords; -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.ReplayGroup.prototype.getReplay = function(zIndex, replayType) { - var zIndexKey = zIndex !== undefined ? zIndex.toString() : '0'; - var replays = this.replaysByZIndex_[zIndexKey]; - if (replays === undefined) { - replays = {}; - this.replaysByZIndex_[zIndexKey] = replays; - } - var replay = replays[replayType]; - if (replay === undefined) { - var Constructor = ol.render.canvas.ReplayGroup.BATCH_CONSTRUCTORS_[replayType]; - replay = new Constructor(this.tolerance_, this.maxExtent_, - this.resolution_, this.pixelRatio_, this.overlaps_); - replays[replayType] = replay; - } - return replay; -}; - - -/** - * @inheritDoc - */ -ol.render.canvas.ReplayGroup.prototype.isEmpty = function() { - return ol.obj.isEmpty(this.replaysByZIndex_); -}; - - -/** - * @param {CanvasRenderingContext2D} context Context. - * @param {ol.Transform} transform Transform. - * @param {number} viewRotation View rotation. - * @param {Object.<string, boolean>} skippedFeaturesHash Ids of features - * to skip. - * @param {Array.<ol.render.ReplayType>=} opt_replayTypes Ordered replay types - * to replay. Default is {@link ol.render.replay.ORDER} - */ -ol.render.canvas.ReplayGroup.prototype.replay = function(context, - transform, viewRotation, skippedFeaturesHash, opt_replayTypes) { - - /** @type {Array.<number>} */ - var zs = Object.keys(this.replaysByZIndex_).map(Number); - zs.sort(ol.array.numberSafeCompareFunction); - - // setup clipping so that the parts of over-simplified geometries are not - // visible outside the current extent when panning - var flatClipCoords = this.getClipCoords(transform); - context.save(); - context.beginPath(); - context.moveTo(flatClipCoords[0], flatClipCoords[1]); - context.lineTo(flatClipCoords[2], flatClipCoords[3]); - context.lineTo(flatClipCoords[4], flatClipCoords[5]); - context.lineTo(flatClipCoords[6], flatClipCoords[7]); - context.clip(); - - var replayTypes = opt_replayTypes ? opt_replayTypes : ol.render.replay.ORDER; - var i, ii, j, jj, replays, replay; - for (i = 0, ii = zs.length; i < ii; ++i) { - replays = this.replaysByZIndex_[zs[i].toString()]; - for (j = 0, jj = replayTypes.length; j < jj; ++j) { - replay = replays[replayTypes[j]]; - if (replay !== undefined) { - replay.replay(context, transform, viewRotation, skippedFeaturesHash); - } - } - } - - context.restore(); -}; - - -/** - * @private - * @param {CanvasRenderingContext2D} context Context. - * @param {ol.Transform} transform Transform. - * @param {number} viewRotation View rotation. - * @param {Object.<string, boolean>} skippedFeaturesHash Ids of features - * to skip. - * @param {function((ol.Feature|ol.render.Feature)): T} featureCallback - * Feature callback. - * @param {ol.Extent=} opt_hitExtent Only check features that intersect this - * extent. - * @return {T|undefined} Callback result. - * @template T - */ -ol.render.canvas.ReplayGroup.prototype.replayHitDetection_ = function( - context, transform, viewRotation, skippedFeaturesHash, - featureCallback, opt_hitExtent) { - /** @type {Array.<number>} */ - var zs = Object.keys(this.replaysByZIndex_).map(Number); - zs.sort(function(a, b) { - return b - a; - }); - - var i, ii, j, replays, replay, result; - for (i = 0, ii = zs.length; i < ii; ++i) { - replays = this.replaysByZIndex_[zs[i].toString()]; - for (j = ol.render.replay.ORDER.length - 1; j >= 0; --j) { - replay = replays[ol.render.replay.ORDER[j]]; - if (replay !== undefined) { - result = replay.replayHitDetection(context, transform, viewRotation, - skippedFeaturesHash, featureCallback, opt_hitExtent); - if (result) { - return result; - } - } - } - } - return undefined; -}; - - -/** - * @const - * @private - * @type {Object.<ol.render.ReplayType, - * function(new: ol.render.canvas.Replay, number, ol.Extent, - * number, number, boolean)>} - */ -ol.render.canvas.ReplayGroup.BATCH_CONSTRUCTORS_ = { - 'Circle': ol.render.canvas.PolygonReplay, - 'Default': ol.render.canvas.Replay, - 'Image': ol.render.canvas.ImageReplay, - 'LineString': ol.render.canvas.LineStringReplay, - 'Polygon': ol.render.canvas.PolygonReplay, - 'Text': ol.render.canvas.TextReplay -}; - -goog.provide('ol.renderer.vector'); - -goog.require('ol'); -goog.require('ol.ImageState'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.render.ReplayType'); - - -/** - * @param {ol.Feature|ol.render.Feature} feature1 Feature 1. - * @param {ol.Feature|ol.render.Feature} feature2 Feature 2. - * @return {number} Order. - */ -ol.renderer.vector.defaultOrder = function(feature1, feature2) { - return ol.getUid(feature1) - ol.getUid(feature2); -}; - - -/** - * @param {number} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @return {number} Squared pixel tolerance. - */ -ol.renderer.vector.getSquaredTolerance = function(resolution, pixelRatio) { - var tolerance = ol.renderer.vector.getTolerance(resolution, pixelRatio); - return tolerance * tolerance; -}; - - -/** - * @param {number} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @return {number} Pixel tolerance. - */ -ol.renderer.vector.getTolerance = function(resolution, pixelRatio) { - return ol.SIMPLIFY_TOLERANCE * resolution / pixelRatio; -}; - - -/** - * @param {ol.render.ReplayGroup} replayGroup Replay group. - * @param {ol.geom.Circle} geometry Geometry. - * @param {ol.style.Style} style Style. - * @param {ol.Feature} feature Feature. - * @private - */ -ol.renderer.vector.renderCircleGeometry_ = function(replayGroup, geometry, style, feature) { - var fillStyle = style.getFill(); - var strokeStyle = style.getStroke(); - if (fillStyle || strokeStyle) { - var circleReplay = replayGroup.getReplay( - style.getZIndex(), ol.render.ReplayType.CIRCLE); - circleReplay.setFillStrokeStyle(fillStyle, strokeStyle); - circleReplay.drawCircle(geometry, feature); - } - var textStyle = style.getText(); - if (textStyle) { - var textReplay = replayGroup.getReplay( - style.getZIndex(), ol.render.ReplayType.TEXT); - textReplay.setTextStyle(textStyle); - textReplay.drawText(geometry, feature); - } -}; - - -/** - * @param {ol.render.ReplayGroup} replayGroup Replay group. - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @param {ol.style.Style} style Style. - * @param {number} squaredTolerance Squared tolerance. - * @param {function(this: T, ol.events.Event)} listener Listener function. - * @param {T} thisArg Value to use as `this` when executing `listener`. - * @return {boolean} `true` if style is loading. - * @template T - */ -ol.renderer.vector.renderFeature = function( - replayGroup, feature, style, squaredTolerance, listener, thisArg) { - var loading = false; - var imageStyle, imageState; - imageStyle = style.getImage(); - if (imageStyle) { - imageState = imageStyle.getImageState(); - if (imageState == ol.ImageState.LOADED || - imageState == ol.ImageState.ERROR) { - imageStyle.unlistenImageChange(listener, thisArg); - } else { - if (imageState == ol.ImageState.IDLE) { - imageStyle.load(); - } - imageState = imageStyle.getImageState(); - imageStyle.listenImageChange(listener, thisArg); - loading = true; - } - } - ol.renderer.vector.renderFeature_(replayGroup, feature, style, - squaredTolerance); - return loading; -}; - - -/** - * @param {ol.render.ReplayGroup} replayGroup Replay group. - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @param {ol.style.Style} style Style. - * @param {number} squaredTolerance Squared tolerance. - * @private - */ -ol.renderer.vector.renderFeature_ = function( - replayGroup, feature, style, squaredTolerance) { - var geometry = style.getGeometryFunction()(feature); - if (!geometry) { - return; - } - var simplifiedGeometry = geometry.getSimplifiedGeometry(squaredTolerance); - var renderer = style.getRenderer(); - if (renderer) { - ol.renderer.vector.renderGeometry_(replayGroup, simplifiedGeometry, style, feature); - } else { - var geometryRenderer = - ol.renderer.vector.GEOMETRY_RENDERERS_[simplifiedGeometry.getType()]; - geometryRenderer(replayGroup, simplifiedGeometry, style, feature); - } -}; - - -/** - * @param {ol.render.ReplayGroup} replayGroup Replay group. - * @param {ol.geom.Geometry} geometry Geometry. - * @param {ol.style.Style} style Style. - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @private - */ -ol.renderer.vector.renderGeometry_ = function(replayGroup, geometry, style, feature) { - if (geometry.getType() == ol.geom.GeometryType.GEOMETRY_COLLECTION) { - var geometries = /** @type {ol.geom.GeometryCollection} */ (geometry).getGeometries(); - for (var i = 0, ii = geometries.length; i < ii; ++i) { - ol.renderer.vector.renderGeometry_(replayGroup, geometries[i], style, feature); - } - return; - } - var replay = replayGroup.getReplay(style.getZIndex(), ol.render.ReplayType.DEFAULT); - replay.drawCustom(/** @type {ol.geom.SimpleGeometry} */ (geometry), feature, style.getRenderer()); -}; - - -/** - * @param {ol.render.ReplayGroup} replayGroup Replay group. - * @param {ol.geom.GeometryCollection} geometry Geometry. - * @param {ol.style.Style} style Style. - * @param {ol.Feature} feature Feature. - * @private - */ -ol.renderer.vector.renderGeometryCollectionGeometry_ = function(replayGroup, geometry, style, feature) { - var geometries = geometry.getGeometriesArray(); - var i, ii; - for (i = 0, ii = geometries.length; i < ii; ++i) { - var geometryRenderer = - ol.renderer.vector.GEOMETRY_RENDERERS_[geometries[i].getType()]; - geometryRenderer(replayGroup, geometries[i], style, feature); - } -}; - - -/** - * @param {ol.render.ReplayGroup} replayGroup Replay group. - * @param {ol.geom.LineString|ol.render.Feature} geometry Geometry. - * @param {ol.style.Style} style Style. - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @private - */ -ol.renderer.vector.renderLineStringGeometry_ = function(replayGroup, geometry, style, feature) { - var strokeStyle = style.getStroke(); - if (strokeStyle) { - var lineStringReplay = replayGroup.getReplay( - style.getZIndex(), ol.render.ReplayType.LINE_STRING); - lineStringReplay.setFillStrokeStyle(null, strokeStyle); - lineStringReplay.drawLineString(geometry, feature); - } - var textStyle = style.getText(); - if (textStyle) { - var textReplay = replayGroup.getReplay( - style.getZIndex(), ol.render.ReplayType.TEXT); - textReplay.setTextStyle(textStyle); - textReplay.drawText(geometry, feature); - } -}; - - -/** - * @param {ol.render.ReplayGroup} replayGroup Replay group. - * @param {ol.geom.MultiLineString|ol.render.Feature} geometry Geometry. - * @param {ol.style.Style} style Style. - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @private - */ -ol.renderer.vector.renderMultiLineStringGeometry_ = function(replayGroup, geometry, style, feature) { - var strokeStyle = style.getStroke(); - if (strokeStyle) { - var lineStringReplay = replayGroup.getReplay( - style.getZIndex(), ol.render.ReplayType.LINE_STRING); - lineStringReplay.setFillStrokeStyle(null, strokeStyle); - lineStringReplay.drawMultiLineString(geometry, feature); - } - var textStyle = style.getText(); - if (textStyle) { - var textReplay = replayGroup.getReplay( - style.getZIndex(), ol.render.ReplayType.TEXT); - textReplay.setTextStyle(textStyle); - textReplay.drawText(geometry, feature); - } -}; - - -/** - * @param {ol.render.ReplayGroup} replayGroup Replay group. - * @param {ol.geom.MultiPolygon} geometry Geometry. - * @param {ol.style.Style} style Style. - * @param {ol.Feature} feature Feature. - * @private - */ -ol.renderer.vector.renderMultiPolygonGeometry_ = function(replayGroup, geometry, style, feature) { - var fillStyle = style.getFill(); - var strokeStyle = style.getStroke(); - if (strokeStyle || fillStyle) { - var polygonReplay = replayGroup.getReplay( - style.getZIndex(), ol.render.ReplayType.POLYGON); - polygonReplay.setFillStrokeStyle(fillStyle, strokeStyle); - polygonReplay.drawMultiPolygon(geometry, feature); - } - var textStyle = style.getText(); - if (textStyle) { - var textReplay = replayGroup.getReplay( - style.getZIndex(), ol.render.ReplayType.TEXT); - textReplay.setTextStyle(textStyle); - textReplay.drawText(geometry, feature); - } -}; - - -/** - * @param {ol.render.ReplayGroup} replayGroup Replay group. - * @param {ol.geom.Point|ol.render.Feature} geometry Geometry. - * @param {ol.style.Style} style Style. - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @private - */ -ol.renderer.vector.renderPointGeometry_ = function(replayGroup, geometry, style, feature) { - var imageStyle = style.getImage(); - if (imageStyle) { - if (imageStyle.getImageState() != ol.ImageState.LOADED) { - return; - } - var imageReplay = replayGroup.getReplay( - style.getZIndex(), ol.render.ReplayType.IMAGE); - imageReplay.setImageStyle(imageStyle); - imageReplay.drawPoint(geometry, feature); - } - var textStyle = style.getText(); - if (textStyle) { - var textReplay = replayGroup.getReplay( - style.getZIndex(), ol.render.ReplayType.TEXT); - textReplay.setTextStyle(textStyle); - textReplay.drawText(geometry, feature); - } -}; - - -/** - * @param {ol.render.ReplayGroup} replayGroup Replay group. - * @param {ol.geom.MultiPoint|ol.render.Feature} geometry Geometry. - * @param {ol.style.Style} style Style. - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @private - */ -ol.renderer.vector.renderMultiPointGeometry_ = function(replayGroup, geometry, style, feature) { - var imageStyle = style.getImage(); - if (imageStyle) { - if (imageStyle.getImageState() != ol.ImageState.LOADED) { - return; - } - var imageReplay = replayGroup.getReplay( - style.getZIndex(), ol.render.ReplayType.IMAGE); - imageReplay.setImageStyle(imageStyle); - imageReplay.drawMultiPoint(geometry, feature); - } - var textStyle = style.getText(); - if (textStyle) { - var textReplay = replayGroup.getReplay( - style.getZIndex(), ol.render.ReplayType.TEXT); - textReplay.setTextStyle(textStyle); - textReplay.drawText(geometry, feature); - } -}; - - -/** - * @param {ol.render.ReplayGroup} replayGroup Replay group. - * @param {ol.geom.Polygon|ol.render.Feature} geometry Geometry. - * @param {ol.style.Style} style Style. - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @private - */ -ol.renderer.vector.renderPolygonGeometry_ = function(replayGroup, geometry, style, feature) { - var fillStyle = style.getFill(); - var strokeStyle = style.getStroke(); - if (fillStyle || strokeStyle) { - var polygonReplay = replayGroup.getReplay( - style.getZIndex(), ol.render.ReplayType.POLYGON); - polygonReplay.setFillStrokeStyle(fillStyle, strokeStyle); - polygonReplay.drawPolygon(geometry, feature); - } - var textStyle = style.getText(); - if (textStyle) { - var textReplay = replayGroup.getReplay( - style.getZIndex(), ol.render.ReplayType.TEXT); - textReplay.setTextStyle(textStyle); - textReplay.drawText(geometry, feature); - } -}; - - -/** - * @const - * @private - * @type {Object.<ol.geom.GeometryType, - * function(ol.render.ReplayGroup, ol.geom.Geometry, - * ol.style.Style, Object)>} - */ -ol.renderer.vector.GEOMETRY_RENDERERS_ = { - 'Point': ol.renderer.vector.renderPointGeometry_, - 'LineString': ol.renderer.vector.renderLineStringGeometry_, - 'Polygon': ol.renderer.vector.renderPolygonGeometry_, - 'MultiPoint': ol.renderer.vector.renderMultiPointGeometry_, - 'MultiLineString': ol.renderer.vector.renderMultiLineStringGeometry_, - 'MultiPolygon': ol.renderer.vector.renderMultiPolygonGeometry_, - 'GeometryCollection': ol.renderer.vector.renderGeometryCollectionGeometry_, - 'Circle': ol.renderer.vector.renderCircleGeometry_ -}; - -goog.provide('ol.renderer.canvas.VectorLayer'); - -goog.require('ol'); -goog.require('ol.LayerType'); -goog.require('ol.ViewHint'); -goog.require('ol.dom'); -goog.require('ol.extent'); -goog.require('ol.render.EventType'); -goog.require('ol.render.canvas'); -goog.require('ol.render.canvas.ReplayGroup'); -goog.require('ol.renderer.Type'); -goog.require('ol.renderer.canvas.Layer'); -goog.require('ol.renderer.vector'); - - -/** - * @constructor - * @extends {ol.renderer.canvas.Layer} - * @param {ol.layer.Vector} vectorLayer Vector layer. - * @api - */ -ol.renderer.canvas.VectorLayer = function(vectorLayer) { - - ol.renderer.canvas.Layer.call(this, vectorLayer); - - /** - * @private - * @type {boolean} - */ - this.dirty_ = false; - - /** - * @private - * @type {number} - */ - this.renderedRevision_ = -1; - - /** - * @private - * @type {number} - */ - this.renderedResolution_ = NaN; - - /** - * @private - * @type {ol.Extent} - */ - this.renderedExtent_ = ol.extent.createEmpty(); - - /** - * @private - * @type {function(ol.Feature, ol.Feature): number|null} - */ - this.renderedRenderOrder_ = null; - - /** - * @private - * @type {ol.render.canvas.ReplayGroup} - */ - this.replayGroup_ = null; - - /** - * @private - * @type {CanvasRenderingContext2D} - */ - this.context_ = ol.dom.createCanvasContext2D(); - -}; -ol.inherits(ol.renderer.canvas.VectorLayer, ol.renderer.canvas.Layer); - - -/** - * Determine if this renderer handles the provided layer. - * @param {ol.renderer.Type} type The renderer type. - * @param {ol.layer.Layer} layer The candidate layer. - * @return {boolean} The renderer can render the layer. - */ -ol.renderer.canvas.VectorLayer['handles'] = function(type, layer) { - return type === ol.renderer.Type.CANVAS && layer.getType() === ol.LayerType.VECTOR; -}; - - -/** - * Create a layer renderer. - * @param {ol.renderer.Map} mapRenderer The map renderer. - * @param {ol.layer.Layer} layer The layer to be rendererd. - * @return {ol.renderer.canvas.VectorLayer} The layer renderer. - */ -ol.renderer.canvas.VectorLayer['create'] = function(mapRenderer, layer) { - return new ol.renderer.canvas.VectorLayer(/** @type {ol.layer.Vector} */ (layer)); -}; - - -/** - * @inheritDoc - */ -ol.renderer.canvas.VectorLayer.prototype.composeFrame = function(frameState, layerState, context) { - - var extent = frameState.extent; - var pixelRatio = frameState.pixelRatio; - var skippedFeatureUids = layerState.managed ? - frameState.skippedFeatureUids : {}; - var viewState = frameState.viewState; - var projection = viewState.projection; - var rotation = viewState.rotation; - var projectionExtent = projection.getExtent(); - var vectorSource = /** @type {ol.source.Vector} */ (this.getLayer().getSource()); - - var transform = this.getTransform(frameState, 0); - - this.preCompose(context, frameState, transform); - - // clipped rendering if layer extent is set - var clipExtent = layerState.extent; - var clipped = clipExtent !== undefined; - if (clipped) { - this.clip(context, frameState, /** @type {ol.Extent} */ (clipExtent)); - } - var replayGroup = this.replayGroup_; - if (replayGroup && !replayGroup.isEmpty()) { - var layer = this.getLayer(); - var drawOffsetX = 0; - var drawOffsetY = 0; - var replayContext; - var transparentLayer = layerState.opacity !== 1; - var hasRenderListeners = layer.hasListener(ol.render.EventType.RENDER); - if (transparentLayer || hasRenderListeners) { - var drawWidth = context.canvas.width; - var drawHeight = context.canvas.height; - if (rotation) { - var drawSize = Math.round(Math.sqrt(drawWidth * drawWidth + drawHeight * drawHeight)); - drawOffsetX = (drawSize - drawWidth) / 2; - drawOffsetY = (drawSize - drawHeight) / 2; - drawWidth = drawHeight = drawSize; - } - // resize and clear - this.context_.canvas.width = drawWidth; - this.context_.canvas.height = drawHeight; - replayContext = this.context_; - } else { - replayContext = context; - } - - var alpha = replayContext.globalAlpha; - if (!transparentLayer) { - // for performance reasons, context.save / context.restore is not used - // to save and restore the transformation matrix and the opacity. - // see http://jsperf.com/context-save-restore-versus-variable - replayContext.globalAlpha = layerState.opacity; - } - - if (replayContext != context) { - replayContext.translate(drawOffsetX, drawOffsetY); - } - - var width = frameState.size[0] * pixelRatio; - var height = frameState.size[1] * pixelRatio; - ol.render.canvas.rotateAtOffset(replayContext, -rotation, - width / 2, height / 2); - replayGroup.replay(replayContext, transform, rotation, skippedFeatureUids); - if (vectorSource.getWrapX() && projection.canWrapX() && - !ol.extent.containsExtent(projectionExtent, extent)) { - var startX = extent[0]; - var worldWidth = ol.extent.getWidth(projectionExtent); - var world = 0; - var offsetX; - while (startX < projectionExtent[0]) { - --world; - offsetX = worldWidth * world; - transform = this.getTransform(frameState, offsetX); - replayGroup.replay(replayContext, transform, rotation, skippedFeatureUids); - startX += worldWidth; - } - world = 0; - startX = extent[2]; - while (startX > projectionExtent[2]) { - ++world; - offsetX = worldWidth * world; - transform = this.getTransform(frameState, offsetX); - replayGroup.replay(replayContext, transform, rotation, skippedFeatureUids); - startX -= worldWidth; - } - // restore original transform for render and compose events - transform = this.getTransform(frameState, 0); - } - ol.render.canvas.rotateAtOffset(replayContext, rotation, - width / 2, height / 2); - - if (replayContext != context) { - if (hasRenderListeners) { - this.dispatchRenderEvent(replayContext, frameState, transform); - } - if (transparentLayer) { - var mainContextAlpha = context.globalAlpha; - context.globalAlpha = layerState.opacity; - context.drawImage(replayContext.canvas, -drawOffsetX, -drawOffsetY); - context.globalAlpha = mainContextAlpha; - } else { - context.drawImage(replayContext.canvas, -drawOffsetX, -drawOffsetY); - } - replayContext.translate(-drawOffsetX, -drawOffsetY); - } - - if (!transparentLayer) { - replayContext.globalAlpha = alpha; - } - } - - if (clipped) { - context.restore(); - } - this.postCompose(context, frameState, layerState, transform); - -}; - - -/** - * @inheritDoc - */ -ol.renderer.canvas.VectorLayer.prototype.forEachFeatureAtCoordinate = function(coordinate, frameState, hitTolerance, callback, thisArg) { - if (!this.replayGroup_) { - return undefined; - } else { - var resolution = frameState.viewState.resolution; - var rotation = frameState.viewState.rotation; - var layer = this.getLayer(); - /** @type {Object.<string, boolean>} */ - var features = {}; - return this.replayGroup_.forEachFeatureAtCoordinate(coordinate, resolution, - rotation, hitTolerance, {}, - /** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @return {?} Callback result. - */ - function(feature) { - var key = ol.getUid(feature).toString(); - if (!(key in features)) { - features[key] = true; - return callback.call(thisArg, feature, layer); - } - }); - } -}; - - -/** - * Handle changes in image style state. - * @param {ol.events.Event} event Image style change event. - * @private - */ -ol.renderer.canvas.VectorLayer.prototype.handleStyleImageChange_ = function(event) { - this.renderIfReadyAndVisible(); -}; - - -/** - * @inheritDoc - */ -ol.renderer.canvas.VectorLayer.prototype.prepareFrame = function(frameState, layerState) { - - var vectorLayer = /** @type {ol.layer.Vector} */ (this.getLayer()); - var vectorSource = vectorLayer.getSource(); - - this.updateAttributions( - frameState.attributions, vectorSource.getAttributions()); - this.updateLogos(frameState, vectorSource); - - var animating = frameState.viewHints[ol.ViewHint.ANIMATING]; - var interacting = frameState.viewHints[ol.ViewHint.INTERACTING]; - var updateWhileAnimating = vectorLayer.getUpdateWhileAnimating(); - var updateWhileInteracting = vectorLayer.getUpdateWhileInteracting(); - - if (!this.dirty_ && (!updateWhileAnimating && animating) || - (!updateWhileInteracting && interacting)) { - return true; - } - - var frameStateExtent = frameState.extent; - var viewState = frameState.viewState; - var projection = viewState.projection; - var resolution = viewState.resolution; - var pixelRatio = frameState.pixelRatio; - var vectorLayerRevision = vectorLayer.getRevision(); - var vectorLayerRenderBuffer = vectorLayer.getRenderBuffer(); - var vectorLayerRenderOrder = vectorLayer.getRenderOrder(); - - if (vectorLayerRenderOrder === undefined) { - vectorLayerRenderOrder = ol.renderer.vector.defaultOrder; - } - - var extent = ol.extent.buffer(frameStateExtent, - vectorLayerRenderBuffer * resolution); - var projectionExtent = viewState.projection.getExtent(); - - if (vectorSource.getWrapX() && viewState.projection.canWrapX() && - !ol.extent.containsExtent(projectionExtent, frameState.extent)) { - // For the replay group, we need an extent that intersects the real world - // (-180° to +180°). To support geometries in a coordinate range from -540° - // to +540°, we add at least 1 world width on each side of the projection - // extent. If the viewport is wider than the world, we need to add half of - // the viewport width to make sure we cover the whole viewport. - var worldWidth = ol.extent.getWidth(projectionExtent); - var buffer = Math.max(ol.extent.getWidth(extent) / 2, worldWidth); - extent[0] = projectionExtent[0] - buffer; - extent[2] = projectionExtent[2] + buffer; - } - - if (!this.dirty_ && - this.renderedResolution_ == resolution && - this.renderedRevision_ == vectorLayerRevision && - this.renderedRenderOrder_ == vectorLayerRenderOrder && - ol.extent.containsExtent(this.renderedExtent_, extent)) { - return true; - } - - this.replayGroup_ = null; - - this.dirty_ = false; - - var replayGroup = new ol.render.canvas.ReplayGroup( - ol.renderer.vector.getTolerance(resolution, pixelRatio), extent, resolution, - pixelRatio, vectorSource.getOverlaps(), vectorLayer.getRenderBuffer()); - vectorSource.loadFeatures(extent, resolution, projection); - /** - * @param {ol.Feature} feature Feature. - * @this {ol.renderer.canvas.VectorLayer} - */ - var renderFeature = function(feature) { - var styles; - var styleFunction = feature.getStyleFunction(); - if (styleFunction) { - styles = styleFunction.call(feature, resolution); - } else { - styleFunction = vectorLayer.getStyleFunction(); - if (styleFunction) { - styles = styleFunction(feature, resolution); - } - } - if (styles) { - var dirty = this.renderFeature( - feature, resolution, pixelRatio, styles, replayGroup); - this.dirty_ = this.dirty_ || dirty; - } - }.bind(this); - if (vectorLayerRenderOrder) { - /** @type {Array.<ol.Feature>} */ - var features = []; - vectorSource.forEachFeatureInExtent(extent, - /** - * @param {ol.Feature} feature Feature. - */ - function(feature) { - features.push(feature); - }, this); - features.sort(vectorLayerRenderOrder); - for (var i = 0, ii = features.length; i < ii; ++i) { - renderFeature(features[i]); - } - } else { - vectorSource.forEachFeatureInExtent(extent, renderFeature, this); - } - replayGroup.finish(); - - this.renderedResolution_ = resolution; - this.renderedRevision_ = vectorLayerRevision; - this.renderedRenderOrder_ = vectorLayerRenderOrder; - this.renderedExtent_ = extent; - this.replayGroup_ = replayGroup; - - return true; -}; - - -/** - * @param {ol.Feature} feature Feature. - * @param {number} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @param {(ol.style.Style|Array.<ol.style.Style>)} styles The style or array of - * styles. - * @param {ol.render.canvas.ReplayGroup} replayGroup Replay group. - * @return {boolean} `true` if an image is loading. - */ -ol.renderer.canvas.VectorLayer.prototype.renderFeature = function(feature, resolution, pixelRatio, styles, replayGroup) { - if (!styles) { - return false; - } - var loading = false; - if (Array.isArray(styles)) { - for (var i = 0, ii = styles.length; i < ii; ++i) { - loading = ol.renderer.vector.renderFeature( - replayGroup, feature, styles[i], - ol.renderer.vector.getSquaredTolerance(resolution, pixelRatio), - this.handleStyleImageChange_, this) || loading; - } - } else { - loading = ol.renderer.vector.renderFeature( - replayGroup, feature, styles, - ol.renderer.vector.getSquaredTolerance(resolution, pixelRatio), - this.handleStyleImageChange_, this) || loading; - } - return loading; -}; - -goog.provide('ol.layer.VectorTileRenderType'); - -/** - * @enum {string} - * Render mode for vector tiles: - * * `'image'`: Vector tiles are rendered as images. Great performance, but - * point symbols and texts are always rotated with the view and pixels are - * scaled during zoom animations. - * * `'hybrid'`: Polygon and line elements are rendered as images, so pixels - * are scaled during zoom animations. Point symbols and texts are accurately - * rendered as vectors and can stay upright on rotated views. - * * `'vector'`: Vector tiles are rendered as vectors. Most accurate rendering - * even during animations, but slower performance than the other options. - * @api - */ -ol.layer.VectorTileRenderType = { - IMAGE: 'image', - HYBRID: 'hybrid', - VECTOR: 'vector' -}; - -goog.provide('ol.renderer.canvas.VectorTileLayer'); - -goog.require('ol'); -goog.require('ol.LayerType'); -goog.require('ol.TileState'); -goog.require('ol.dom'); -goog.require('ol.extent'); -goog.require('ol.layer.VectorTileRenderType'); -goog.require('ol.proj'); -goog.require('ol.proj.Units'); -goog.require('ol.render.ReplayType'); -goog.require('ol.render.canvas'); -goog.require('ol.render.canvas.ReplayGroup'); -goog.require('ol.render.replay'); -goog.require('ol.renderer.Type'); -goog.require('ol.renderer.canvas.TileLayer'); -goog.require('ol.renderer.vector'); -goog.require('ol.transform'); - - -/** - * @constructor - * @extends {ol.renderer.canvas.TileLayer} - * @param {ol.layer.VectorTile} layer VectorTile layer. - * @api - */ -ol.renderer.canvas.VectorTileLayer = function(layer) { - - /** - * @type {CanvasRenderingContext2D} - */ - this.context = null; - - ol.renderer.canvas.TileLayer.call(this, layer); - - /** - * @private - * @type {boolean} - */ - this.dirty_ = false; - - /** - * @private - * @type {number} - */ - this.renderedLayerRevision_; - - /** - * @private - * @type {ol.Transform} - */ - this.tmpTransform_ = ol.transform.create(); - - // Use lower resolution for pure vector rendering. Closest resolution otherwise. - this.zDirection = - layer.getRenderMode() == ol.layer.VectorTileRenderType.VECTOR ? 1 : 0; - -}; -ol.inherits(ol.renderer.canvas.VectorTileLayer, ol.renderer.canvas.TileLayer); - - -/** - * Determine if this renderer handles the provided layer. - * @param {ol.renderer.Type} type The renderer type. - * @param {ol.layer.Layer} layer The candidate layer. - * @return {boolean} The renderer can render the layer. - */ -ol.renderer.canvas.VectorTileLayer['handles'] = function(type, layer) { - return type === ol.renderer.Type.CANVAS && layer.getType() === ol.LayerType.VECTOR_TILE; -}; - - -/** - * Create a layer renderer. - * @param {ol.renderer.Map} mapRenderer The map renderer. - * @param {ol.layer.Layer} layer The layer to be rendererd. - * @return {ol.renderer.canvas.VectorTileLayer} The layer renderer. - */ -ol.renderer.canvas.VectorTileLayer['create'] = function(mapRenderer, layer) { - return new ol.renderer.canvas.VectorTileLayer(/** @type {ol.layer.VectorTile} */ (layer)); -}; - - -/** - * @const - * @type {!Object.<string, Array.<ol.render.ReplayType>>} - */ -ol.renderer.canvas.VectorTileLayer.IMAGE_REPLAYS = { - 'image': [ol.render.ReplayType.POLYGON, ol.render.ReplayType.CIRCLE, - ol.render.ReplayType.LINE_STRING, ol.render.ReplayType.IMAGE, ol.render.ReplayType.TEXT], - 'hybrid': [ol.render.ReplayType.POLYGON, ol.render.ReplayType.LINE_STRING] -}; - - -/** - * @const - * @type {!Object.<string, Array.<ol.render.ReplayType>>} - */ -ol.renderer.canvas.VectorTileLayer.VECTOR_REPLAYS = { - 'image': [ol.render.ReplayType.DEFAULT], - 'hybrid': [ol.render.ReplayType.IMAGE, ol.render.ReplayType.TEXT, ol.render.ReplayType.DEFAULT], - 'vector': ol.render.replay.ORDER -}; - - -/** - * @inheritDoc - */ -ol.renderer.canvas.VectorTileLayer.prototype.prepareFrame = function(frameState, layerState) { - var layer = this.getLayer(); - var layerRevision = layer.getRevision(); - if (this.renderedLayerRevision_ != layerRevision) { - this.renderedTiles.length = 0; - var renderMode = layer.getRenderMode(); - if (!this.context && renderMode != ol.layer.VectorTileRenderType.VECTOR) { - this.context = ol.dom.createCanvasContext2D(); - } - if (this.context && renderMode == ol.layer.VectorTileRenderType.VECTOR) { - this.context = null; - } - } - this.renderedLayerRevision_ = layerRevision; - return ol.renderer.canvas.TileLayer.prototype.prepareFrame.apply(this, arguments); -}; - - -/** - * @param {ol.VectorImageTile} tile Tile. - * @param {olx.FrameState} frameState Frame state. - * @private - */ -ol.renderer.canvas.VectorTileLayer.prototype.createReplayGroup_ = function( - tile, frameState) { - var layer = this.getLayer(); - var pixelRatio = frameState.pixelRatio; - var projection = frameState.viewState.projection; - var revision = layer.getRevision(); - var renderOrder = /** @type {ol.RenderOrderFunction} */ - (layer.getRenderOrder()) || null; - - var replayState = tile.getReplayState(layer); - if (!replayState.dirty && replayState.renderedRevision == revision && - replayState.renderedRenderOrder == renderOrder) { - return; - } - - var source = /** @type {ol.source.VectorTile} */ (layer.getSource()); - var sourceTileGrid = source.getTileGrid(); - var tileGrid = source.getTileGridForProjection(projection); - var resolution = tileGrid.getResolution(tile.tileCoord[0]); - var tileExtent = tileGrid.getTileCoordExtent(tile.wrappedTileCoord); - - for (var t = 0, tt = tile.tileKeys.length; t < tt; ++t) { - var sourceTile = tile.getTile(tile.tileKeys[t]); - if (sourceTile.getState() == ol.TileState.ERROR) { - continue; - } - - var sourceTileCoord = sourceTile.tileCoord; - var sourceTileExtent = sourceTileGrid.getTileCoordExtent(sourceTileCoord); - var sharedExtent = ol.extent.getIntersection(tileExtent, sourceTileExtent); - var tileProjection = sourceTile.getProjection(); - var reproject = false; - if (!ol.proj.equivalent(projection, tileProjection)) { - reproject = true; - sourceTile.setProjection(projection); - } - replayState.dirty = false; - var replayGroup = new ol.render.canvas.ReplayGroup(0, sharedExtent, - resolution, pixelRatio, source.getOverlaps(), layer.getRenderBuffer()); - var squaredTolerance = ol.renderer.vector.getSquaredTolerance( - resolution, pixelRatio); - - /** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @this {ol.renderer.canvas.VectorTileLayer} - */ - var renderFeature = function(feature) { - var styles; - var styleFunction = feature.getStyleFunction(); - if (styleFunction) { - styles = styleFunction.call(/** @type {ol.Feature} */ (feature), resolution); - } else { - styleFunction = layer.getStyleFunction(); - if (styleFunction) { - styles = styleFunction(feature, resolution); - } - } - if (styles) { - var dirty = this.renderFeature(feature, squaredTolerance, styles, - replayGroup); - this.dirty_ = this.dirty_ || dirty; - replayState.dirty = replayState.dirty || dirty; - } - }; - - var features = sourceTile.getFeatures(); - if (renderOrder && renderOrder !== replayState.renderedRenderOrder) { - features.sort(renderOrder); - } - var feature; - for (var i = 0, ii = features.length; i < ii; ++i) { - feature = features[i]; - if (reproject) { - if (tileProjection.getUnits() == ol.proj.Units.TILE_PIXELS) { - // projected tile extent - tileProjection.setWorldExtent(sourceTileExtent); - // tile extent in tile pixel space - tileProjection.setExtent(sourceTile.getExtent()); - } - feature.getGeometry().transform(tileProjection, projection); - } - renderFeature.call(this, feature); - } - replayGroup.finish(); - sourceTile.setReplayGroup(layer, tile.tileCoord.toString(), replayGroup); - } - replayState.renderedRevision = revision; - replayState.renderedRenderOrder = renderOrder; -}; - - -/** - * @inheritDoc - */ -ol.renderer.canvas.VectorTileLayer.prototype.drawTileImage = function( - tile, frameState, layerState, x, y, w, h, gutter, transition) { - var vectorImageTile = /** @type {ol.VectorImageTile} */ (tile); - this.createReplayGroup_(vectorImageTile, frameState); - if (this.context) { - this.renderTileImage_(vectorImageTile, frameState, layerState); - ol.renderer.canvas.TileLayer.prototype.drawTileImage.apply(this, arguments); - } -}; - - -/** - * @inheritDoc - */ -ol.renderer.canvas.VectorTileLayer.prototype.forEachFeatureAtCoordinate = function(coordinate, frameState, hitTolerance, callback, thisArg) { - var resolution = frameState.viewState.resolution; - var rotation = frameState.viewState.rotation; - hitTolerance = hitTolerance == undefined ? 0 : hitTolerance; - var layer = this.getLayer(); - /** @type {Object.<string, boolean>} */ - var features = {}; - - /** @type {Array.<ol.VectorImageTile>} */ - var renderedTiles = this.renderedTiles; - - var source = /** @type {ol.source.VectorTile} */ (layer.getSource()); - var tileGrid = source.getTileGridForProjection(frameState.viewState.projection); - var bufferedExtent, found; - var i, ii, replayGroup; - var tile, tileCoord, tileExtent; - for (i = 0, ii = renderedTiles.length; i < ii; ++i) { - tile = renderedTiles[i]; - tileCoord = tile.tileCoord; - tileExtent = tileGrid.getTileCoordExtent(tileCoord, this.tmpExtent); - bufferedExtent = ol.extent.buffer(tileExtent, hitTolerance * resolution, bufferedExtent); - if (!ol.extent.containsCoordinate(bufferedExtent, coordinate)) { - continue; - } - for (var t = 0, tt = tile.tileKeys.length; t < tt; ++t) { - var sourceTile = tile.getTile(tile.tileKeys[t]); - if (sourceTile.getState() == ol.TileState.ERROR) { - continue; - } - replayGroup = sourceTile.getReplayGroup(layer, tile.tileCoord.toString()); - found = found || replayGroup.forEachFeatureAtCoordinate( - coordinate, resolution, rotation, hitTolerance, {}, - /** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @return {?} Callback result. - */ - function(feature) { - var key = ol.getUid(feature).toString(); - if (!(key in features)) { - features[key] = true; - return callback.call(thisArg, feature, layer); - } - }); - } - } - return found; -}; - - -/** - * @param {ol.VectorTile} tile Tile. - * @param {olx.FrameState} frameState Frame state. - * @return {ol.Transform} transform Transform. - * @private - */ -ol.renderer.canvas.VectorTileLayer.prototype.getReplayTransform_ = function(tile, frameState) { - var layer = this.getLayer(); - var source = /** @type {ol.source.VectorTile} */ (layer.getSource()); - var tileGrid = source.getTileGrid(); - var tileCoord = tile.tileCoord; - var tileResolution = tileGrid.getResolution(tileCoord[0]); - var viewState = frameState.viewState; - var pixelRatio = frameState.pixelRatio; - var renderResolution = viewState.resolution / pixelRatio; - var tileExtent = tileGrid.getTileCoordExtent(tileCoord, this.tmpExtent); - var center = viewState.center; - var origin = ol.extent.getTopLeft(tileExtent); - var size = frameState.size; - var offsetX = Math.round(pixelRatio * size[0] / 2); - var offsetY = Math.round(pixelRatio * size[1] / 2); - return ol.transform.compose(this.tmpTransform_, - offsetX, offsetY, - tileResolution / renderResolution, tileResolution / renderResolution, - viewState.rotation, - (origin[0] - center[0]) / tileResolution, - (center[1] - origin[1]) / tileResolution); -}; - - -/** - * Handle changes in image style state. - * @param {ol.events.Event} event Image style change event. - * @private - */ -ol.renderer.canvas.VectorTileLayer.prototype.handleStyleImageChange_ = function(event) { - this.renderIfReadyAndVisible(); -}; - - -/** - * @inheritDoc - */ -ol.renderer.canvas.VectorTileLayer.prototype.postCompose = function(context, frameState, layerState) { - var layer = this.getLayer(); - var source = /** @type {ol.source.VectorTile} */ (layer.getSource()); - var renderMode = layer.getRenderMode(); - var replays = ol.renderer.canvas.VectorTileLayer.VECTOR_REPLAYS[renderMode]; - var pixelRatio = frameState.pixelRatio; - var rotation = frameState.viewState.rotation; - var size = frameState.size; - var offsetX = Math.round(pixelRatio * size[0] / 2); - var offsetY = Math.round(pixelRatio * size[1] / 2); - var tiles = this.renderedTiles; - var tileGrid = source.getTileGridForProjection(frameState.viewState.projection); - var clips = []; - var zs = []; - for (var i = tiles.length - 1; i >= 0; --i) { - var tile = /** @type {ol.VectorImageTile} */ (tiles[i]); - if (tile.getState() == ol.TileState.ABORT) { - continue; - } - var tileCoord = tile.tileCoord; - var worldOffset = tileGrid.getTileCoordExtent(tileCoord)[0] - - tileGrid.getTileCoordExtent(tile.wrappedTileCoord)[0]; - for (var t = 0, tt = tile.tileKeys.length; t < tt; ++t) { - var sourceTile = tile.getTile(tile.tileKeys[t]); - if (sourceTile.getState() == ol.TileState.ERROR) { - continue; - } - var replayGroup = sourceTile.getReplayGroup(layer, tileCoord.toString()); - if (renderMode != ol.layer.VectorTileRenderType.VECTOR && !replayGroup.hasReplays(replays)) { - continue; - } - var currentZ = sourceTile.tileCoord[0]; - var transform = this.getTransform(frameState, worldOffset); - var currentClip = replayGroup.getClipCoords(transform); - context.save(); - context.globalAlpha = layerState.opacity; - ol.render.canvas.rotateAtOffset(context, -rotation, offsetX, offsetY); - // Create a clip mask for regions in this low resolution tile that are - // already filled by a higher resolution tile - for (var j = 0, jj = clips.length; j < jj; ++j) { - var clip = clips[j]; - if (currentZ < zs[j]) { - context.beginPath(); - // counter-clockwise (outer ring) for current tile - context.moveTo(currentClip[0], currentClip[1]); - context.lineTo(currentClip[2], currentClip[3]); - context.lineTo(currentClip[4], currentClip[5]); - context.lineTo(currentClip[6], currentClip[7]); - // clockwise (inner ring) for higher resolution tile - context.moveTo(clip[6], clip[7]); - context.lineTo(clip[4], clip[5]); - context.lineTo(clip[2], clip[3]); - context.lineTo(clip[0], clip[1]); - context.clip(); - } - } - replayGroup.replay(context, transform, rotation, {}, replays); - context.restore(); - clips.push(currentClip); - zs.push(currentZ); - } - } - ol.renderer.canvas.TileLayer.prototype.postCompose.apply(this, arguments); -}; - - -/** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @param {number} squaredTolerance Squared tolerance. - * @param {(ol.style.Style|Array.<ol.style.Style>)} styles The style or array of - * styles. - * @param {ol.render.canvas.ReplayGroup} replayGroup Replay group. - * @return {boolean} `true` if an image is loading. - */ -ol.renderer.canvas.VectorTileLayer.prototype.renderFeature = function(feature, squaredTolerance, styles, replayGroup) { - if (!styles) { - return false; - } - var loading = false; - if (Array.isArray(styles)) { - for (var i = 0, ii = styles.length; i < ii; ++i) { - loading = ol.renderer.vector.renderFeature( - replayGroup, feature, styles[i], squaredTolerance, - this.handleStyleImageChange_, this) || loading; - } - } else { - loading = ol.renderer.vector.renderFeature( - replayGroup, feature, styles, squaredTolerance, - this.handleStyleImageChange_, this) || loading; - } - return loading; -}; - - -/** - * @param {ol.VectorImageTile} tile Tile. - * @param {olx.FrameState} frameState Frame state. - * @param {ol.LayerState} layerState Layer state. - * @private - */ -ol.renderer.canvas.VectorTileLayer.prototype.renderTileImage_ = function( - tile, frameState, layerState) { - var layer = this.getLayer(); - var replayState = tile.getReplayState(layer); - var revision = layer.getRevision(); - var replays = ol.renderer.canvas.VectorTileLayer.IMAGE_REPLAYS[layer.getRenderMode()]; - if (replays && replayState.renderedTileRevision !== revision) { - replayState.renderedTileRevision = revision; - var tileCoord = tile.wrappedTileCoord; - var z = tileCoord[0]; - var pixelRatio = frameState.pixelRatio; - var source = /** @type {ol.source.VectorTile} */ (layer.getSource()); - var tileGrid = source.getTileGridForProjection(frameState.viewState.projection); - var resolution = tileGrid.getResolution(z); - var context = tile.getContext(layer); - var size = source.getTilePixelSize(z, pixelRatio, frameState.viewState.projection); - context.canvas.width = size[0]; - context.canvas.height = size[1]; - var tileExtent = tileGrid.getTileCoordExtent(tileCoord); - for (var i = 0, ii = tile.tileKeys.length; i < ii; ++i) { - var sourceTile = tile.getTile(tile.tileKeys[i]); - if (sourceTile.getState() == ol.TileState.ERROR) { - continue; - } - var pixelScale = pixelRatio / resolution; - var transform = ol.transform.reset(this.tmpTransform_); - ol.transform.scale(transform, pixelScale, -pixelScale); - ol.transform.translate(transform, -tileExtent[0], -tileExtent[3]); - var replayGroup = sourceTile.getReplayGroup(layer, tile.tileCoord.toString()); - replayGroup.replay(context, transform, 0, {}, replays, true); - } - } -}; - -goog.provide('ol.CanvasMap'); - -goog.require('ol'); -goog.require('ol.PluggableMap'); -goog.require('ol.PluginType'); -goog.require('ol.control'); -goog.require('ol.interaction'); -goog.require('ol.obj'); -goog.require('ol.plugins'); -goog.require('ol.renderer.canvas.ImageLayer'); -goog.require('ol.renderer.canvas.Map'); -goog.require('ol.renderer.canvas.TileLayer'); -goog.require('ol.renderer.canvas.VectorLayer'); -goog.require('ol.renderer.canvas.VectorTileLayer'); - - -ol.plugins.register(ol.PluginType.MAP_RENDERER, ol.renderer.canvas.Map); -ol.plugins.registerMultiple(ol.PluginType.LAYER_RENDERER, [ - ol.renderer.canvas.ImageLayer, - ol.renderer.canvas.TileLayer, - ol.renderer.canvas.VectorLayer, - ol.renderer.canvas.VectorTileLayer -]); - - -/** - * @classdesc - * The map is the core component of OpenLayers. For a map to render, a view, - * one or more layers, and a target container are needed: - * - * var map = new ol.CanvasMap({ - * view: new ol.View({ - * center: [0, 0], - * zoom: 1 - * }), - * layers: [ - * new ol.layer.Tile({ - * source: new ol.source.OSM() - * }) - * ], - * target: 'map' - * }); - * - * The above snippet creates a map using a {@link ol.layer.Tile} to display - * {@link ol.source.OSM} OSM data and render it to a DOM element with the - * id `map`. - * - * The constructor places a viewport container (with CSS class name - * `ol-viewport`) in the target element (see `getViewport()`), and then two - * further elements within the viewport: one with CSS class name - * `ol-overlaycontainer-stopevent` for controls and some overlays, and one with - * CSS class name `ol-overlaycontainer` for other overlays (see the `stopEvent` - * option of {@link ol.Overlay} for the difference). The map itself is placed in - * a further element within the viewport. - * - * Layers are stored as a `ol.Collection` in layerGroups. A top-level group is - * provided by the library. This is what is accessed by `getLayerGroup` and - * `setLayerGroup`. Layers entered in the options are added to this group, and - * `addLayer` and `removeLayer` change the layer collection in the group. - * `getLayers` is a convenience function for `getLayerGroup().getLayers()`. - * Note that `ol.layer.Group` is a subclass of `ol.layer.Base`, so layers - * entered in the options or added with `addLayer` can be groups, which can - * contain further groups, and so on. - * - * @constructor - * @extends {ol.PluggableMap} - * @param {olx.MapOptions} options Map options. - * @fires ol.MapBrowserEvent - * @fires ol.MapEvent - * @fires ol.render.Event#postcompose - * @fires ol.render.Event#precompose - * @api - */ -ol.CanvasMap = function(options) { - options = ol.obj.assign({}, options); - delete options.renderer; - if (!options.controls) { - options.controls = ol.control.defaults(); - } - if (!options.interactions) { - options.interactions = ol.interaction.defaults(); - } - - ol.PluggableMap.call(this, options); -}; -ol.inherits(ol.CanvasMap, ol.PluggableMap); - -goog.provide('ol.control.FullScreen'); - -goog.require('ol'); -goog.require('ol.control.Control'); -goog.require('ol.css'); -goog.require('ol.dom'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); - - -/** - * @classdesc - * Provides a button that when clicked fills up the full screen with the map. - * The full screen source element is by default the element containing the map viewport unless - * overridden by providing the `source` option. In which case, the dom - * element introduced using this parameter will be displayed in full screen. - * - * When in full screen mode, a close button is shown to exit full screen mode. - * The [Fullscreen API](http://www.w3.org/TR/fullscreen/) is used to - * toggle the map in full screen mode. - * - * - * @constructor - * @extends {ol.control.Control} - * @param {olx.control.FullScreenOptions=} opt_options Options. - * @api - */ -ol.control.FullScreen = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - /** - * @private - * @type {string} - */ - this.cssClassName_ = options.className !== undefined ? options.className : - 'ol-full-screen'; - - var label = options.label !== undefined ? options.label : '\u2922'; - - /** - * @private - * @type {Node} - */ - this.labelNode_ = typeof label === 'string' ? - document.createTextNode(label) : label; - - var labelActive = options.labelActive !== undefined ? options.labelActive : '\u00d7'; - - /** - * @private - * @type {Node} - */ - this.labelActiveNode_ = typeof labelActive === 'string' ? - document.createTextNode(labelActive) : labelActive; - - var tipLabel = options.tipLabel ? options.tipLabel : 'Toggle full-screen'; - var button = document.createElement('button'); - button.className = this.cssClassName_ + '-' + ol.control.FullScreen.isFullScreen(); - button.setAttribute('type', 'button'); - button.title = tipLabel; - button.appendChild(this.labelNode_); - - ol.events.listen(button, ol.events.EventType.CLICK, - this.handleClick_, this); - - var cssClasses = this.cssClassName_ + ' ' + ol.css.CLASS_UNSELECTABLE + - ' ' + ol.css.CLASS_CONTROL + ' ' + - (!ol.control.FullScreen.isFullScreenSupported() ? ol.css.CLASS_UNSUPPORTED : ''); - var element = document.createElement('div'); - element.className = cssClasses; - element.appendChild(button); - - ol.control.Control.call(this, { - element: element, - target: options.target - }); - - /** - * @private - * @type {boolean} - */ - this.keys_ = options.keys !== undefined ? options.keys : false; - - /** - * @private - * @type {Element|string|undefined} - */ - this.source_ = options.source; - -}; -ol.inherits(ol.control.FullScreen, ol.control.Control); - - -/** - * @param {Event} event The event to handle - * @private - */ -ol.control.FullScreen.prototype.handleClick_ = function(event) { - event.preventDefault(); - this.handleFullScreen_(); -}; - - -/** - * @private - */ -ol.control.FullScreen.prototype.handleFullScreen_ = function() { - if (!ol.control.FullScreen.isFullScreenSupported()) { - return; - } - var map = this.getMap(); - if (!map) { - return; - } - if (ol.control.FullScreen.isFullScreen()) { - ol.control.FullScreen.exitFullScreen(); - } else { - var element; - if (this.source_) { - element = typeof this.source_ === 'string' ? - document.getElementById(this.source_) : - this.source_; - } else { - element = map.getTargetElement(); - } - if (this.keys_) { - ol.control.FullScreen.requestFullScreenWithKeys(element); - - } else { - ol.control.FullScreen.requestFullScreen(element); - } - } -}; - - -/** - * @private - */ -ol.control.FullScreen.prototype.handleFullScreenChange_ = function() { - var button = this.element.firstElementChild; - var map = this.getMap(); - if (ol.control.FullScreen.isFullScreen()) { - button.className = this.cssClassName_ + '-true'; - ol.dom.replaceNode(this.labelActiveNode_, this.labelNode_); - } else { - button.className = this.cssClassName_ + '-false'; - ol.dom.replaceNode(this.labelNode_, this.labelActiveNode_); - } - if (map) { - map.updateSize(); - } -}; - - -/** - * @inheritDoc - * @api - */ -ol.control.FullScreen.prototype.setMap = function(map) { - ol.control.Control.prototype.setMap.call(this, map); - if (map) { - this.listenerKeys.push(ol.events.listen(document, - ol.control.FullScreen.getChangeType_(), - this.handleFullScreenChange_, this) - ); - } -}; - -/** - * @return {boolean} Fullscreen is supported by the current platform. - */ -ol.control.FullScreen.isFullScreenSupported = function() { - var body = document.body; - return !!( - body.webkitRequestFullscreen || - (body.mozRequestFullScreen && document.mozFullScreenEnabled) || - (body.msRequestFullscreen && document.msFullscreenEnabled) || - (body.requestFullscreen && document.fullscreenEnabled) - ); -}; - -/** - * @return {boolean} Element is currently in fullscreen. - */ -ol.control.FullScreen.isFullScreen = function() { - return !!( - document.webkitIsFullScreen || document.mozFullScreen || - document.msFullscreenElement || document.fullscreenElement - ); -}; - -/** - * Request to fullscreen an element. - * @param {Node} element Element to request fullscreen - */ -ol.control.FullScreen.requestFullScreen = function(element) { - if (element.requestFullscreen) { - element.requestFullscreen(); - } else if (element.msRequestFullscreen) { - element.msRequestFullscreen(); - } else if (element.mozRequestFullScreen) { - element.mozRequestFullScreen(); - } else if (element.webkitRequestFullscreen) { - element.webkitRequestFullscreen(); - } -}; - -/** - * Request to fullscreen an element with keyboard input. - * @param {Node} element Element to request fullscreen - */ -ol.control.FullScreen.requestFullScreenWithKeys = function(element) { - if (element.mozRequestFullScreenWithKeys) { - element.mozRequestFullScreenWithKeys(); - } else if (element.webkitRequestFullscreen) { - element.webkitRequestFullscreen(Element.ALLOW_KEYBOARD_INPUT); - } else { - ol.control.FullScreen.requestFullScreen(element); - } -}; - -/** - * Exit fullscreen. - */ -ol.control.FullScreen.exitFullScreen = function() { - if (document.exitFullscreen) { - document.exitFullscreen(); - } else if (document.msExitFullscreen) { - document.msExitFullscreen(); - } else if (document.mozCancelFullScreen) { - document.mozCancelFullScreen(); - } else if (document.webkitExitFullscreen) { - document.webkitExitFullscreen(); - } -}; - -/** - * @return {string} Change type. - * @private - */ -ol.control.FullScreen.getChangeType_ = (function() { - var changeType; - return function() { - if (!changeType) { - var body = document.body; - if (body.webkitRequestFullscreen) { - changeType = 'webkitfullscreenchange'; - } else if (body.mozRequestFullScreen) { - changeType = 'mozfullscreenchange'; - } else if (body.msRequestFullscreen) { - changeType = 'MSFullscreenChange'; - } else if (body.requestFullscreen) { - changeType = 'fullscreenchange'; - } - } - return changeType; - }; -})(); - -// FIXME should listen on appropriate pane, once it is defined - -goog.provide('ol.control.MousePosition'); - -goog.require('ol'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.Object'); -goog.require('ol.control.Control'); -goog.require('ol.proj'); - - -/** - * @classdesc - * A control to show the 2D coordinates of the mouse cursor. By default, these - * are in the view projection, but can be in any supported projection. - * By default the control is shown in the top right corner of the map, but this - * can be changed by using the css selector `.ol-mouse-position`. - * - * @constructor - * @extends {ol.control.Control} - * @param {olx.control.MousePositionOptions=} opt_options Mouse position - * options. - * @api - */ -ol.control.MousePosition = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - var element = document.createElement('DIV'); - element.className = options.className !== undefined ? options.className : 'ol-mouse-position'; - - var render = options.render ? - options.render : ol.control.MousePosition.render; - - ol.control.Control.call(this, { - element: element, - render: render, - target: options.target - }); - - ol.events.listen(this, - ol.Object.getChangeEventType(ol.control.MousePosition.Property_.PROJECTION), - this.handleProjectionChanged_, this); - - if (options.coordinateFormat) { - this.setCoordinateFormat(options.coordinateFormat); - } - if (options.projection) { - this.setProjection(options.projection); - } - - /** - * @private - * @type {string} - */ - this.undefinedHTML_ = options.undefinedHTML !== undefined ? options.undefinedHTML : ''; - - /** - * @private - * @type {string} - */ - this.renderedHTML_ = element.innerHTML; - - /** - * @private - * @type {ol.proj.Projection} - */ - this.mapProjection_ = null; - - /** - * @private - * @type {?ol.TransformFunction} - */ - this.transform_ = null; - - /** - * @private - * @type {ol.Pixel} - */ - this.lastMouseMovePixel_ = null; - -}; -ol.inherits(ol.control.MousePosition, ol.control.Control); - - -/** - * Update the mouseposition element. - * @param {ol.MapEvent} mapEvent Map event. - * @this {ol.control.MousePosition} - * @api - */ -ol.control.MousePosition.render = function(mapEvent) { - var frameState = mapEvent.frameState; - if (!frameState) { - this.mapProjection_ = null; - } else { - if (this.mapProjection_ != frameState.viewState.projection) { - this.mapProjection_ = frameState.viewState.projection; - this.transform_ = null; - } - } - this.updateHTML_(this.lastMouseMovePixel_); -}; - - -/** - * @private - */ -ol.control.MousePosition.prototype.handleProjectionChanged_ = function() { - this.transform_ = null; -}; - - -/** - * Return the coordinate format type used to render the current position or - * undefined. - * @return {ol.CoordinateFormatType|undefined} The format to render the current - * position in. - * @observable - * @api - */ -ol.control.MousePosition.prototype.getCoordinateFormat = function() { - return /** @type {ol.CoordinateFormatType|undefined} */ ( - this.get(ol.control.MousePosition.Property_.COORDINATE_FORMAT)); -}; - - -/** - * Return the projection that is used to report the mouse position. - * @return {ol.proj.Projection|undefined} The projection to report mouse - * position in. - * @observable - * @api - */ -ol.control.MousePosition.prototype.getProjection = function() { - return /** @type {ol.proj.Projection|undefined} */ ( - this.get(ol.control.MousePosition.Property_.PROJECTION)); -}; - - -/** - * @param {Event} event Browser event. - * @protected - */ -ol.control.MousePosition.prototype.handleMouseMove = function(event) { - var map = this.getMap(); - this.lastMouseMovePixel_ = map.getEventPixel(event); - this.updateHTML_(this.lastMouseMovePixel_); -}; - - -/** - * @param {Event} event Browser event. - * @protected - */ -ol.control.MousePosition.prototype.handleMouseOut = function(event) { - this.updateHTML_(null); - this.lastMouseMovePixel_ = null; -}; - - -/** - * @inheritDoc - * @api - */ -ol.control.MousePosition.prototype.setMap = function(map) { - ol.control.Control.prototype.setMap.call(this, map); - if (map) { - var viewport = map.getViewport(); - this.listenerKeys.push( - ol.events.listen(viewport, ol.events.EventType.MOUSEMOVE, - this.handleMouseMove, this), - ol.events.listen(viewport, ol.events.EventType.MOUSEOUT, - this.handleMouseOut, this) - ); - } -}; - - -/** - * Set the coordinate format type used to render the current position. - * @param {ol.CoordinateFormatType} format The format to render the current - * position in. - * @observable - * @api - */ -ol.control.MousePosition.prototype.setCoordinateFormat = function(format) { - this.set(ol.control.MousePosition.Property_.COORDINATE_FORMAT, format); -}; - - -/** - * Set the projection that is used to report the mouse position. - * @param {ol.ProjectionLike} projection The projection to report mouse - * position in. - * @observable - * @api - */ -ol.control.MousePosition.prototype.setProjection = function(projection) { - this.set(ol.control.MousePosition.Property_.PROJECTION, ol.proj.get(projection)); -}; - - -/** - * @param {?ol.Pixel} pixel Pixel. - * @private - */ -ol.control.MousePosition.prototype.updateHTML_ = function(pixel) { - var html = this.undefinedHTML_; - if (pixel && this.mapProjection_) { - if (!this.transform_) { - var projection = this.getProjection(); - if (projection) { - this.transform_ = ol.proj.getTransformFromProjections( - this.mapProjection_, projection); - } else { - this.transform_ = ol.proj.identityTransform; - } - } - var map = this.getMap(); - var coordinate = map.getCoordinateFromPixel(pixel); - if (coordinate) { - this.transform_(coordinate, coordinate); - var coordinateFormat = this.getCoordinateFormat(); - if (coordinateFormat) { - html = coordinateFormat(coordinate); - } else { - html = coordinate.toString(); - } - } - } - if (!this.renderedHTML_ || html != this.renderedHTML_) { - this.element.innerHTML = html; - this.renderedHTML_ = html; - } -}; - - -/** - * @enum {string} - * @private - */ -ol.control.MousePosition.Property_ = { - PROJECTION: 'projection', - COORDINATE_FORMAT: 'coordinateFormat' -}; - -goog.provide('ol.OverlayPositioning'); - -/** - * Overlay position: `'bottom-left'`, `'bottom-center'`, `'bottom-right'`, - * `'center-left'`, `'center-center'`, `'center-right'`, `'top-left'`, - * `'top-center'`, `'top-right'` - * @enum {string} - */ -ol.OverlayPositioning = { - BOTTOM_LEFT: 'bottom-left', - BOTTOM_CENTER: 'bottom-center', - BOTTOM_RIGHT: 'bottom-right', - CENTER_LEFT: 'center-left', - CENTER_CENTER: 'center-center', - CENTER_RIGHT: 'center-right', - TOP_LEFT: 'top-left', - TOP_CENTER: 'top-center', - TOP_RIGHT: 'top-right' -}; - -goog.provide('ol.Overlay'); - -goog.require('ol'); -goog.require('ol.MapEventType'); -goog.require('ol.Object'); -goog.require('ol.OverlayPositioning'); -goog.require('ol.css'); -goog.require('ol.dom'); -goog.require('ol.events'); -goog.require('ol.extent'); - - -/** - * @classdesc - * An element to be displayed over the map and attached to a single map - * location. Like {@link ol.control.Control}, Overlays are visible widgets. - * Unlike Controls, they are not in a fixed position on the screen, but are tied - * to a geographical coordinate, so panning the map will move an Overlay but not - * a Control. - * - * Example: - * - * var popup = new ol.Overlay({ - * element: document.getElementById('popup') - * }); - * popup.setPosition(coordinate); - * map.addOverlay(popup); - * - * @constructor - * @extends {ol.Object} - * @param {olx.OverlayOptions} options Overlay options. - * @api - */ -ol.Overlay = function(options) { - - ol.Object.call(this); - - /** - * @private - * @type {number|string|undefined} - */ - this.id_ = options.id; - - /** - * @private - * @type {boolean} - */ - this.insertFirst_ = options.insertFirst !== undefined ? - options.insertFirst : true; - - /** - * @private - * @type {boolean} - */ - this.stopEvent_ = options.stopEvent !== undefined ? options.stopEvent : true; - - /** - * @private - * @type {Element} - */ - this.element_ = document.createElement('DIV'); - this.element_.className = 'ol-overlay-container ' + ol.css.CLASS_SELECTABLE; - this.element_.style.position = 'absolute'; - - /** - * @protected - * @type {boolean} - */ - this.autoPan = options.autoPan !== undefined ? options.autoPan : false; - - /** - * @private - * @type {olx.OverlayPanOptions} - */ - this.autoPanAnimation_ = options.autoPanAnimation || - /** @type {olx.OverlayPanOptions} */ ({}); - - /** - * @private - * @type {number} - */ - this.autoPanMargin_ = options.autoPanMargin !== undefined ? - options.autoPanMargin : 20; - - /** - * @private - * @type {{bottom_: string, - * left_: string, - * right_: string, - * top_: string, - * visible: boolean}} - */ - this.rendered_ = { - bottom_: '', - left_: '', - right_: '', - top_: '', - visible: true - }; - - /** - * @private - * @type {?ol.EventsKey} - */ - this.mapPostrenderListenerKey_ = null; - - ol.events.listen( - this, ol.Object.getChangeEventType(ol.Overlay.Property_.ELEMENT), - this.handleElementChanged, this); - - ol.events.listen( - this, ol.Object.getChangeEventType(ol.Overlay.Property_.MAP), - this.handleMapChanged, this); - - ol.events.listen( - this, ol.Object.getChangeEventType(ol.Overlay.Property_.OFFSET), - this.handleOffsetChanged, this); - - ol.events.listen( - this, ol.Object.getChangeEventType(ol.Overlay.Property_.POSITION), - this.handlePositionChanged, this); - - ol.events.listen( - this, ol.Object.getChangeEventType(ol.Overlay.Property_.POSITIONING), - this.handlePositioningChanged, this); - - if (options.element !== undefined) { - this.setElement(options.element); - } - - this.setOffset(options.offset !== undefined ? options.offset : [0, 0]); - - this.setPositioning(options.positioning !== undefined ? - /** @type {ol.OverlayPositioning} */ (options.positioning) : - ol.OverlayPositioning.TOP_LEFT); - - if (options.position !== undefined) { - this.setPosition(options.position); - } - -}; -ol.inherits(ol.Overlay, ol.Object); - - -/** - * Get the DOM element of this overlay. - * @return {Element|undefined} The Element containing the overlay. - * @observable - * @api - */ -ol.Overlay.prototype.getElement = function() { - return /** @type {Element|undefined} */ ( - this.get(ol.Overlay.Property_.ELEMENT)); -}; - - -/** - * Get the overlay identifier which is set on constructor. - * @return {number|string|undefined} Id. - * @api - */ -ol.Overlay.prototype.getId = function() { - return this.id_; -}; - - -/** - * Get the map associated with this overlay. - * @return {ol.PluggableMap|undefined} The map that the overlay is part of. - * @observable - * @api - */ -ol.Overlay.prototype.getMap = function() { - return /** @type {ol.PluggableMap|undefined} */ ( - this.get(ol.Overlay.Property_.MAP)); -}; - - -/** - * Get the offset of this overlay. - * @return {Array.<number>} The offset. - * @observable - * @api - */ -ol.Overlay.prototype.getOffset = function() { - return /** @type {Array.<number>} */ ( - this.get(ol.Overlay.Property_.OFFSET)); -}; - - -/** - * Get the current position of this overlay. - * @return {ol.Coordinate|undefined} The spatial point that the overlay is - * anchored at. - * @observable - * @api - */ -ol.Overlay.prototype.getPosition = function() { - return /** @type {ol.Coordinate|undefined} */ ( - this.get(ol.Overlay.Property_.POSITION)); -}; - - -/** - * Get the current positioning of this overlay. - * @return {ol.OverlayPositioning} How the overlay is positioned - * relative to its point on the map. - * @observable - * @api - */ -ol.Overlay.prototype.getPositioning = function() { - return /** @type {ol.OverlayPositioning} */ ( - this.get(ol.Overlay.Property_.POSITIONING)); -}; - - -/** - * @protected - */ -ol.Overlay.prototype.handleElementChanged = function() { - ol.dom.removeChildren(this.element_); - var element = this.getElement(); - if (element) { - this.element_.appendChild(element); - } -}; - - -/** - * @protected - */ -ol.Overlay.prototype.handleMapChanged = function() { - if (this.mapPostrenderListenerKey_) { - ol.dom.removeNode(this.element_); - ol.events.unlistenByKey(this.mapPostrenderListenerKey_); - this.mapPostrenderListenerKey_ = null; - } - var map = this.getMap(); - if (map) { - this.mapPostrenderListenerKey_ = ol.events.listen(map, - ol.MapEventType.POSTRENDER, this.render, this); - this.updatePixelPosition(); - var container = this.stopEvent_ ? - map.getOverlayContainerStopEvent() : map.getOverlayContainer(); - if (this.insertFirst_) { - container.insertBefore(this.element_, container.childNodes[0] || null); - } else { - container.appendChild(this.element_); - } - } -}; - - -/** - * @protected - */ -ol.Overlay.prototype.render = function() { - this.updatePixelPosition(); -}; - - -/** - * @protected - */ -ol.Overlay.prototype.handleOffsetChanged = function() { - this.updatePixelPosition(); -}; - - -/** - * @protected - */ -ol.Overlay.prototype.handlePositionChanged = function() { - this.updatePixelPosition(); - if (this.get(ol.Overlay.Property_.POSITION) && this.autoPan) { - this.panIntoView_(); - } -}; - - -/** - * @protected - */ -ol.Overlay.prototype.handlePositioningChanged = function() { - this.updatePixelPosition(); -}; - - -/** - * Set the DOM element to be associated with this overlay. - * @param {Element|undefined} element The Element containing the overlay. - * @observable - * @api - */ -ol.Overlay.prototype.setElement = function(element) { - this.set(ol.Overlay.Property_.ELEMENT, element); -}; - - -/** - * Set the map to be associated with this overlay. - * @param {ol.PluggableMap|undefined} map The map that the overlay is part of. - * @observable - * @api - */ -ol.Overlay.prototype.setMap = function(map) { - this.set(ol.Overlay.Property_.MAP, map); -}; - - -/** - * Set the offset for this overlay. - * @param {Array.<number>} offset Offset. - * @observable - * @api - */ -ol.Overlay.prototype.setOffset = function(offset) { - this.set(ol.Overlay.Property_.OFFSET, offset); -}; - - -/** - * Set the position for this overlay. If the position is `undefined` the - * overlay is hidden. - * @param {ol.Coordinate|undefined} position The spatial point that the overlay - * is anchored at. - * @observable - * @api - */ -ol.Overlay.prototype.setPosition = function(position) { - this.set(ol.Overlay.Property_.POSITION, position); -}; - - -/** - * Pan the map so that the overlay is entirely visible in the current viewport - * (if necessary). - * @private - */ -ol.Overlay.prototype.panIntoView_ = function() { - var map = this.getMap(); - - if (!map || !map.getTargetElement()) { - return; - } - - var mapRect = this.getRect_(map.getTargetElement(), map.getSize()); - var element = /** @type {!Element} */ (this.getElement()); - var overlayRect = this.getRect_(element, - [ol.dom.outerWidth(element), ol.dom.outerHeight(element)]); - - var margin = this.autoPanMargin_; - if (!ol.extent.containsExtent(mapRect, overlayRect)) { - // the overlay is not completely inside the viewport, so pan the map - var offsetLeft = overlayRect[0] - mapRect[0]; - var offsetRight = mapRect[2] - overlayRect[2]; - var offsetTop = overlayRect[1] - mapRect[1]; - var offsetBottom = mapRect[3] - overlayRect[3]; - - var delta = [0, 0]; - if (offsetLeft < 0) { - // move map to the left - delta[0] = offsetLeft - margin; - } else if (offsetRight < 0) { - // move map to the right - delta[0] = Math.abs(offsetRight) + margin; - } - if (offsetTop < 0) { - // move map up - delta[1] = offsetTop - margin; - } else if (offsetBottom < 0) { - // move map down - delta[1] = Math.abs(offsetBottom) + margin; - } - - if (delta[0] !== 0 || delta[1] !== 0) { - var center = /** @type {ol.Coordinate} */ (map.getView().getCenter()); - var centerPx = map.getPixelFromCoordinate(center); - var newCenterPx = [ - centerPx[0] + delta[0], - centerPx[1] + delta[1] - ]; - - map.getView().animate({ - center: map.getCoordinateFromPixel(newCenterPx), - duration: this.autoPanAnimation_.duration, - easing: this.autoPanAnimation_.easing - }); - } - } -}; - - -/** - * Get the extent of an element relative to the document - * @param {Element|undefined} element The element. - * @param {ol.Size|undefined} size The size of the element. - * @return {ol.Extent} The extent. - * @private - */ -ol.Overlay.prototype.getRect_ = function(element, size) { - var box = element.getBoundingClientRect(); - var offsetX = box.left + window.pageXOffset; - var offsetY = box.top + window.pageYOffset; - return [ - offsetX, - offsetY, - offsetX + size[0], - offsetY + size[1] - ]; -}; - - -/** - * Set the positioning for this overlay. - * @param {ol.OverlayPositioning} positioning how the overlay is - * positioned relative to its point on the map. - * @observable - * @api - */ -ol.Overlay.prototype.setPositioning = function(positioning) { - this.set(ol.Overlay.Property_.POSITIONING, positioning); -}; - - -/** - * Modify the visibility of the element. - * @param {boolean} visible Element visibility. - * @protected - */ -ol.Overlay.prototype.setVisible = function(visible) { - if (this.rendered_.visible !== visible) { - this.element_.style.display = visible ? '' : 'none'; - this.rendered_.visible = visible; - } -}; - - -/** - * Update pixel position. - * @protected - */ -ol.Overlay.prototype.updatePixelPosition = function() { - var map = this.getMap(); - var position = this.getPosition(); - if (!map || !map.isRendered() || !position) { - this.setVisible(false); - return; - } - - var pixel = map.getPixelFromCoordinate(position); - var mapSize = map.getSize(); - this.updateRenderedPosition(pixel, mapSize); -}; - - -/** - * @param {ol.Pixel} pixel The pixel location. - * @param {ol.Size|undefined} mapSize The map size. - * @protected - */ -ol.Overlay.prototype.updateRenderedPosition = function(pixel, mapSize) { - var style = this.element_.style; - var offset = this.getOffset(); - - var positioning = this.getPositioning(); - - this.setVisible(true); - - var offsetX = offset[0]; - var offsetY = offset[1]; - if (positioning == ol.OverlayPositioning.BOTTOM_RIGHT || - positioning == ol.OverlayPositioning.CENTER_RIGHT || - positioning == ol.OverlayPositioning.TOP_RIGHT) { - if (this.rendered_.left_ !== '') { - this.rendered_.left_ = style.left = ''; - } - var right = Math.round(mapSize[0] - pixel[0] - offsetX) + 'px'; - if (this.rendered_.right_ != right) { - this.rendered_.right_ = style.right = right; - } - } else { - if (this.rendered_.right_ !== '') { - this.rendered_.right_ = style.right = ''; - } - if (positioning == ol.OverlayPositioning.BOTTOM_CENTER || - positioning == ol.OverlayPositioning.CENTER_CENTER || - positioning == ol.OverlayPositioning.TOP_CENTER) { - offsetX -= this.element_.offsetWidth / 2; - } - var left = Math.round(pixel[0] + offsetX) + 'px'; - if (this.rendered_.left_ != left) { - this.rendered_.left_ = style.left = left; - } - } - if (positioning == ol.OverlayPositioning.BOTTOM_LEFT || - positioning == ol.OverlayPositioning.BOTTOM_CENTER || - positioning == ol.OverlayPositioning.BOTTOM_RIGHT) { - if (this.rendered_.top_ !== '') { - this.rendered_.top_ = style.top = ''; - } - var bottom = Math.round(mapSize[1] - pixel[1] - offsetY) + 'px'; - if (this.rendered_.bottom_ != bottom) { - this.rendered_.bottom_ = style.bottom = bottom; - } - } else { - if (this.rendered_.bottom_ !== '') { - this.rendered_.bottom_ = style.bottom = ''; - } - if (positioning == ol.OverlayPositioning.CENTER_LEFT || - positioning == ol.OverlayPositioning.CENTER_CENTER || - positioning == ol.OverlayPositioning.CENTER_RIGHT) { - offsetY -= this.element_.offsetHeight / 2; - } - var top = Math.round(pixel[1] + offsetY) + 'px'; - if (this.rendered_.top_ != top) { - this.rendered_.top_ = style.top = top; - } - } -}; - - -/** - * @enum {string} - * @private - */ -ol.Overlay.Property_ = { - ELEMENT: 'element', - MAP: 'map', - OFFSET: 'offset', - POSITION: 'position', - POSITIONING: 'positioning' -}; - -goog.provide('ol.control.OverviewMap'); - -goog.require('ol'); -goog.require('ol.Collection'); -goog.require('ol.PluggableMap'); -goog.require('ol.MapEventType'); -goog.require('ol.MapProperty'); -goog.require('ol.Object'); -goog.require('ol.ObjectEventType'); -goog.require('ol.Overlay'); -goog.require('ol.OverlayPositioning'); -goog.require('ol.ViewProperty'); -goog.require('ol.control.Control'); -goog.require('ol.coordinate'); -goog.require('ol.css'); -goog.require('ol.dom'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.extent'); - - -/** - * Create a new control with a map acting as an overview map for an other - * defined map. - * @constructor - * @extends {ol.control.Control} - * @param {olx.control.OverviewMapOptions=} opt_options OverviewMap options. - * @api - */ -ol.control.OverviewMap = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - /** - * @type {boolean} - * @private - */ - this.collapsed_ = options.collapsed !== undefined ? options.collapsed : true; - - /** - * @private - * @type {boolean} - */ - this.collapsible_ = options.collapsible !== undefined ? - options.collapsible : true; - - if (!this.collapsible_) { - this.collapsed_ = false; - } - - var className = options.className !== undefined ? options.className : 'ol-overviewmap'; - - var tipLabel = options.tipLabel !== undefined ? options.tipLabel : 'Overview map'; - - var collapseLabel = options.collapseLabel !== undefined ? options.collapseLabel : '\u00AB'; - - if (typeof collapseLabel === 'string') { - /** - * @private - * @type {Node} - */ - this.collapseLabel_ = document.createElement('span'); - this.collapseLabel_.textContent = collapseLabel; - } else { - this.collapseLabel_ = collapseLabel; - } - - var label = options.label !== undefined ? options.label : '\u00BB'; - - - if (typeof label === 'string') { - /** - * @private - * @type {Node} - */ - this.label_ = document.createElement('span'); - this.label_.textContent = label; - } else { - this.label_ = label; - } - - var activeLabel = (this.collapsible_ && !this.collapsed_) ? - this.collapseLabel_ : this.label_; - var button = document.createElement('button'); - button.setAttribute('type', 'button'); - button.title = tipLabel; - button.appendChild(activeLabel); - - ol.events.listen(button, ol.events.EventType.CLICK, - this.handleClick_, this); - - /** - * @type {Element} - * @private - */ - this.ovmapDiv_ = document.createElement('DIV'); - this.ovmapDiv_.className = 'ol-overviewmap-map'; - - /** - * @type {ol.PluggableMap} - * @private - */ - this.ovmap_ = new ol.PluggableMap({ - controls: new ol.Collection(), - interactions: new ol.Collection(), - view: options.view - }); - var ovmap = this.ovmap_; - - if (options.layers) { - options.layers.forEach( - /** - * @param {ol.layer.Layer} layer Layer. - */ - function(layer) { - ovmap.addLayer(layer); - }, this); - } - - var box = document.createElement('DIV'); - box.className = 'ol-overviewmap-box'; - box.style.boxSizing = 'border-box'; - - /** - * @type {ol.Overlay} - * @private - */ - this.boxOverlay_ = new ol.Overlay({ - position: [0, 0], - positioning: ol.OverlayPositioning.BOTTOM_LEFT, - element: box - }); - this.ovmap_.addOverlay(this.boxOverlay_); - - var cssClasses = className + ' ' + ol.css.CLASS_UNSELECTABLE + ' ' + - ol.css.CLASS_CONTROL + - (this.collapsed_ && this.collapsible_ ? ' ol-collapsed' : '') + - (this.collapsible_ ? '' : ' ol-uncollapsible'); - var element = document.createElement('div'); - element.className = cssClasses; - element.appendChild(this.ovmapDiv_); - element.appendChild(button); - - var render = options.render ? options.render : ol.control.OverviewMap.render; - - ol.control.Control.call(this, { - element: element, - render: render, - target: options.target - }); - - /* Interactive map */ - - var scope = this; - - var overlay = this.boxOverlay_; - var overlayBox = this.boxOverlay_.getElement(); - - /* Functions definition */ - - var computeDesiredMousePosition = function(mousePosition) { - return { - clientX: mousePosition.clientX - (overlayBox.offsetWidth / 2), - clientY: mousePosition.clientY + (overlayBox.offsetHeight / 2) - }; - }; - - var move = function(event) { - var coordinates = ovmap.getEventCoordinate(computeDesiredMousePosition(event)); - - overlay.setPosition(coordinates); - }; - - var endMoving = function(event) { - var coordinates = ovmap.getEventCoordinate(event); - - scope.getMap().getView().setCenter(coordinates); - - window.removeEventListener('mousemove', move); - window.removeEventListener('mouseup', endMoving); - }; - - /* Binding */ - - overlayBox.addEventListener('mousedown', function() { - window.addEventListener('mousemove', move); - window.addEventListener('mouseup', endMoving); - }); -}; -ol.inherits(ol.control.OverviewMap, ol.control.Control); - - -/** - * @inheritDoc - * @api - */ -ol.control.OverviewMap.prototype.setMap = function(map) { - var oldMap = this.getMap(); - if (map === oldMap) { - return; - } - if (oldMap) { - var oldView = oldMap.getView(); - if (oldView) { - this.unbindView_(oldView); - } - this.ovmap_.setTarget(null); - } - ol.control.Control.prototype.setMap.call(this, map); - - if (map) { - this.ovmap_.setTarget(this.ovmapDiv_); - this.listenerKeys.push(ol.events.listen( - map, ol.ObjectEventType.PROPERTYCHANGE, - this.handleMapPropertyChange_, this)); - - // TODO: to really support map switching, this would need to be reworked - if (this.ovmap_.getLayers().getLength() === 0) { - this.ovmap_.setLayerGroup(map.getLayerGroup()); - } - - var view = map.getView(); - if (view) { - this.bindView_(view); - if (view.isDef()) { - this.ovmap_.updateSize(); - this.resetExtent_(); - } - } - } -}; - - -/** - * Handle map property changes. This only deals with changes to the map's view. - * @param {ol.Object.Event} event The propertychange event. - * @private - */ -ol.control.OverviewMap.prototype.handleMapPropertyChange_ = function(event) { - if (event.key === ol.MapProperty.VIEW) { - var oldView = /** @type {ol.View} */ (event.oldValue); - if (oldView) { - this.unbindView_(oldView); - } - var newView = this.getMap().getView(); - this.bindView_(newView); - } -}; - - -/** - * Register listeners for view property changes. - * @param {ol.View} view The view. - * @private - */ -ol.control.OverviewMap.prototype.bindView_ = function(view) { - ol.events.listen(view, - ol.Object.getChangeEventType(ol.ViewProperty.ROTATION), - this.handleRotationChanged_, this); -}; - - -/** - * Unregister listeners for view property changes. - * @param {ol.View} view The view. - * @private - */ -ol.control.OverviewMap.prototype.unbindView_ = function(view) { - ol.events.unlisten(view, - ol.Object.getChangeEventType(ol.ViewProperty.ROTATION), - this.handleRotationChanged_, this); -}; - - -/** - * Handle rotation changes to the main map. - * TODO: This should rotate the extent rectrangle instead of the - * overview map's view. - * @private - */ -ol.control.OverviewMap.prototype.handleRotationChanged_ = function() { - this.ovmap_.getView().setRotation(this.getMap().getView().getRotation()); -}; - - -/** - * Update the overview map element. - * @param {ol.MapEvent} mapEvent Map event. - * @this {ol.control.OverviewMap} - * @api - */ -ol.control.OverviewMap.render = function(mapEvent) { - this.validateExtent_(); - this.updateBox_(); -}; - - -/** - * Reset the overview map extent if the box size (width or - * height) is less than the size of the overview map size times minRatio - * or is greater than the size of the overview size times maxRatio. - * - * If the map extent was not reset, the box size can fits in the defined - * ratio sizes. This method then checks if is contained inside the overview - * map current extent. If not, recenter the overview map to the current - * main map center location. - * @private - */ -ol.control.OverviewMap.prototype.validateExtent_ = function() { - var map = this.getMap(); - var ovmap = this.ovmap_; - - if (!map.isRendered() || !ovmap.isRendered()) { - return; - } - - var mapSize = /** @type {ol.Size} */ (map.getSize()); - - var view = map.getView(); - var extent = view.calculateExtent(mapSize); - - var ovmapSize = /** @type {ol.Size} */ (ovmap.getSize()); - - var ovview = ovmap.getView(); - var ovextent = ovview.calculateExtent(ovmapSize); - - var topLeftPixel = - ovmap.getPixelFromCoordinate(ol.extent.getTopLeft(extent)); - var bottomRightPixel = - ovmap.getPixelFromCoordinate(ol.extent.getBottomRight(extent)); - - var boxWidth = Math.abs(topLeftPixel[0] - bottomRightPixel[0]); - var boxHeight = Math.abs(topLeftPixel[1] - bottomRightPixel[1]); - - var ovmapWidth = ovmapSize[0]; - var ovmapHeight = ovmapSize[1]; - - if (boxWidth < ovmapWidth * ol.OVERVIEWMAP_MIN_RATIO || - boxHeight < ovmapHeight * ol.OVERVIEWMAP_MIN_RATIO || - boxWidth > ovmapWidth * ol.OVERVIEWMAP_MAX_RATIO || - boxHeight > ovmapHeight * ol.OVERVIEWMAP_MAX_RATIO) { - this.resetExtent_(); - } else if (!ol.extent.containsExtent(ovextent, extent)) { - this.recenter_(); - } -}; - - -/** - * Reset the overview map extent to half calculated min and max ratio times - * the extent of the main map. - * @private - */ -ol.control.OverviewMap.prototype.resetExtent_ = function() { - if (ol.OVERVIEWMAP_MAX_RATIO === 0 || ol.OVERVIEWMAP_MIN_RATIO === 0) { - return; - } - - var map = this.getMap(); - var ovmap = this.ovmap_; - - var mapSize = /** @type {ol.Size} */ (map.getSize()); - - var view = map.getView(); - var extent = view.calculateExtent(mapSize); - - var ovview = ovmap.getView(); - - // get how many times the current map overview could hold different - // box sizes using the min and max ratio, pick the step in the middle used - // to calculate the extent from the main map to set it to the overview map, - var steps = Math.log( - ol.OVERVIEWMAP_MAX_RATIO / ol.OVERVIEWMAP_MIN_RATIO) / Math.LN2; - var ratio = 1 / (Math.pow(2, steps / 2) * ol.OVERVIEWMAP_MIN_RATIO); - ol.extent.scaleFromCenter(extent, ratio); - ovview.fit(extent); -}; - - -/** - * Set the center of the overview map to the map center without changing its - * resolution. - * @private - */ -ol.control.OverviewMap.prototype.recenter_ = function() { - var map = this.getMap(); - var ovmap = this.ovmap_; - - var view = map.getView(); - - var ovview = ovmap.getView(); - - ovview.setCenter(view.getCenter()); -}; - - -/** - * Update the box using the main map extent - * @private - */ -ol.control.OverviewMap.prototype.updateBox_ = function() { - var map = this.getMap(); - var ovmap = this.ovmap_; - - if (!map.isRendered() || !ovmap.isRendered()) { - return; - } - - var mapSize = /** @type {ol.Size} */ (map.getSize()); - - var view = map.getView(); - - var ovview = ovmap.getView(); - - var rotation = view.getRotation(); - - var overlay = this.boxOverlay_; - var box = this.boxOverlay_.getElement(); - var extent = view.calculateExtent(mapSize); - var ovresolution = ovview.getResolution(); - var bottomLeft = ol.extent.getBottomLeft(extent); - var topRight = ol.extent.getTopRight(extent); - - // set position using bottom left coordinates - var rotateBottomLeft = this.calculateCoordinateRotate_(rotation, bottomLeft); - overlay.setPosition(rotateBottomLeft); - - // set box size calculated from map extent size and overview map resolution - if (box) { - box.style.width = Math.abs((bottomLeft[0] - topRight[0]) / ovresolution) + 'px'; - box.style.height = Math.abs((topRight[1] - bottomLeft[1]) / ovresolution) + 'px'; - } -}; - - -/** - * @param {number} rotation Target rotation. - * @param {ol.Coordinate} coordinate Coordinate. - * @return {ol.Coordinate|undefined} Coordinate for rotation and center anchor. - * @private - */ -ol.control.OverviewMap.prototype.calculateCoordinateRotate_ = function( - rotation, coordinate) { - var coordinateRotate; - - var map = this.getMap(); - var view = map.getView(); - - var currentCenter = view.getCenter(); - - if (currentCenter) { - coordinateRotate = [ - coordinate[0] - currentCenter[0], - coordinate[1] - currentCenter[1] - ]; - ol.coordinate.rotate(coordinateRotate, rotation); - ol.coordinate.add(coordinateRotate, currentCenter); - } - return coordinateRotate; -}; - - -/** - * @param {Event} event The event to handle - * @private - */ -ol.control.OverviewMap.prototype.handleClick_ = function(event) { - event.preventDefault(); - this.handleToggle_(); -}; - - -/** - * @private - */ -ol.control.OverviewMap.prototype.handleToggle_ = function() { - this.element.classList.toggle('ol-collapsed'); - if (this.collapsed_) { - ol.dom.replaceNode(this.collapseLabel_, this.label_); - } else { - ol.dom.replaceNode(this.label_, this.collapseLabel_); - } - this.collapsed_ = !this.collapsed_; - - // manage overview map if it had not been rendered before and control - // is expanded - var ovmap = this.ovmap_; - if (!this.collapsed_ && !ovmap.isRendered()) { - ovmap.updateSize(); - this.resetExtent_(); - ol.events.listenOnce(ovmap, ol.MapEventType.POSTRENDER, - function(event) { - this.updateBox_(); - }, - this); - } -}; - - -/** - * Return `true` if the overview map is collapsible, `false` otherwise. - * @return {boolean} True if the widget is collapsible. - * @api - */ -ol.control.OverviewMap.prototype.getCollapsible = function() { - return this.collapsible_; -}; - - -/** - * Set whether the overview map should be collapsible. - * @param {boolean} collapsible True if the widget is collapsible. - * @api - */ -ol.control.OverviewMap.prototype.setCollapsible = function(collapsible) { - if (this.collapsible_ === collapsible) { - return; - } - this.collapsible_ = collapsible; - this.element.classList.toggle('ol-uncollapsible'); - if (!collapsible && this.collapsed_) { - this.handleToggle_(); - } -}; - - -/** - * Collapse or expand the overview map according to the passed parameter. Will - * not do anything if the overview map isn't collapsible or if the current - * collapsed state is already the one requested. - * @param {boolean} collapsed True if the widget is collapsed. - * @api - */ -ol.control.OverviewMap.prototype.setCollapsed = function(collapsed) { - if (!this.collapsible_ || this.collapsed_ === collapsed) { - return; - } - this.handleToggle_(); -}; - - -/** - * Determine if the overview map is collapsed. - * @return {boolean} The overview map is collapsed. - * @api - */ -ol.control.OverviewMap.prototype.getCollapsed = function() { - return this.collapsed_; -}; - - -/** - * Return the overview map. - * @return {ol.PluggableMap} Overview map. - * @api - */ -ol.control.OverviewMap.prototype.getOverviewMap = function() { - return this.ovmap_; -}; - -goog.provide('ol.control.ScaleLineUnits'); - -/** - * Units for the scale line. Supported values are `'degrees'`, `'imperial'`, - * `'nautical'`, `'metric'`, `'us'`. - * @enum {string} - */ -ol.control.ScaleLineUnits = { - DEGREES: 'degrees', - IMPERIAL: 'imperial', - NAUTICAL: 'nautical', - METRIC: 'metric', - US: 'us' -}; - -goog.provide('ol.control.ScaleLine'); - -goog.require('ol'); -goog.require('ol.Object'); -goog.require('ol.asserts'); -goog.require('ol.control.Control'); -goog.require('ol.control.ScaleLineUnits'); -goog.require('ol.css'); -goog.require('ol.events'); -goog.require('ol.proj'); -goog.require('ol.proj.Units'); - - -/** - * @classdesc - * A control displaying rough y-axis distances, calculated for the center of the - * viewport. For conformal projections (e.g. EPSG:3857, the default view - * projection in OpenLayers), the scale is valid for all directions. - * No scale line will be shown when the y-axis distance of a pixel at the - * viewport center cannot be calculated in the view projection. - * By default the scale line will show in the bottom left portion of the map, - * but this can be changed by using the css selector `.ol-scale-line`. - * - * @constructor - * @extends {ol.control.Control} - * @param {olx.control.ScaleLineOptions=} opt_options Scale line options. - * @api - */ -ol.control.ScaleLine = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - var className = options.className !== undefined ? options.className : 'ol-scale-line'; - - /** - * @private - * @type {Element} - */ - this.innerElement_ = document.createElement('DIV'); - this.innerElement_.className = className + '-inner'; - - /** - * @private - * @type {Element} - */ - this.element_ = document.createElement('DIV'); - this.element_.className = className + ' ' + ol.css.CLASS_UNSELECTABLE; - this.element_.appendChild(this.innerElement_); - - /** - * @private - * @type {?olx.ViewState} - */ - this.viewState_ = null; - - /** - * @private - * @type {number} - */ - this.minWidth_ = options.minWidth !== undefined ? options.minWidth : 64; - - /** - * @private - * @type {boolean} - */ - this.renderedVisible_ = false; - - /** - * @private - * @type {number|undefined} - */ - this.renderedWidth_ = undefined; - - /** - * @private - * @type {string} - */ - this.renderedHTML_ = ''; - - var render = options.render ? options.render : ol.control.ScaleLine.render; - - ol.control.Control.call(this, { - element: this.element_, - render: render, - target: options.target - }); - - ol.events.listen( - this, ol.Object.getChangeEventType(ol.control.ScaleLine.Property_.UNITS), - this.handleUnitsChanged_, this); - - this.setUnits(/** @type {ol.control.ScaleLineUnits} */ (options.units) || - ol.control.ScaleLineUnits.METRIC); - -}; -ol.inherits(ol.control.ScaleLine, ol.control.Control); - - -/** - * @const - * @type {Array.<number>} - */ -ol.control.ScaleLine.LEADING_DIGITS = [1, 2, 5]; - - -/** - * Return the units to use in the scale line. - * @return {ol.control.ScaleLineUnits|undefined} The units to use in the scale - * line. - * @observable - * @api - */ -ol.control.ScaleLine.prototype.getUnits = function() { - return /** @type {ol.control.ScaleLineUnits|undefined} */ ( - this.get(ol.control.ScaleLine.Property_.UNITS)); -}; - - -/** - * Update the scale line element. - * @param {ol.MapEvent} mapEvent Map event. - * @this {ol.control.ScaleLine} - * @api - */ -ol.control.ScaleLine.render = function(mapEvent) { - var frameState = mapEvent.frameState; - if (!frameState) { - this.viewState_ = null; - } else { - this.viewState_ = frameState.viewState; - } - this.updateElement_(); -}; - - -/** - * @private - */ -ol.control.ScaleLine.prototype.handleUnitsChanged_ = function() { - this.updateElement_(); -}; - - -/** - * Set the units to use in the scale line. - * @param {ol.control.ScaleLineUnits} units The units to use in the scale line. - * @observable - * @api - */ -ol.control.ScaleLine.prototype.setUnits = function(units) { - this.set(ol.control.ScaleLine.Property_.UNITS, units); -}; - - -/** - * @private - */ -ol.control.ScaleLine.prototype.updateElement_ = function() { - var viewState = this.viewState_; - - if (!viewState) { - if (this.renderedVisible_) { - this.element_.style.display = 'none'; - this.renderedVisible_ = false; - } - return; - } - - var center = viewState.center; - var projection = viewState.projection; - var units = this.getUnits(); - var pointResolutionUnits = units == ol.control.ScaleLineUnits.DEGREES ? - ol.proj.Units.DEGREES : - ol.proj.Units.METERS; - var pointResolution = - ol.proj.getPointResolution(projection, viewState.resolution, center, pointResolutionUnits); - - var nominalCount = this.minWidth_ * pointResolution; - var suffix = ''; - if (units == ol.control.ScaleLineUnits.DEGREES) { - var metersPerDegree = ol.proj.METERS_PER_UNIT[ol.proj.Units.DEGREES]; - if (projection.getUnits() == ol.proj.Units.DEGREES) { - nominalCount *= metersPerDegree; - } else { - pointResolution /= metersPerDegree; - } - if (nominalCount < metersPerDegree / 60) { - suffix = '\u2033'; // seconds - pointResolution *= 3600; - } else if (nominalCount < metersPerDegree) { - suffix = '\u2032'; // minutes - pointResolution *= 60; - } else { - suffix = '\u00b0'; // degrees - } - } else if (units == ol.control.ScaleLineUnits.IMPERIAL) { - if (nominalCount < 0.9144) { - suffix = 'in'; - pointResolution /= 0.0254; - } else if (nominalCount < 1609.344) { - suffix = 'ft'; - pointResolution /= 0.3048; - } else { - suffix = 'mi'; - pointResolution /= 1609.344; - } - } else if (units == ol.control.ScaleLineUnits.NAUTICAL) { - pointResolution /= 1852; - suffix = 'nm'; - } else if (units == ol.control.ScaleLineUnits.METRIC) { - if (nominalCount < 0.001) { - suffix = 'μm'; - pointResolution *= 1000000; - } else if (nominalCount < 1) { - suffix = 'mm'; - pointResolution *= 1000; - } else if (nominalCount < 1000) { - suffix = 'm'; - } else { - suffix = 'km'; - pointResolution /= 1000; - } - } else if (units == ol.control.ScaleLineUnits.US) { - if (nominalCount < 0.9144) { - suffix = 'in'; - pointResolution *= 39.37; - } else if (nominalCount < 1609.344) { - suffix = 'ft'; - pointResolution /= 0.30480061; - } else { - suffix = 'mi'; - pointResolution /= 1609.3472; - } - } else { - ol.asserts.assert(false, 33); // Invalid units - } - - var i = 3 * Math.floor( - Math.log(this.minWidth_ * pointResolution) / Math.log(10)); - var count, width; - while (true) { - count = ol.control.ScaleLine.LEADING_DIGITS[((i % 3) + 3) % 3] * - Math.pow(10, Math.floor(i / 3)); - width = Math.round(count / pointResolution); - if (isNaN(width)) { - this.element_.style.display = 'none'; - this.renderedVisible_ = false; - return; - } else if (width >= this.minWidth_) { - break; - } - ++i; - } - - var html = count + ' ' + suffix; - if (this.renderedHTML_ != html) { - this.innerElement_.innerHTML = html; - this.renderedHTML_ = html; - } - - if (this.renderedWidth_ != width) { - this.innerElement_.style.width = width + 'px'; - this.renderedWidth_ = width; - } - - if (!this.renderedVisible_) { - this.element_.style.display = ''; - this.renderedVisible_ = true; - } - -}; - - -/** - * @enum {string} - * @private - */ -ol.control.ScaleLine.Property_ = { - UNITS: 'units' -}; - -// FIXME should possibly show tooltip when dragging? - -goog.provide('ol.control.ZoomSlider'); - -goog.require('ol'); -goog.require('ol.ViewHint'); -goog.require('ol.control.Control'); -goog.require('ol.css'); -goog.require('ol.easing'); -goog.require('ol.events'); -goog.require('ol.events.Event'); -goog.require('ol.events.EventType'); -goog.require('ol.math'); -goog.require('ol.pointer.EventType'); -goog.require('ol.pointer.PointerEventHandler'); - - -/** - * @classdesc - * A slider type of control for zooming. - * - * Example: - * - * map.addControl(new ol.control.ZoomSlider()); - * - * @constructor - * @extends {ol.control.Control} - * @param {olx.control.ZoomSliderOptions=} opt_options Zoom slider options. - * @api - */ -ol.control.ZoomSlider = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - /** - * Will hold the current resolution of the view. - * - * @type {number|undefined} - * @private - */ - this.currentResolution_ = undefined; - - /** - * The direction of the slider. Will be determined from actual display of the - * container and defaults to ol.control.ZoomSlider.Direction_.VERTICAL. - * - * @type {ol.control.ZoomSlider.Direction_} - * @private - */ - this.direction_ = ol.control.ZoomSlider.Direction_.VERTICAL; - - /** - * @type {boolean} - * @private - */ - this.dragging_; - - /** - * @type {number} - * @private - */ - this.heightLimit_ = 0; - - /** - * @type {number} - * @private - */ - this.widthLimit_ = 0; - - /** - * @type {number|undefined} - * @private - */ - this.previousX_; - - /** - * @type {number|undefined} - * @private - */ - this.previousY_; - - /** - * The calculated thumb size (border box plus margins). Set when initSlider_ - * is called. - * @type {ol.Size} - * @private - */ - this.thumbSize_ = null; - - /** - * Whether the slider is initialized. - * @type {boolean} - * @private - */ - this.sliderInitialized_ = false; - - /** - * @type {number} - * @private - */ - this.duration_ = options.duration !== undefined ? options.duration : 200; - - var className = options.className !== undefined ? options.className : 'ol-zoomslider'; - var thumbElement = document.createElement('button'); - thumbElement.setAttribute('type', 'button'); - thumbElement.className = className + '-thumb ' + ol.css.CLASS_UNSELECTABLE; - var containerElement = document.createElement('div'); - containerElement.className = className + ' ' + ol.css.CLASS_UNSELECTABLE + ' ' + ol.css.CLASS_CONTROL; - containerElement.appendChild(thumbElement); - /** - * @type {ol.pointer.PointerEventHandler} - * @private - */ - this.dragger_ = new ol.pointer.PointerEventHandler(containerElement); - - ol.events.listen(this.dragger_, ol.pointer.EventType.POINTERDOWN, - this.handleDraggerStart_, this); - ol.events.listen(this.dragger_, ol.pointer.EventType.POINTERMOVE, - this.handleDraggerDrag_, this); - ol.events.listen(this.dragger_, ol.pointer.EventType.POINTERUP, - this.handleDraggerEnd_, this); - - ol.events.listen(containerElement, ol.events.EventType.CLICK, - this.handleContainerClick_, this); - ol.events.listen(thumbElement, ol.events.EventType.CLICK, - ol.events.Event.stopPropagation); - - var render = options.render ? options.render : ol.control.ZoomSlider.render; - - ol.control.Control.call(this, { - element: containerElement, - render: render - }); -}; -ol.inherits(ol.control.ZoomSlider, ol.control.Control); - - -/** - * @inheritDoc - */ -ol.control.ZoomSlider.prototype.disposeInternal = function() { - this.dragger_.dispose(); - ol.control.Control.prototype.disposeInternal.call(this); -}; - - -/** - * The enum for available directions. - * - * @enum {number} - * @private - */ -ol.control.ZoomSlider.Direction_ = { - VERTICAL: 0, - HORIZONTAL: 1 -}; - - -/** - * @inheritDoc - */ -ol.control.ZoomSlider.prototype.setMap = function(map) { - ol.control.Control.prototype.setMap.call(this, map); - if (map) { - map.render(); - } -}; - - -/** - * Initializes the slider element. This will determine and set this controls - * direction_ and also constrain the dragging of the thumb to always be within - * the bounds of the container. - * - * @private - */ -ol.control.ZoomSlider.prototype.initSlider_ = function() { - var container = this.element; - var containerSize = { - width: container.offsetWidth, height: container.offsetHeight - }; - - var thumb = container.firstElementChild; - var computedStyle = getComputedStyle(thumb); - var thumbWidth = thumb.offsetWidth + - parseFloat(computedStyle['marginRight']) + - parseFloat(computedStyle['marginLeft']); - var thumbHeight = thumb.offsetHeight + - parseFloat(computedStyle['marginTop']) + - parseFloat(computedStyle['marginBottom']); - this.thumbSize_ = [thumbWidth, thumbHeight]; - - if (containerSize.width > containerSize.height) { - this.direction_ = ol.control.ZoomSlider.Direction_.HORIZONTAL; - this.widthLimit_ = containerSize.width - thumbWidth; - } else { - this.direction_ = ol.control.ZoomSlider.Direction_.VERTICAL; - this.heightLimit_ = containerSize.height - thumbHeight; - } - this.sliderInitialized_ = true; -}; - - -/** - * Update the zoomslider element. - * @param {ol.MapEvent} mapEvent Map event. - * @this {ol.control.ZoomSlider} - * @api - */ -ol.control.ZoomSlider.render = function(mapEvent) { - if (!mapEvent.frameState) { - return; - } - if (!this.sliderInitialized_) { - this.initSlider_(); - } - var res = mapEvent.frameState.viewState.resolution; - if (res !== this.currentResolution_) { - this.currentResolution_ = res; - this.setThumbPosition_(res); - } -}; - - -/** - * @param {Event} event The browser event to handle. - * @private - */ -ol.control.ZoomSlider.prototype.handleContainerClick_ = function(event) { - var view = this.getMap().getView(); - - var relativePosition = this.getRelativePosition_( - event.offsetX - this.thumbSize_[0] / 2, - event.offsetY - this.thumbSize_[1] / 2); - - var resolution = this.getResolutionForPosition_(relativePosition); - - view.animate({ - resolution: view.constrainResolution(resolution), - duration: this.duration_, - easing: ol.easing.easeOut - }); -}; - - -/** - * Handle dragger start events. - * @param {ol.pointer.PointerEvent} event The drag event. - * @private - */ -ol.control.ZoomSlider.prototype.handleDraggerStart_ = function(event) { - if (!this.dragging_ && event.originalEvent.target === this.element.firstElementChild) { - this.getMap().getView().setHint(ol.ViewHint.INTERACTING, 1); - this.previousX_ = event.clientX; - this.previousY_ = event.clientY; - this.dragging_ = true; - } -}; - - -/** - * Handle dragger drag events. - * - * @param {ol.pointer.PointerEvent|Event} event The drag event. - * @private - */ -ol.control.ZoomSlider.prototype.handleDraggerDrag_ = function(event) { - if (this.dragging_) { - var element = this.element.firstElementChild; - var deltaX = event.clientX - this.previousX_ + parseInt(element.style.left, 10); - var deltaY = event.clientY - this.previousY_ + parseInt(element.style.top, 10); - var relativePosition = this.getRelativePosition_(deltaX, deltaY); - this.currentResolution_ = this.getResolutionForPosition_(relativePosition); - this.getMap().getView().setResolution(this.currentResolution_); - this.setThumbPosition_(this.currentResolution_); - this.previousX_ = event.clientX; - this.previousY_ = event.clientY; - } -}; - - -/** - * Handle dragger end events. - * @param {ol.pointer.PointerEvent|Event} event The drag event. - * @private - */ -ol.control.ZoomSlider.prototype.handleDraggerEnd_ = function(event) { - if (this.dragging_) { - var view = this.getMap().getView(); - view.setHint(ol.ViewHint.INTERACTING, -1); - - view.animate({ - resolution: view.constrainResolution(this.currentResolution_), - duration: this.duration_, - easing: ol.easing.easeOut - }); - - this.dragging_ = false; - this.previousX_ = undefined; - this.previousY_ = undefined; - } -}; - - -/** - * Positions the thumb inside its container according to the given resolution. - * - * @param {number} res The res. - * @private - */ -ol.control.ZoomSlider.prototype.setThumbPosition_ = function(res) { - var position = this.getPositionForResolution_(res); - var thumb = this.element.firstElementChild; - - if (this.direction_ == ol.control.ZoomSlider.Direction_.HORIZONTAL) { - thumb.style.left = this.widthLimit_ * position + 'px'; - } else { - thumb.style.top = this.heightLimit_ * position + 'px'; - } -}; - - -/** - * Calculates the relative position of the thumb given x and y offsets. The - * relative position scales from 0 to 1. The x and y offsets are assumed to be - * in pixel units within the dragger limits. - * - * @param {number} x Pixel position relative to the left of the slider. - * @param {number} y Pixel position relative to the top of the slider. - * @return {number} The relative position of the thumb. - * @private - */ -ol.control.ZoomSlider.prototype.getRelativePosition_ = function(x, y) { - var amount; - if (this.direction_ === ol.control.ZoomSlider.Direction_.HORIZONTAL) { - amount = x / this.widthLimit_; - } else { - amount = y / this.heightLimit_; - } - return ol.math.clamp(amount, 0, 1); -}; - - -/** - * Calculates the corresponding resolution of the thumb given its relative - * position (where 0 is the minimum and 1 is the maximum). - * - * @param {number} position The relative position of the thumb. - * @return {number} The corresponding resolution. - * @private - */ -ol.control.ZoomSlider.prototype.getResolutionForPosition_ = function(position) { - var fn = this.getMap().getView().getResolutionForValueFunction(); - return fn(1 - position); -}; - - -/** - * Determines the relative position of the slider for the given resolution. A - * relative position of 0 corresponds to the minimum view resolution. A - * relative position of 1 corresponds to the maximum view resolution. - * - * @param {number} res The resolution. - * @return {number} The relative position value (between 0 and 1). - * @private - */ -ol.control.ZoomSlider.prototype.getPositionForResolution_ = function(res) { - var fn = this.getMap().getView().getValueForResolutionFunction(); - return 1 - fn(res); -}; - -goog.provide('ol.control.ZoomToExtent'); - -goog.require('ol'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.control.Control'); -goog.require('ol.css'); - - -/** - * @classdesc - * A button control which, when pressed, changes the map view to a specific - * extent. To style this control use the css selector `.ol-zoom-extent`. - * - * @constructor - * @extends {ol.control.Control} - * @param {olx.control.ZoomToExtentOptions=} opt_options Options. - * @api - */ -ol.control.ZoomToExtent = function(opt_options) { - var options = opt_options ? opt_options : {}; - - /** - * @type {ol.Extent} - * @private - */ - this.extent_ = options.extent ? options.extent : null; - - var className = options.className !== undefined ? options.className : - 'ol-zoom-extent'; - - var label = options.label !== undefined ? options.label : 'E'; - var tipLabel = options.tipLabel !== undefined ? - options.tipLabel : 'Fit to extent'; - var button = document.createElement('button'); - button.setAttribute('type', 'button'); - button.title = tipLabel; - button.appendChild( - typeof label === 'string' ? document.createTextNode(label) : label - ); - - ol.events.listen(button, ol.events.EventType.CLICK, - this.handleClick_, this); - - var cssClasses = className + ' ' + ol.css.CLASS_UNSELECTABLE + ' ' + - ol.css.CLASS_CONTROL; - var element = document.createElement('div'); - element.className = cssClasses; - element.appendChild(button); - - ol.control.Control.call(this, { - element: element, - target: options.target - }); -}; -ol.inherits(ol.control.ZoomToExtent, ol.control.Control); - - -/** - * @param {Event} event The event to handle - * @private - */ -ol.control.ZoomToExtent.prototype.handleClick_ = function(event) { - event.preventDefault(); - this.handleZoomToExtent_(); -}; - - -/** - * @private - */ -ol.control.ZoomToExtent.prototype.handleZoomToExtent_ = function() { - var map = this.getMap(); - var view = map.getView(); - var extent = !this.extent_ ? view.getProjection().getExtent() : this.extent_; - view.fit(extent); -}; - -goog.provide('ol.DeviceOrientation'); - -goog.require('ol.events'); -goog.require('ol'); -goog.require('ol.Object'); -goog.require('ol.has'); -goog.require('ol.math'); - - -/** - * @classdesc - * The ol.DeviceOrientation class provides access to information from - * DeviceOrientation events. See the [HTML 5 DeviceOrientation Specification]( - * http://www.w3.org/TR/orientation-event/) for more details. - * - * Many new computers, and especially mobile phones - * and tablets, provide hardware support for device orientation. Web - * developers targeting mobile devices will be especially interested in this - * class. - * - * Device orientation data are relative to a common starting point. For mobile - * devices, the starting point is to lay your phone face up on a table with the - * top of the phone pointing north. This represents the zero state. All - * angles are then relative to this state. For computers, it is the same except - * the screen is open at 90 degrees. - * - * Device orientation is reported as three angles - `alpha`, `beta`, and - * `gamma` - relative to the starting position along the three planar axes X, Y - * and Z. The X axis runs from the left edge to the right edge through the - * middle of the device. Similarly, the Y axis runs from the bottom to the top - * of the device through the middle. The Z axis runs from the back to the front - * through the middle. In the starting position, the X axis points to the - * right, the Y axis points away from you and the Z axis points straight up - * from the device lying flat. - * - * The three angles representing the device orientation are relative to the - * three axes. `alpha` indicates how much the device has been rotated around the - * Z axis, which is commonly interpreted as the compass heading (see note - * below). `beta` indicates how much the device has been rotated around the X - * axis, or how much it is tilted from front to back. `gamma` indicates how - * much the device has been rotated around the Y axis, or how much it is tilted - * from left to right. - * - * For most browsers, the `alpha` value returns the compass heading so if the - * device points north, it will be 0. With Safari on iOS, the 0 value of - * `alpha` is calculated from when device orientation was first requested. - * ol.DeviceOrientation provides the `heading` property which normalizes this - * behavior across all browsers for you. - * - * It is important to note that the HTML 5 DeviceOrientation specification - * indicates that `alpha`, `beta` and `gamma` are in degrees while the - * equivalent properties in ol.DeviceOrientation are in radians for consistency - * with all other uses of angles throughout OpenLayers. - * - * To get notified of device orientation changes, register a listener for the - * generic `change` event on your `ol.DeviceOrientation` instance. - * - * @see {@link http://www.w3.org/TR/orientation-event/} - * - * @deprecated This class is deprecated and will removed in the next major release. - * - * @constructor - * @extends {ol.Object} - * @param {olx.DeviceOrientationOptions=} opt_options Options. - * @api - */ -ol.DeviceOrientation = function(opt_options) { - - ol.Object.call(this); - - var options = opt_options ? opt_options : {}; - - /** - * @private - * @type {?ol.EventsKey} - */ - this.listenerKey_ = null; - - ol.events.listen(this, - ol.Object.getChangeEventType(ol.DeviceOrientation.Property_.TRACKING), - this.handleTrackingChanged_, this); - - this.setTracking(options.tracking !== undefined ? options.tracking : false); - -}; -ol.inherits(ol.DeviceOrientation, ol.Object); - - -/** - * @inheritDoc - */ -ol.DeviceOrientation.prototype.disposeInternal = function() { - this.setTracking(false); - ol.Object.prototype.disposeInternal.call(this); -}; - - -/** - * @private - * @param {Event} originalEvent Event. - */ -ol.DeviceOrientation.prototype.orientationChange_ = function(originalEvent) { - var event = /** @type {DeviceOrientationEvent} */ (originalEvent); - if (event.alpha !== null) { - var alpha = ol.math.toRadians(event.alpha); - this.set(ol.DeviceOrientation.Property_.ALPHA, alpha); - // event.absolute is undefined in iOS. - if (typeof event.absolute === 'boolean' && event.absolute) { - this.set(ol.DeviceOrientation.Property_.HEADING, alpha); - } else if (typeof event.webkitCompassHeading === 'number' && - event.webkitCompassAccuracy != -1) { - var heading = ol.math.toRadians(event.webkitCompassHeading); - this.set(ol.DeviceOrientation.Property_.HEADING, heading); - } - } - if (event.beta !== null) { - this.set(ol.DeviceOrientation.Property_.BETA, - ol.math.toRadians(event.beta)); - } - if (event.gamma !== null) { - this.set(ol.DeviceOrientation.Property_.GAMMA, - ol.math.toRadians(event.gamma)); - } - this.changed(); -}; - - -/** - * Rotation around the device z-axis (in radians). - * @return {number|undefined} The euler angle in radians of the device from the - * standard Z axis. - * @observable - * @api - */ -ol.DeviceOrientation.prototype.getAlpha = function() { - return /** @type {number|undefined} */ ( - this.get(ol.DeviceOrientation.Property_.ALPHA)); -}; - - -/** - * Rotation around the device x-axis (in radians). - * @return {number|undefined} The euler angle in radians of the device from the - * planar X axis. - * @observable - * @api - */ -ol.DeviceOrientation.prototype.getBeta = function() { - return /** @type {number|undefined} */ ( - this.get(ol.DeviceOrientation.Property_.BETA)); -}; - - -/** - * Rotation around the device y-axis (in radians). - * @return {number|undefined} The euler angle in radians of the device from the - * planar Y axis. - * @observable - * @api - */ -ol.DeviceOrientation.prototype.getGamma = function() { - return /** @type {number|undefined} */ ( - this.get(ol.DeviceOrientation.Property_.GAMMA)); -}; - - -/** - * The heading of the device relative to north (in radians). - * @return {number|undefined} The heading of the device relative to north, in - * radians, normalizing for different browser behavior. - * @observable - * @api - */ -ol.DeviceOrientation.prototype.getHeading = function() { - return /** @type {number|undefined} */ ( - this.get(ol.DeviceOrientation.Property_.HEADING)); -}; - - -/** - * Determine if orientation is being tracked. - * @return {boolean} Changes in device orientation are being tracked. - * @observable - * @api - */ -ol.DeviceOrientation.prototype.getTracking = function() { - return /** @type {boolean} */ ( - this.get(ol.DeviceOrientation.Property_.TRACKING)); -}; - - -/** - * @private - */ -ol.DeviceOrientation.prototype.handleTrackingChanged_ = function() { - if (ol.has.DEVICE_ORIENTATION) { - var tracking = this.getTracking(); - if (tracking && !this.listenerKey_) { - this.listenerKey_ = ol.events.listen(window, 'deviceorientation', - this.orientationChange_, this); - } else if (!tracking && this.listenerKey_ !== null) { - ol.events.unlistenByKey(this.listenerKey_); - this.listenerKey_ = null; - } - } -}; - - -/** - * Enable or disable tracking of device orientation events. - * @param {boolean} tracking The status of tracking changes to alpha, beta and - * gamma. If true, changes are tracked and reported immediately. - * @observable - * @api - */ -ol.DeviceOrientation.prototype.setTracking = function(tracking) { - this.set(ol.DeviceOrientation.Property_.TRACKING, tracking); -}; - - -/** - * @enum {string} - * @private - */ -ol.DeviceOrientation.Property_ = { - ALPHA: 'alpha', - BETA: 'beta', - GAMMA: 'gamma', - HEADING: 'heading', - TRACKING: 'tracking' -}; - -goog.provide('ol.style.Image'); - - -/** - * @classdesc - * A base class used for creating subclasses and not instantiated in - * apps. Base class for {@link ol.style.Icon}, {@link ol.style.Circle} and - * {@link ol.style.RegularShape}. - * - * @constructor - * @abstract - * @param {ol.StyleImageOptions} options Options. - * @api - */ -ol.style.Image = function(options) { - - /** - * @private - * @type {number} - */ - this.opacity_ = options.opacity; - - /** - * @private - * @type {boolean} - */ - this.rotateWithView_ = options.rotateWithView; - - /** - * @private - * @type {number} - */ - this.rotation_ = options.rotation; - - /** - * @private - * @type {number} - */ - this.scale_ = options.scale; - - /** - * @private - * @type {boolean} - */ - this.snapToPixel_ = options.snapToPixel; - -}; - - -/** - * Get the symbolizer opacity. - * @return {number} Opacity. - * @api - */ -ol.style.Image.prototype.getOpacity = function() { - return this.opacity_; -}; - - -/** - * Determine whether the symbolizer rotates with the map. - * @return {boolean} Rotate with map. - * @api - */ -ol.style.Image.prototype.getRotateWithView = function() { - return this.rotateWithView_; -}; - - -/** - * Get the symoblizer rotation. - * @return {number} Rotation. - * @api - */ -ol.style.Image.prototype.getRotation = function() { - return this.rotation_; -}; - - -/** - * Get the symbolizer scale. - * @return {number} Scale. - * @api - */ -ol.style.Image.prototype.getScale = function() { - return this.scale_; -}; - - -/** - * Determine whether the symbolizer should be snapped to a pixel. - * @return {boolean} The symbolizer should snap to a pixel. - * @api - */ -ol.style.Image.prototype.getSnapToPixel = function() { - return this.snapToPixel_; -}; - - -/** - * Get the anchor point in pixels. The anchor determines the center point for the - * symbolizer. - * @abstract - * @return {Array.<number>} Anchor. - */ -ol.style.Image.prototype.getAnchor = function() {}; - - -/** - * Get the image element for the symbolizer. - * @abstract - * @param {number} pixelRatio Pixel ratio. - * @return {HTMLCanvasElement|HTMLVideoElement|Image} Image element. - */ -ol.style.Image.prototype.getImage = function(pixelRatio) {}; - - -/** - * @abstract - * @param {number} pixelRatio Pixel ratio. - * @return {HTMLCanvasElement|HTMLVideoElement|Image} Image element. - */ -ol.style.Image.prototype.getHitDetectionImage = function(pixelRatio) {}; - - -/** - * @abstract - * @return {ol.ImageState} Image state. - */ -ol.style.Image.prototype.getImageState = function() {}; - - -/** - * @abstract - * @return {ol.Size} Image size. - */ -ol.style.Image.prototype.getImageSize = function() {}; - - -/** - * @abstract - * @return {ol.Size} Size of the hit-detection image. - */ -ol.style.Image.prototype.getHitDetectionImageSize = function() {}; - - -/** - * Get the origin of the symbolizer. - * @abstract - * @return {Array.<number>} Origin. - */ -ol.style.Image.prototype.getOrigin = function() {}; - - -/** - * Get the size of the symbolizer (in pixels). - * @abstract - * @return {ol.Size} Size. - */ -ol.style.Image.prototype.getSize = function() {}; - - -/** - * Set the opacity. - * - * @param {number} opacity Opacity. - * @api - */ -ol.style.Image.prototype.setOpacity = function(opacity) { - this.opacity_ = opacity; -}; - - -/** - * Set whether to rotate the style with the view. - * - * @param {boolean} rotateWithView Rotate with map. - */ -ol.style.Image.prototype.setRotateWithView = function(rotateWithView) { - this.rotateWithView_ = rotateWithView; -}; - - -/** - * Set the rotation. - * - * @param {number} rotation Rotation. - * @api - */ -ol.style.Image.prototype.setRotation = function(rotation) { - this.rotation_ = rotation; -}; - - -/** - * Set the scale. - * - * @param {number} scale Scale. - * @api - */ -ol.style.Image.prototype.setScale = function(scale) { - this.scale_ = scale; -}; - - -/** - * Set whether to snap the image to the closest pixel. - * - * @param {boolean} snapToPixel Snap to pixel? - */ -ol.style.Image.prototype.setSnapToPixel = function(snapToPixel) { - this.snapToPixel_ = snapToPixel; -}; - - -/** - * @abstract - * @param {function(this: T, ol.events.Event)} listener Listener function. - * @param {T} thisArg Value to use as `this` when executing `listener`. - * @return {ol.EventsKey|undefined} Listener key. - * @template T - */ -ol.style.Image.prototype.listenImageChange = function(listener, thisArg) {}; - - -/** - * Load not yet loaded URI. - * @abstract - */ -ol.style.Image.prototype.load = function() {}; - - -/** - * @abstract - * @param {function(this: T, ol.events.Event)} listener Listener function. - * @param {T} thisArg Value to use as `this` when executing `listener`. - * @template T - */ -ol.style.Image.prototype.unlistenImageChange = function(listener, thisArg) {}; - -goog.provide('ol.style.RegularShape'); - -goog.require('ol'); -goog.require('ol.colorlike'); -goog.require('ol.dom'); -goog.require('ol.has'); -goog.require('ol.ImageState'); -goog.require('ol.render.canvas'); -goog.require('ol.style.Image'); - - -/** - * @classdesc - * Set regular shape style for vector features. The resulting shape will be - * a regular polygon when `radius` is provided, or a star when `radius1` and - * `radius2` are provided. - * - * @constructor - * @param {olx.style.RegularShapeOptions} options Options. - * @extends {ol.style.Image} - * @api - */ -ol.style.RegularShape = function(options) { - /** - * @private - * @type {Array.<string>} - */ - this.checksums_ = null; - - /** - * @private - * @type {HTMLCanvasElement} - */ - this.canvas_ = null; - - /** - * @private - * @type {HTMLCanvasElement} - */ - this.hitDetectionCanvas_ = null; - - /** - * @private - * @type {ol.style.Fill} - */ - this.fill_ = options.fill !== undefined ? options.fill : null; - - /** - * @private - * @type {Array.<number>} - */ - this.origin_ = [0, 0]; - - /** - * @private - * @type {number} - */ - this.points_ = options.points; - - /** - * @protected - * @type {number} - */ - this.radius_ = /** @type {number} */ (options.radius !== undefined ? - options.radius : options.radius1); - - /** - * @private - * @type {number|undefined} - */ - this.radius2_ = options.radius2; - - /** - * @private - * @type {number} - */ - this.angle_ = options.angle !== undefined ? options.angle : 0; - - /** - * @private - * @type {ol.style.Stroke} - */ - this.stroke_ = options.stroke !== undefined ? options.stroke : null; - - /** - * @private - * @type {Array.<number>} - */ - this.anchor_ = null; - - /** - * @private - * @type {ol.Size} - */ - this.size_ = null; - - /** - * @private - * @type {ol.Size} - */ - this.imageSize_ = null; - - /** - * @private - * @type {ol.Size} - */ - this.hitDetectionImageSize_ = null; - - /** - * @protected - * @type {ol.style.AtlasManager|undefined} - */ - this.atlasManager_ = options.atlasManager; - - this.render_(this.atlasManager_); - - /** - * @type {boolean} - */ - var snapToPixel = options.snapToPixel !== undefined ? - options.snapToPixel : true; - - /** - * @type {boolean} - */ - var rotateWithView = options.rotateWithView !== undefined ? - options.rotateWithView : false; - - ol.style.Image.call(this, { - opacity: 1, - rotateWithView: rotateWithView, - rotation: options.rotation !== undefined ? options.rotation : 0, - scale: 1, - snapToPixel: snapToPixel - }); -}; -ol.inherits(ol.style.RegularShape, ol.style.Image); - - -/** - * Clones the style. If an atlasmanager was provided to the original style it will be used in the cloned style, too. - * @return {ol.style.RegularShape} The cloned style. - * @api - */ -ol.style.RegularShape.prototype.clone = function() { - var style = new ol.style.RegularShape({ - fill: this.getFill() ? this.getFill().clone() : undefined, - points: this.getPoints(), - radius: this.getRadius(), - radius2: this.getRadius2(), - angle: this.getAngle(), - snapToPixel: this.getSnapToPixel(), - stroke: this.getStroke() ? this.getStroke().clone() : undefined, - rotation: this.getRotation(), - rotateWithView: this.getRotateWithView(), - atlasManager: this.atlasManager_ - }); - style.setOpacity(this.getOpacity()); - style.setScale(this.getScale()); - return style; -}; - - -/** - * @inheritDoc - * @api - */ -ol.style.RegularShape.prototype.getAnchor = function() { - return this.anchor_; -}; - - -/** - * Get the angle used in generating the shape. - * @return {number} Shape's rotation in radians. - * @api - */ -ol.style.RegularShape.prototype.getAngle = function() { - return this.angle_; -}; - - -/** - * Get the fill style for the shape. - * @return {ol.style.Fill} Fill style. - * @api - */ -ol.style.RegularShape.prototype.getFill = function() { - return this.fill_; -}; - - -/** - * @inheritDoc - */ -ol.style.RegularShape.prototype.getHitDetectionImage = function(pixelRatio) { - return this.hitDetectionCanvas_; -}; - - -/** - * @inheritDoc - * @api - */ -ol.style.RegularShape.prototype.getImage = function(pixelRatio) { - return this.canvas_; -}; - - -/** - * @inheritDoc - */ -ol.style.RegularShape.prototype.getImageSize = function() { - return this.imageSize_; -}; - - -/** - * @inheritDoc - */ -ol.style.RegularShape.prototype.getHitDetectionImageSize = function() { - return this.hitDetectionImageSize_; -}; - - -/** - * @inheritDoc - */ -ol.style.RegularShape.prototype.getImageState = function() { - return ol.ImageState.LOADED; -}; - - -/** - * @inheritDoc - * @api - */ -ol.style.RegularShape.prototype.getOrigin = function() { - return this.origin_; -}; - - -/** - * Get the number of points for generating the shape. - * @return {number} Number of points for stars and regular polygons. - * @api - */ -ol.style.RegularShape.prototype.getPoints = function() { - return this.points_; -}; - - -/** - * Get the (primary) radius for the shape. - * @return {number} Radius. - * @api - */ -ol.style.RegularShape.prototype.getRadius = function() { - return this.radius_; -}; - - -/** - * Get the secondary radius for the shape. - * @return {number|undefined} Radius2. - * @api - */ -ol.style.RegularShape.prototype.getRadius2 = function() { - return this.radius2_; -}; - - -/** - * @inheritDoc - * @api - */ -ol.style.RegularShape.prototype.getSize = function() { - return this.size_; -}; - - -/** - * Get the stroke style for the shape. - * @return {ol.style.Stroke} Stroke style. - * @api - */ -ol.style.RegularShape.prototype.getStroke = function() { - return this.stroke_; -}; - - -/** - * @inheritDoc - */ -ol.style.RegularShape.prototype.listenImageChange = function(listener, thisArg) {}; - - -/** - * @inheritDoc - */ -ol.style.RegularShape.prototype.load = function() {}; - - -/** - * @inheritDoc - */ -ol.style.RegularShape.prototype.unlistenImageChange = function(listener, thisArg) {}; - - -/** - * @protected - * @param {ol.style.AtlasManager|undefined} atlasManager An atlas manager. - */ -ol.style.RegularShape.prototype.render_ = function(atlasManager) { - var imageSize; - var lineCap = ''; - var lineJoin = ''; - var miterLimit = 0; - var lineDash = null; - var lineDashOffset = 0; - var strokeStyle; - var strokeWidth = 0; - - if (this.stroke_) { - strokeStyle = this.stroke_.getColor(); - if (strokeStyle === null) { - strokeStyle = ol.render.canvas.defaultStrokeStyle; - } - strokeStyle = ol.colorlike.asColorLike(strokeStyle); - strokeWidth = this.stroke_.getWidth(); - if (strokeWidth === undefined) { - strokeWidth = ol.render.canvas.defaultLineWidth; - } - lineDash = this.stroke_.getLineDash(); - lineDashOffset = this.stroke_.getLineDashOffset(); - if (!ol.has.CANVAS_LINE_DASH) { - lineDash = null; - lineDashOffset = 0; - } - lineJoin = this.stroke_.getLineJoin(); - if (lineJoin === undefined) { - lineJoin = ol.render.canvas.defaultLineJoin; - } - lineCap = this.stroke_.getLineCap(); - if (lineCap === undefined) { - lineCap = ol.render.canvas.defaultLineCap; - } - miterLimit = this.stroke_.getMiterLimit(); - if (miterLimit === undefined) { - miterLimit = ol.render.canvas.defaultMiterLimit; - } - } - - var size = 2 * (this.radius_ + strokeWidth) + 1; - - /** @type {ol.RegularShapeRenderOptions} */ - var renderOptions = { - strokeStyle: strokeStyle, - strokeWidth: strokeWidth, - size: size, - lineCap: lineCap, - lineDash: lineDash, - lineDashOffset: lineDashOffset, - lineJoin: lineJoin, - miterLimit: miterLimit - }; - - if (atlasManager === undefined) { - // no atlas manager is used, create a new canvas - var context = ol.dom.createCanvasContext2D(size, size); - this.canvas_ = context.canvas; - - // canvas.width and height are rounded to the closest integer - size = this.canvas_.width; - imageSize = size; - - this.draw_(renderOptions, context, 0, 0); - - this.createHitDetectionCanvas_(renderOptions); - } else { - // an atlas manager is used, add the symbol to an atlas - size = Math.round(size); - - var hasCustomHitDetectionImage = !this.fill_; - var renderHitDetectionCallback; - if (hasCustomHitDetectionImage) { - // render the hit-detection image into a separate atlas image - renderHitDetectionCallback = - this.drawHitDetectionCanvas_.bind(this, renderOptions); - } - - var id = this.getChecksum(); - var info = atlasManager.add( - id, size, size, this.draw_.bind(this, renderOptions), - renderHitDetectionCallback); - - this.canvas_ = info.image; - this.origin_ = [info.offsetX, info.offsetY]; - imageSize = info.image.width; - - if (hasCustomHitDetectionImage) { - this.hitDetectionCanvas_ = info.hitImage; - this.hitDetectionImageSize_ = - [info.hitImage.width, info.hitImage.height]; - } else { - this.hitDetectionCanvas_ = this.canvas_; - this.hitDetectionImageSize_ = [imageSize, imageSize]; - } - } - - this.anchor_ = [size / 2, size / 2]; - this.size_ = [size, size]; - this.imageSize_ = [imageSize, imageSize]; -}; - - -/** - * @private - * @param {ol.RegularShapeRenderOptions} renderOptions Render options. - * @param {CanvasRenderingContext2D} context The rendering context. - * @param {number} x The origin for the symbol (x). - * @param {number} y The origin for the symbol (y). - */ -ol.style.RegularShape.prototype.draw_ = function(renderOptions, context, x, y) { - var i, angle0, radiusC; - // reset transform - context.setTransform(1, 0, 0, 1, 0, 0); - - // then move to (x, y) - context.translate(x, y); - - context.beginPath(); - - var points = this.points_; - if (points === Infinity) { - context.arc( - renderOptions.size / 2, renderOptions.size / 2, - this.radius_, 0, 2 * Math.PI, true); - } else { - var radius2 = (this.radius2_ !== undefined) ? this.radius2_ - : this.radius_; - if (radius2 !== this.radius_) { - points = 2 * points; - } - for (i = 0; i <= points; i++) { - angle0 = i * 2 * Math.PI / points - Math.PI / 2 + this.angle_; - radiusC = i % 2 === 0 ? this.radius_ : radius2; - context.lineTo(renderOptions.size / 2 + radiusC * Math.cos(angle0), - renderOptions.size / 2 + radiusC * Math.sin(angle0)); - } - } - - - if (this.fill_) { - var color = this.fill_.getColor(); - if (color === null) { - color = ol.render.canvas.defaultFillStyle; - } - context.fillStyle = ol.colorlike.asColorLike(color); - context.fill(); - } - if (this.stroke_) { - context.strokeStyle = renderOptions.strokeStyle; - context.lineWidth = renderOptions.strokeWidth; - if (renderOptions.lineDash) { - context.setLineDash(renderOptions.lineDash); - context.lineDashOffset = renderOptions.lineDashOffset; - } - context.lineCap = renderOptions.lineCap; - context.lineJoin = renderOptions.lineJoin; - context.miterLimit = renderOptions.miterLimit; - context.stroke(); - } - context.closePath(); -}; - - -/** - * @private - * @param {ol.RegularShapeRenderOptions} renderOptions Render options. - */ -ol.style.RegularShape.prototype.createHitDetectionCanvas_ = function(renderOptions) { - this.hitDetectionImageSize_ = [renderOptions.size, renderOptions.size]; - if (this.fill_) { - this.hitDetectionCanvas_ = this.canvas_; - return; - } - - // if no fill style is set, create an extra hit-detection image with a - // default fill style - var context = ol.dom.createCanvasContext2D(renderOptions.size, renderOptions.size); - this.hitDetectionCanvas_ = context.canvas; - - this.drawHitDetectionCanvas_(renderOptions, context, 0, 0); -}; - - -/** - * @private - * @param {ol.RegularShapeRenderOptions} renderOptions Render options. - * @param {CanvasRenderingContext2D} context The context. - * @param {number} x The origin for the symbol (x). - * @param {number} y The origin for the symbol (y). - */ -ol.style.RegularShape.prototype.drawHitDetectionCanvas_ = function(renderOptions, context, x, y) { - // reset transform - context.setTransform(1, 0, 0, 1, 0, 0); - - // then move to (x, y) - context.translate(x, y); - - context.beginPath(); - - var points = this.points_; - if (points === Infinity) { - context.arc( - renderOptions.size / 2, renderOptions.size / 2, - this.radius_, 0, 2 * Math.PI, true); - } else { - var radius2 = (this.radius2_ !== undefined) ? this.radius2_ - : this.radius_; - if (radius2 !== this.radius_) { - points = 2 * points; - } - var i, radiusC, angle0; - for (i = 0; i <= points; i++) { - angle0 = i * 2 * Math.PI / points - Math.PI / 2 + this.angle_; - radiusC = i % 2 === 0 ? this.radius_ : radius2; - context.lineTo(renderOptions.size / 2 + radiusC * Math.cos(angle0), - renderOptions.size / 2 + radiusC * Math.sin(angle0)); - } - } - - context.fillStyle = ol.render.canvas.defaultFillStyle; - context.fill(); - if (this.stroke_) { - context.strokeStyle = renderOptions.strokeStyle; - context.lineWidth = renderOptions.strokeWidth; - if (renderOptions.lineDash) { - context.setLineDash(renderOptions.lineDash); - context.lineDashOffset = renderOptions.lineDashOffset; - } - context.stroke(); - } - context.closePath(); -}; - - -/** - * @return {string} The checksum. - */ -ol.style.RegularShape.prototype.getChecksum = function() { - var strokeChecksum = this.stroke_ ? - this.stroke_.getChecksum() : '-'; - var fillChecksum = this.fill_ ? - this.fill_.getChecksum() : '-'; - - var recalculate = !this.checksums_ || - (strokeChecksum != this.checksums_[1] || - fillChecksum != this.checksums_[2] || - this.radius_ != this.checksums_[3] || - this.radius2_ != this.checksums_[4] || - this.angle_ != this.checksums_[5] || - this.points_ != this.checksums_[6]); - - if (recalculate) { - var checksum = 'r' + strokeChecksum + fillChecksum + - (this.radius_ !== undefined ? this.radius_.toString() : '-') + - (this.radius2_ !== undefined ? this.radius2_.toString() : '-') + - (this.angle_ !== undefined ? this.angle_.toString() : '-') + - (this.points_ !== undefined ? this.points_.toString() : '-'); - this.checksums_ = [checksum, strokeChecksum, fillChecksum, - this.radius_, this.radius2_, this.angle_, this.points_]; - } - - return this.checksums_[0]; -}; - -goog.provide('ol.style.Circle'); - -goog.require('ol'); -goog.require('ol.style.RegularShape'); - - -/** - * @classdesc - * Set circle style for vector features. - * - * @constructor - * @param {olx.style.CircleOptions=} opt_options Options. - * @extends {ol.style.RegularShape} - * @api - */ -ol.style.Circle = function(opt_options) { - - var options = opt_options || {}; - - ol.style.RegularShape.call(this, { - points: Infinity, - fill: options.fill, - radius: options.radius, - snapToPixel: options.snapToPixel, - stroke: options.stroke, - atlasManager: options.atlasManager - }); - -}; -ol.inherits(ol.style.Circle, ol.style.RegularShape); - - -/** - * Clones the style. If an atlasmanager was provided to the original style it will be used in the cloned style, too. - * @return {ol.style.Circle} The cloned style. - * @override - * @api - */ -ol.style.Circle.prototype.clone = function() { - var style = new ol.style.Circle({ - fill: this.getFill() ? this.getFill().clone() : undefined, - stroke: this.getStroke() ? this.getStroke().clone() : undefined, - radius: this.getRadius(), - snapToPixel: this.getSnapToPixel(), - atlasManager: this.atlasManager_ - }); - style.setOpacity(this.getOpacity()); - style.setScale(this.getScale()); - return style; -}; - - -/** - * Set the circle radius. - * - * @param {number} radius Circle radius. - * @api - */ -ol.style.Circle.prototype.setRadius = function(radius) { - this.radius_ = radius; - this.render_(this.atlasManager_); -}; - -goog.provide('ol.style.Fill'); - -goog.require('ol'); -goog.require('ol.color'); - - -/** - * @classdesc - * Set fill style for vector features. - * - * @constructor - * @param {olx.style.FillOptions=} opt_options Options. - * @api - */ -ol.style.Fill = function(opt_options) { - - var options = opt_options || {}; - - /** - * @private - * @type {ol.Color|ol.ColorLike} - */ - this.color_ = options.color !== undefined ? options.color : null; - - /** - * @private - * @type {string|undefined} - */ - this.checksum_ = undefined; -}; - - -/** - * Clones the style. The color is not cloned if it is an {@link ol.ColorLike}. - * @return {ol.style.Fill} The cloned style. - * @api - */ -ol.style.Fill.prototype.clone = function() { - var color = this.getColor(); - return new ol.style.Fill({ - color: (color && color.slice) ? color.slice() : color || undefined - }); -}; - - -/** - * Get the fill color. - * @return {ol.Color|ol.ColorLike} Color. - * @api - */ -ol.style.Fill.prototype.getColor = function() { - return this.color_; -}; - - -/** - * Set the color. - * - * @param {ol.Color|ol.ColorLike} color Color. - * @api - */ -ol.style.Fill.prototype.setColor = function(color) { - this.color_ = color; - this.checksum_ = undefined; -}; - - -/** - * @return {string} The checksum. - */ -ol.style.Fill.prototype.getChecksum = function() { - if (this.checksum_ === undefined) { - if ( - this.color_ instanceof CanvasPattern || - this.color_ instanceof CanvasGradient - ) { - this.checksum_ = ol.getUid(this.color_).toString(); - } else { - this.checksum_ = 'f' + (this.color_ ? - ol.color.asString(this.color_) : '-'); - } - } - - return this.checksum_; -}; - -goog.provide('ol.style.Stroke'); - -goog.require('ol'); - - -/** - * @classdesc - * Set stroke style for vector features. - * Note that the defaults given are the Canvas defaults, which will be used if - * option is not defined. The `get` functions return whatever was entered in - * the options; they will not return the default. - * - * @constructor - * @param {olx.style.StrokeOptions=} opt_options Options. - * @api - */ -ol.style.Stroke = function(opt_options) { - - var options = opt_options || {}; - - /** - * @private - * @type {ol.Color|ol.ColorLike} - */ - this.color_ = options.color !== undefined ? options.color : null; - - /** - * @private - * @type {string|undefined} - */ - this.lineCap_ = options.lineCap; - - /** - * @private - * @type {Array.<number>} - */ - this.lineDash_ = options.lineDash !== undefined ? options.lineDash : null; - - /** - * @private - * @type {number|undefined} - */ - this.lineDashOffset_ = options.lineDashOffset; - - /** - * @private - * @type {string|undefined} - */ - this.lineJoin_ = options.lineJoin; - - /** - * @private - * @type {number|undefined} - */ - this.miterLimit_ = options.miterLimit; - - /** - * @private - * @type {number|undefined} - */ - this.width_ = options.width; - - /** - * @private - * @type {string|undefined} - */ - this.checksum_ = undefined; -}; - - -/** - * Clones the style. - * @return {ol.style.Stroke} The cloned style. - * @api - */ -ol.style.Stroke.prototype.clone = function() { - var color = this.getColor(); - return new ol.style.Stroke({ - color: (color && color.slice) ? color.slice() : color || undefined, - lineCap: this.getLineCap(), - lineDash: this.getLineDash() ? this.getLineDash().slice() : undefined, - lineDashOffset: this.getLineDashOffset(), - lineJoin: this.getLineJoin(), - miterLimit: this.getMiterLimit(), - width: this.getWidth() - }); -}; - - -/** - * Get the stroke color. - * @return {ol.Color|ol.ColorLike} Color. - * @api - */ -ol.style.Stroke.prototype.getColor = function() { - return this.color_; -}; - - -/** - * Get the line cap type for the stroke. - * @return {string|undefined} Line cap. - * @api - */ -ol.style.Stroke.prototype.getLineCap = function() { - return this.lineCap_; -}; - - -/** - * Get the line dash style for the stroke. - * @return {Array.<number>} Line dash. - * @api - */ -ol.style.Stroke.prototype.getLineDash = function() { - return this.lineDash_; -}; - - -/** - * Get the line dash offset for the stroke. - * @return {number|undefined} Line dash offset. - * @api - */ -ol.style.Stroke.prototype.getLineDashOffset = function() { - return this.lineDashOffset_; -}; - - -/** - * Get the line join type for the stroke. - * @return {string|undefined} Line join. - * @api - */ -ol.style.Stroke.prototype.getLineJoin = function() { - return this.lineJoin_; -}; - - -/** - * Get the miter limit for the stroke. - * @return {number|undefined} Miter limit. - * @api - */ -ol.style.Stroke.prototype.getMiterLimit = function() { - return this.miterLimit_; -}; - - -/** - * Get the stroke width. - * @return {number|undefined} Width. - * @api - */ -ol.style.Stroke.prototype.getWidth = function() { - return this.width_; -}; - - -/** - * Set the color. - * - * @param {ol.Color|ol.ColorLike} color Color. - * @api - */ -ol.style.Stroke.prototype.setColor = function(color) { - this.color_ = color; - this.checksum_ = undefined; -}; - - -/** - * Set the line cap. - * - * @param {string|undefined} lineCap Line cap. - * @api - */ -ol.style.Stroke.prototype.setLineCap = function(lineCap) { - this.lineCap_ = lineCap; - this.checksum_ = undefined; -}; - - -/** - * Set the line dash. - * - * Please note that Internet Explorer 10 and lower [do not support][mdn] the - * `setLineDash` method on the `CanvasRenderingContext2D` and therefore this - * property will have no visual effect in these browsers. - * - * [mdn]: https://developer.mozilla.org/en-US/docs/Web/API/CanvasRenderingContext2D/setLineDash#Browser_compatibility - * - * @param {Array.<number>} lineDash Line dash. - * @api - */ -ol.style.Stroke.prototype.setLineDash = function(lineDash) { - this.lineDash_ = lineDash; - this.checksum_ = undefined; -}; - - -/** - * Set the line dash offset. - * - * @param {number|undefined} lineDashOffset Line dash offset. - * @api - */ -ol.style.Stroke.prototype.setLineDashOffset = function(lineDashOffset) { - this.lineDashOffset_ = lineDashOffset; - this.checksum_ = undefined; -}; - - -/** - * Set the line join. - * - * @param {string|undefined} lineJoin Line join. - * @api - */ -ol.style.Stroke.prototype.setLineJoin = function(lineJoin) { - this.lineJoin_ = lineJoin; - this.checksum_ = undefined; -}; - - -/** - * Set the miter limit. - * - * @param {number|undefined} miterLimit Miter limit. - * @api - */ -ol.style.Stroke.prototype.setMiterLimit = function(miterLimit) { - this.miterLimit_ = miterLimit; - this.checksum_ = undefined; -}; - - -/** - * Set the width. - * - * @param {number|undefined} width Width. - * @api - */ -ol.style.Stroke.prototype.setWidth = function(width) { - this.width_ = width; - this.checksum_ = undefined; -}; - - -/** - * @return {string} The checksum. - */ -ol.style.Stroke.prototype.getChecksum = function() { - if (this.checksum_ === undefined) { - this.checksum_ = 's'; - if (this.color_) { - if (typeof this.color_ === 'string') { - this.checksum_ += this.color_; - } else { - this.checksum_ += ol.getUid(this.color_).toString(); - } - } else { - this.checksum_ += '-'; - } - this.checksum_ += ',' + - (this.lineCap_ !== undefined ? - this.lineCap_.toString() : '-') + ',' + - (this.lineDash_ ? - this.lineDash_.toString() : '-') + ',' + - (this.lineDashOffset_ !== undefined ? - this.lineDashOffset_ : '-') + ',' + - (this.lineJoin_ !== undefined ? - this.lineJoin_ : '-') + ',' + - (this.miterLimit_ !== undefined ? - this.miterLimit_.toString() : '-') + ',' + - (this.width_ !== undefined ? - this.width_.toString() : '-'); - } - - return this.checksum_; -}; - -goog.provide('ol.style.Style'); - -goog.require('ol.asserts'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.style.Circle'); -goog.require('ol.style.Fill'); -goog.require('ol.style.Stroke'); - - -/** - * @classdesc - * Container for vector feature rendering styles. Any changes made to the style - * or its children through `set*()` methods will not take effect until the - * feature or layer that uses the style is re-rendered. - * - * @constructor - * @struct - * @param {olx.style.StyleOptions=} opt_options Style options. - * @api - */ -ol.style.Style = function(opt_options) { - - var options = opt_options || {}; - - /** - * @private - * @type {string|ol.geom.Geometry|ol.StyleGeometryFunction} - */ - this.geometry_ = null; - - /** - * @private - * @type {!ol.StyleGeometryFunction} - */ - this.geometryFunction_ = ol.style.Style.defaultGeometryFunction; - - if (options.geometry !== undefined) { - this.setGeometry(options.geometry); - } - - /** - * @private - * @type {ol.style.Fill} - */ - this.fill_ = options.fill !== undefined ? options.fill : null; - - /** - * @private - * @type {ol.style.Image} - */ - this.image_ = options.image !== undefined ? options.image : null; - - /** - * @private - * @type {ol.StyleRenderFunction|null} - */ - this.renderer_ = options.renderer !== undefined ? options.renderer : null; - - /** - * @private - * @type {ol.style.Stroke} - */ - this.stroke_ = options.stroke !== undefined ? options.stroke : null; - - /** - * @private - * @type {ol.style.Text} - */ - this.text_ = options.text !== undefined ? options.text : null; - - /** - * @private - * @type {number|undefined} - */ - this.zIndex_ = options.zIndex; - -}; - - -/** - * Clones the style. - * @return {ol.style.Style} The cloned style. - * @api - */ -ol.style.Style.prototype.clone = function() { - var geometry = this.getGeometry(); - if (geometry && geometry.clone) { - geometry = geometry.clone(); - } - return new ol.style.Style({ - geometry: geometry, - fill: this.getFill() ? this.getFill().clone() : undefined, - image: this.getImage() ? this.getImage().clone() : undefined, - stroke: this.getStroke() ? this.getStroke().clone() : undefined, - text: this.getText() ? this.getText().clone() : undefined, - zIndex: this.getZIndex() - }); -}; - - -/** - * Get the custom renderer function that was configured with - * {@link #setRenderer} or the `renderer` constructor option. - * @return {ol.StyleRenderFunction|null} Custom renderer function. - * @api - */ -ol.style.Style.prototype.getRenderer = function() { - return this.renderer_; -}; - - -/** - * Sets a custom renderer function for this style. When set, `fill`, `stroke` - * and `image` options of the style will be ignored. - * @param {ol.StyleRenderFunction|null} renderer Custom renderer function. - * @api - */ -ol.style.Style.prototype.setRenderer = function(renderer) { - this.renderer_ = renderer; -}; - - -/** - * Get the geometry to be rendered. - * @return {string|ol.geom.Geometry|ol.StyleGeometryFunction} - * Feature property or geometry or function that returns the geometry that will - * be rendered with this style. - * @api - */ -ol.style.Style.prototype.getGeometry = function() { - return this.geometry_; -}; - - -/** - * Get the function used to generate a geometry for rendering. - * @return {!ol.StyleGeometryFunction} Function that is called with a feature - * and returns the geometry to render instead of the feature's geometry. - * @api - */ -ol.style.Style.prototype.getGeometryFunction = function() { - return this.geometryFunction_; -}; - - -/** - * Get the fill style. - * @return {ol.style.Fill} Fill style. - * @api - */ -ol.style.Style.prototype.getFill = function() { - return this.fill_; -}; - - -/** - * Set the fill style. - * @param {ol.style.Fill} fill Fill style. - * @api - */ -ol.style.Style.prototype.setFill = function(fill) { - this.fill_ = fill; -}; - - -/** - * Get the image style. - * @return {ol.style.Image} Image style. - * @api - */ -ol.style.Style.prototype.getImage = function() { - return this.image_; -}; - - -/** - * Set the image style. - * @param {ol.style.Image} image Image style. - * @api - */ -ol.style.Style.prototype.setImage = function(image) { - this.image_ = image; -}; - - -/** - * Get the stroke style. - * @return {ol.style.Stroke} Stroke style. - * @api - */ -ol.style.Style.prototype.getStroke = function() { - return this.stroke_; -}; - - -/** - * Set the stroke style. - * @param {ol.style.Stroke} stroke Stroke style. - * @api - */ -ol.style.Style.prototype.setStroke = function(stroke) { - this.stroke_ = stroke; -}; - - -/** - * Get the text style. - * @return {ol.style.Text} Text style. - * @api - */ -ol.style.Style.prototype.getText = function() { - return this.text_; -}; - - -/** - * Set the text style. - * @param {ol.style.Text} text Text style. - * @api - */ -ol.style.Style.prototype.setText = function(text) { - this.text_ = text; -}; - - -/** - * Get the z-index for the style. - * @return {number|undefined} ZIndex. - * @api - */ -ol.style.Style.prototype.getZIndex = function() { - return this.zIndex_; -}; - - -/** - * Set a geometry that is rendered instead of the feature's geometry. - * - * @param {string|ol.geom.Geometry|ol.StyleGeometryFunction} geometry - * Feature property or geometry or function returning a geometry to render - * for this style. - * @api - */ -ol.style.Style.prototype.setGeometry = function(geometry) { - if (typeof geometry === 'function') { - this.geometryFunction_ = geometry; - } else if (typeof geometry === 'string') { - this.geometryFunction_ = function(feature) { - return /** @type {ol.geom.Geometry} */ (feature.get(geometry)); - }; - } else if (!geometry) { - this.geometryFunction_ = ol.style.Style.defaultGeometryFunction; - } else if (geometry !== undefined) { - this.geometryFunction_ = function() { - return /** @type {ol.geom.Geometry} */ (geometry); - }; - } - this.geometry_ = geometry; -}; - - -/** - * Set the z-index. - * - * @param {number|undefined} zIndex ZIndex. - * @api - */ -ol.style.Style.prototype.setZIndex = function(zIndex) { - this.zIndex_ = zIndex; -}; - - -/** - * Convert the provided object into a style function. Functions passed through - * unchanged. Arrays of ol.style.Style or single style objects wrapped in a - * new style function. - * @param {ol.StyleFunction|Array.<ol.style.Style>|ol.style.Style} obj - * A style function, a single style, or an array of styles. - * @return {ol.StyleFunction} A style function. - */ -ol.style.Style.createFunction = function(obj) { - var styleFunction; - - if (typeof obj === 'function') { - styleFunction = obj; - } else { - /** - * @type {Array.<ol.style.Style>} - */ - var styles; - if (Array.isArray(obj)) { - styles = obj; - } else { - ol.asserts.assert(obj instanceof ol.style.Style, - 41); // Expected an `ol.style.Style` or an array of `ol.style.Style` - styles = [obj]; - } - styleFunction = function() { - return styles; - }; - } - return styleFunction; -}; - - -/** - * @type {Array.<ol.style.Style>} - * @private - */ -ol.style.Style.default_ = null; - - -/** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @param {number} resolution Resolution. - * @return {Array.<ol.style.Style>} Style. - */ -ol.style.Style.defaultFunction = function(feature, resolution) { - // We don't use an immediately-invoked function - // and a closure so we don't get an error at script evaluation time in - // browsers that do not support Canvas. (ol.style.Circle does - // canvas.getContext('2d') at construction time, which will cause an.error - // in such browsers.) - if (!ol.style.Style.default_) { - var fill = new ol.style.Fill({ - color: 'rgba(255,255,255,0.4)' - }); - var stroke = new ol.style.Stroke({ - color: '#3399CC', - width: 1.25 - }); - ol.style.Style.default_ = [ - new ol.style.Style({ - image: new ol.style.Circle({ - fill: fill, - stroke: stroke, - radius: 5 - }), - fill: fill, - stroke: stroke - }) - ]; - } - return ol.style.Style.default_; -}; - - -/** - * Default styles for editing features. - * @return {Object.<ol.geom.GeometryType, Array.<ol.style.Style>>} Styles - */ -ol.style.Style.createDefaultEditing = function() { - /** @type {Object.<ol.geom.GeometryType, Array.<ol.style.Style>>} */ - var styles = {}; - var white = [255, 255, 255, 1]; - var blue = [0, 153, 255, 1]; - var width = 3; - styles[ol.geom.GeometryType.POLYGON] = [ - new ol.style.Style({ - fill: new ol.style.Fill({ - color: [255, 255, 255, 0.5] - }) - }) - ]; - styles[ol.geom.GeometryType.MULTI_POLYGON] = - styles[ol.geom.GeometryType.POLYGON]; - - styles[ol.geom.GeometryType.LINE_STRING] = [ - new ol.style.Style({ - stroke: new ol.style.Stroke({ - color: white, - width: width + 2 - }) - }), - new ol.style.Style({ - stroke: new ol.style.Stroke({ - color: blue, - width: width - }) - }) - ]; - styles[ol.geom.GeometryType.MULTI_LINE_STRING] = - styles[ol.geom.GeometryType.LINE_STRING]; - - styles[ol.geom.GeometryType.CIRCLE] = - styles[ol.geom.GeometryType.POLYGON].concat( - styles[ol.geom.GeometryType.LINE_STRING] - ); - - - styles[ol.geom.GeometryType.POINT] = [ - new ol.style.Style({ - image: new ol.style.Circle({ - radius: width * 2, - fill: new ol.style.Fill({ - color: blue - }), - stroke: new ol.style.Stroke({ - color: white, - width: width / 2 - }) - }), - zIndex: Infinity - }) - ]; - styles[ol.geom.GeometryType.MULTI_POINT] = - styles[ol.geom.GeometryType.POINT]; - - styles[ol.geom.GeometryType.GEOMETRY_COLLECTION] = - styles[ol.geom.GeometryType.POLYGON].concat( - styles[ol.geom.GeometryType.LINE_STRING], - styles[ol.geom.GeometryType.POINT] - ); - - return styles; -}; - - -/** - * Function that is called with a feature and returns its default geometry. - * @param {ol.Feature|ol.render.Feature} feature Feature to get the geometry - * for. - * @return {ol.geom.Geometry|ol.render.Feature|undefined} Geometry to render. - */ -ol.style.Style.defaultGeometryFunction = function(feature) { - return feature.getGeometry(); -}; - -goog.provide('ol.Feature'); - -goog.require('ol.asserts'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol'); -goog.require('ol.Object'); -goog.require('ol.geom.Geometry'); -goog.require('ol.style.Style'); - - -/** - * @classdesc - * A vector object for geographic features with a geometry and other - * attribute properties, similar to the features in vector file formats like - * GeoJSON. - * - * Features can be styled individually with `setStyle`; otherwise they use the - * style of their vector layer. - * - * Note that attribute properties are set as {@link ol.Object} properties on - * the feature object, so they are observable, and have get/set accessors. - * - * Typically, a feature has a single geometry property. You can set the - * geometry using the `setGeometry` method and get it with `getGeometry`. - * It is possible to store more than one geometry on a feature using attribute - * properties. By default, the geometry used for rendering is identified by - * the property name `geometry`. If you want to use another geometry property - * for rendering, use the `setGeometryName` method to change the attribute - * property associated with the geometry for the feature. For example: - * - * ```js - * var feature = new ol.Feature({ - * geometry: new ol.geom.Polygon(polyCoords), - * labelPoint: new ol.geom.Point(labelCoords), - * name: 'My Polygon' - * }); - * - * // get the polygon geometry - * var poly = feature.getGeometry(); - * - * // Render the feature as a point using the coordinates from labelPoint - * feature.setGeometryName('labelPoint'); - * - * // get the point geometry - * var point = feature.getGeometry(); - * ``` - * - * @constructor - * @extends {ol.Object} - * @param {ol.geom.Geometry|Object.<string, *>=} opt_geometryOrProperties - * You may pass a Geometry object directly, or an object literal - * containing properties. If you pass an object literal, you may - * include a Geometry associated with a `geometry` key. - * @api - */ -ol.Feature = function(opt_geometryOrProperties) { - - ol.Object.call(this); - - /** - * @private - * @type {number|string|undefined} - */ - this.id_ = undefined; - - /** - * @type {string} - * @private - */ - this.geometryName_ = 'geometry'; - - /** - * User provided style. - * @private - * @type {ol.style.Style|Array.<ol.style.Style>| - * ol.FeatureStyleFunction} - */ - this.style_ = null; - - /** - * @private - * @type {ol.FeatureStyleFunction|undefined} - */ - this.styleFunction_ = undefined; - - /** - * @private - * @type {?ol.EventsKey} - */ - this.geometryChangeKey_ = null; - - ol.events.listen( - this, ol.Object.getChangeEventType(this.geometryName_), - this.handleGeometryChanged_, this); - - if (opt_geometryOrProperties !== undefined) { - if (opt_geometryOrProperties instanceof ol.geom.Geometry || - !opt_geometryOrProperties) { - var geometry = opt_geometryOrProperties; - this.setGeometry(geometry); - } else { - /** @type {Object.<string, *>} */ - var properties = opt_geometryOrProperties; - this.setProperties(properties); - } - } -}; -ol.inherits(ol.Feature, ol.Object); - - -/** - * Clone this feature. If the original feature has a geometry it - * is also cloned. The feature id is not set in the clone. - * @return {ol.Feature} The clone. - * @api - */ -ol.Feature.prototype.clone = function() { - var clone = new ol.Feature(this.getProperties()); - clone.setGeometryName(this.getGeometryName()); - var geometry = this.getGeometry(); - if (geometry) { - clone.setGeometry(geometry.clone()); - } - var style = this.getStyle(); - if (style) { - clone.setStyle(style); - } - return clone; -}; - - -/** - * Get the feature's default geometry. A feature may have any number of named - * geometries. The "default" geometry (the one that is rendered by default) is - * set when calling {@link ol.Feature#setGeometry}. - * @return {ol.geom.Geometry|undefined} The default geometry for the feature. - * @api - * @observable - */ -ol.Feature.prototype.getGeometry = function() { - return /** @type {ol.geom.Geometry|undefined} */ ( - this.get(this.geometryName_)); -}; - - -/** - * Get the feature identifier. This is a stable identifier for the feature and - * is either set when reading data from a remote source or set explicitly by - * calling {@link ol.Feature#setId}. - * @return {number|string|undefined} Id. - * @api - */ -ol.Feature.prototype.getId = function() { - return this.id_; -}; - - -/** - * Get the name of the feature's default geometry. By default, the default - * geometry is named `geometry`. - * @return {string} Get the property name associated with the default geometry - * for this feature. - * @api - */ -ol.Feature.prototype.getGeometryName = function() { - return this.geometryName_; -}; - - -/** - * Get the feature's style. Will return what was provided to the - * {@link ol.Feature#setStyle} method. - * @return {ol.style.Style|Array.<ol.style.Style>| - * ol.FeatureStyleFunction|ol.StyleFunction} The feature style. - * @api - */ -ol.Feature.prototype.getStyle = function() { - return this.style_; -}; - - -/** - * Get the feature's style function. - * @return {ol.FeatureStyleFunction|undefined} Return a function - * representing the current style of this feature. - * @api - */ -ol.Feature.prototype.getStyleFunction = function() { - return this.styleFunction_; -}; - - -/** - * @private - */ -ol.Feature.prototype.handleGeometryChange_ = function() { - this.changed(); -}; - - -/** - * @private - */ -ol.Feature.prototype.handleGeometryChanged_ = function() { - if (this.geometryChangeKey_) { - ol.events.unlistenByKey(this.geometryChangeKey_); - this.geometryChangeKey_ = null; - } - var geometry = this.getGeometry(); - if (geometry) { - this.geometryChangeKey_ = ol.events.listen(geometry, - ol.events.EventType.CHANGE, this.handleGeometryChange_, this); - } - this.changed(); -}; - - -/** - * Set the default geometry for the feature. This will update the property - * with the name returned by {@link ol.Feature#getGeometryName}. - * @param {ol.geom.Geometry|undefined} geometry The new geometry. - * @api - * @observable - */ -ol.Feature.prototype.setGeometry = function(geometry) { - this.set(this.geometryName_, geometry); -}; - - -/** - * Set the style for the feature. This can be a single style object, an array - * of styles, or a function that takes a resolution and returns an array of - * styles. If it is `null` the feature has no style (a `null` style). - * @param {ol.style.Style|Array.<ol.style.Style>| - * ol.FeatureStyleFunction|ol.StyleFunction} style Style for this feature. - * @api - * @fires ol.events.Event#event:change - */ -ol.Feature.prototype.setStyle = function(style) { - this.style_ = style; - this.styleFunction_ = !style ? - undefined : ol.Feature.createStyleFunction(style); - this.changed(); -}; - - -/** - * Set the feature id. The feature id is considered stable and may be used when - * requesting features or comparing identifiers returned from a remote source. - * The feature id can be used with the {@link ol.source.Vector#getFeatureById} - * method. - * @param {number|string|undefined} id The feature id. - * @api - * @fires ol.events.Event#event:change - */ -ol.Feature.prototype.setId = function(id) { - this.id_ = id; - this.changed(); -}; - - -/** - * Set the property name to be used when getting the feature's default geometry. - * When calling {@link ol.Feature#getGeometry}, the value of the property with - * this name will be returned. - * @param {string} name The property name of the default geometry. - * @api - */ -ol.Feature.prototype.setGeometryName = function(name) { - ol.events.unlisten( - this, ol.Object.getChangeEventType(this.geometryName_), - this.handleGeometryChanged_, this); - this.geometryName_ = name; - ol.events.listen( - this, ol.Object.getChangeEventType(this.geometryName_), - this.handleGeometryChanged_, this); - this.handleGeometryChanged_(); -}; - - -/** - * Convert the provided object into a feature style function. Functions passed - * through unchanged. Arrays of ol.style.Style or single style objects wrapped - * in a new feature style function. - * @param {ol.FeatureStyleFunction|!Array.<ol.style.Style>|!ol.style.Style} obj - * A feature style function, a single style, or an array of styles. - * @return {ol.FeatureStyleFunction} A style function. - */ -ol.Feature.createStyleFunction = function(obj) { - var styleFunction; - - if (typeof obj === 'function') { - if (obj.length == 2) { - styleFunction = function(resolution) { - return /** @type {ol.StyleFunction} */ (obj)(this, resolution); - }; - } else { - styleFunction = obj; - } - } else { - /** - * @type {Array.<ol.style.Style>} - */ - var styles; - if (Array.isArray(obj)) { - styles = obj; - } else { - ol.asserts.assert(obj instanceof ol.style.Style, - 41); // Expected an `ol.style.Style` or an array of `ol.style.Style` - styles = [obj]; - } - styleFunction = function() { - return styles; - }; - } - return styleFunction; -}; - -goog.provide('ol.format.FormatType'); - - -/** - * @enum {string} - */ -ol.format.FormatType = { - ARRAY_BUFFER: 'arraybuffer', - JSON: 'json', - TEXT: 'text', - XML: 'xml' -}; - -goog.provide('ol.xml'); - -goog.require('ol.array'); - - -/** - * This document should be used when creating nodes for XML serializations. This - * document is also used by {@link ol.xml.createElementNS} and - * {@link ol.xml.setAttributeNS} - * @const - * @type {Document} - */ -ol.xml.DOCUMENT = document.implementation.createDocument('', '', null); - - -/** - * @param {string} namespaceURI Namespace URI. - * @param {string} qualifiedName Qualified name. - * @return {Node} Node. - */ -ol.xml.createElementNS = function(namespaceURI, qualifiedName) { - return ol.xml.DOCUMENT.createElementNS(namespaceURI, qualifiedName); -}; - - -/** - * Recursively grab all text content of child nodes into a single string. - * @param {Node} node Node. - * @param {boolean} normalizeWhitespace Normalize whitespace: remove all line - * breaks. - * @return {string} All text content. - * @api - */ -ol.xml.getAllTextContent = function(node, normalizeWhitespace) { - return ol.xml.getAllTextContent_(node, normalizeWhitespace, []).join(''); -}; - - -/** - * Recursively grab all text content of child nodes into a single string. - * @param {Node} node Node. - * @param {boolean} normalizeWhitespace Normalize whitespace: remove all line - * breaks. - * @param {Array.<string>} accumulator Accumulator. - * @private - * @return {Array.<string>} Accumulator. - */ -ol.xml.getAllTextContent_ = function(node, normalizeWhitespace, accumulator) { - if (node.nodeType == Node.CDATA_SECTION_NODE || - node.nodeType == Node.TEXT_NODE) { - if (normalizeWhitespace) { - accumulator.push(String(node.nodeValue).replace(/(\r\n|\r|\n)/g, '')); - } else { - accumulator.push(node.nodeValue); - } - } else { - var n; - for (n = node.firstChild; n; n = n.nextSibling) { - ol.xml.getAllTextContent_(n, normalizeWhitespace, accumulator); - } - } - return accumulator; -}; - - -/** - * @param {?} value Value. - * @return {boolean} Is document. - */ -ol.xml.isDocument = function(value) { - return value instanceof Document; -}; - - -/** - * @param {?} value Value. - * @return {boolean} Is node. - */ -ol.xml.isNode = function(value) { - return value instanceof Node; -}; - - -/** - * @param {Node} node Node. - * @param {?string} namespaceURI Namespace URI. - * @param {string} name Attribute name. - * @return {string} Value - */ -ol.xml.getAttributeNS = function(node, namespaceURI, name) { - return node.getAttributeNS(namespaceURI, name) || ''; -}; - - -/** - * @param {Node} node Node. - * @param {?string} namespaceURI Namespace URI. - * @param {string} name Attribute name. - * @param {string|number} value Value. - */ -ol.xml.setAttributeNS = function(node, namespaceURI, name, value) { - node.setAttributeNS(namespaceURI, name, value); -}; - - -/** - * Parse an XML string to an XML Document. - * @param {string} xml XML. - * @return {Document} Document. - * @api - */ -ol.xml.parse = function(xml) { - return new DOMParser().parseFromString(xml, 'application/xml'); -}; - - -/** - * Make an array extender function for extending the array at the top of the - * object stack. - * @param {function(this: T, Node, Array.<*>): (Array.<*>|undefined)} - * valueReader Value reader. - * @param {T=} opt_this The object to use as `this` in `valueReader`. - * @return {ol.XmlParser} Parser. - * @template T - */ -ol.xml.makeArrayExtender = function(valueReader, opt_this) { - return ( - /** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - */ - function(node, objectStack) { - var value = valueReader.call(opt_this, node, objectStack); - if (value !== undefined) { - var array = /** @type {Array.<*>} */ - (objectStack[objectStack.length - 1]); - ol.array.extend(array, value); - } - }); -}; - - -/** - * Make an array pusher function for pushing to the array at the top of the - * object stack. - * @param {function(this: T, Node, Array.<*>): *} valueReader Value reader. - * @param {T=} opt_this The object to use as `this` in `valueReader`. - * @return {ol.XmlParser} Parser. - * @template T - */ -ol.xml.makeArrayPusher = function(valueReader, opt_this) { - return ( - /** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - */ - function(node, objectStack) { - var value = valueReader.call(opt_this !== undefined ? opt_this : this, - node, objectStack); - if (value !== undefined) { - var array = objectStack[objectStack.length - 1]; - array.push(value); - } - }); -}; - - -/** - * Make an object stack replacer function for replacing the object at the - * top of the stack. - * @param {function(this: T, Node, Array.<*>): *} valueReader Value reader. - * @param {T=} opt_this The object to use as `this` in `valueReader`. - * @return {ol.XmlParser} Parser. - * @template T - */ -ol.xml.makeReplacer = function(valueReader, opt_this) { - return ( - /** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - */ - function(node, objectStack) { - var value = valueReader.call(opt_this !== undefined ? opt_this : this, - node, objectStack); - if (value !== undefined) { - objectStack[objectStack.length - 1] = value; - } - }); -}; - - -/** - * Make an object property pusher function for adding a property to the - * object at the top of the stack. - * @param {function(this: T, Node, Array.<*>): *} valueReader Value reader. - * @param {string=} opt_property Property. - * @param {T=} opt_this The object to use as `this` in `valueReader`. - * @return {ol.XmlParser} Parser. - * @template T - */ -ol.xml.makeObjectPropertyPusher = function(valueReader, opt_property, opt_this) { - return ( - /** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - */ - function(node, objectStack) { - var value = valueReader.call(opt_this !== undefined ? opt_this : this, - node, objectStack); - if (value !== undefined) { - var object = /** @type {Object} */ - (objectStack[objectStack.length - 1]); - var property = opt_property !== undefined ? - opt_property : node.localName; - var array; - if (property in object) { - array = object[property]; - } else { - array = object[property] = []; - } - array.push(value); - } - }); -}; - - -/** - * Make an object property setter function. - * @param {function(this: T, Node, Array.<*>): *} valueReader Value reader. - * @param {string=} opt_property Property. - * @param {T=} opt_this The object to use as `this` in `valueReader`. - * @return {ol.XmlParser} Parser. - * @template T - */ -ol.xml.makeObjectPropertySetter = function(valueReader, opt_property, opt_this) { - return ( - /** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - */ - function(node, objectStack) { - var value = valueReader.call(opt_this !== undefined ? opt_this : this, - node, objectStack); - if (value !== undefined) { - var object = /** @type {Object} */ - (objectStack[objectStack.length - 1]); - var property = opt_property !== undefined ? - opt_property : node.localName; - object[property] = value; - } - }); -}; - - -/** - * Create a serializer that appends nodes written by its `nodeWriter` to its - * designated parent. The parent is the `node` of the - * {@link ol.XmlNodeStackItem} at the top of the `objectStack`. - * @param {function(this: T, Node, V, Array.<*>)} - * nodeWriter Node writer. - * @param {T=} opt_this The object to use as `this` in `nodeWriter`. - * @return {ol.XmlSerializer} Serializer. - * @template T, V - */ -ol.xml.makeChildAppender = function(nodeWriter, opt_this) { - return function(node, value, objectStack) { - nodeWriter.call(opt_this !== undefined ? opt_this : this, - node, value, objectStack); - var parent = objectStack[objectStack.length - 1]; - var parentNode = parent.node; - parentNode.appendChild(node); - }; -}; - - -/** - * Create a serializer that calls the provided `nodeWriter` from - * {@link ol.xml.serialize}. This can be used by the parent writer to have the - * 'nodeWriter' called with an array of values when the `nodeWriter` was - * designed to serialize a single item. An example would be a LineString - * geometry writer, which could be reused for writing MultiLineString - * geometries. - * @param {function(this: T, Node, V, Array.<*>)} - * nodeWriter Node writer. - * @param {T=} opt_this The object to use as `this` in `nodeWriter`. - * @return {ol.XmlSerializer} Serializer. - * @template T, V - */ -ol.xml.makeArraySerializer = function(nodeWriter, opt_this) { - var serializersNS, nodeFactory; - return function(node, value, objectStack) { - if (serializersNS === undefined) { - serializersNS = {}; - var serializers = {}; - serializers[node.localName] = nodeWriter; - serializersNS[node.namespaceURI] = serializers; - nodeFactory = ol.xml.makeSimpleNodeFactory(node.localName); - } - ol.xml.serialize(serializersNS, nodeFactory, value, objectStack); - }; -}; - - -/** - * Create a node factory which can use the `opt_keys` passed to - * {@link ol.xml.serialize} or {@link ol.xml.pushSerializeAndPop} as node names, - * or a fixed node name. The namespace of the created nodes can either be fixed, - * or the parent namespace will be used. - * @param {string=} opt_nodeName Fixed node name which will be used for all - * created nodes. If not provided, the 3rd argument to the resulting node - * factory needs to be provided and will be the nodeName. - * @param {string=} opt_namespaceURI Fixed namespace URI which will be used for - * all created nodes. If not provided, the namespace of the parent node will - * be used. - * @return {function(*, Array.<*>, string=): (Node|undefined)} Node factory. - */ -ol.xml.makeSimpleNodeFactory = function(opt_nodeName, opt_namespaceURI) { - var fixedNodeName = opt_nodeName; - return ( - /** - * @param {*} value Value. - * @param {Array.<*>} objectStack Object stack. - * @param {string=} opt_nodeName Node name. - * @return {Node} Node. - */ - function(value, objectStack, opt_nodeName) { - var context = objectStack[objectStack.length - 1]; - var node = context.node; - var nodeName = fixedNodeName; - if (nodeName === undefined) { - nodeName = opt_nodeName; - } - var namespaceURI = opt_namespaceURI; - if (opt_namespaceURI === undefined) { - namespaceURI = node.namespaceURI; - } - return ol.xml.createElementNS(namespaceURI, /** @type {string} */ (nodeName)); - } - ); -}; - - -/** - * A node factory that creates a node using the parent's `namespaceURI` and the - * `nodeName` passed by {@link ol.xml.serialize} or - * {@link ol.xml.pushSerializeAndPop} to the node factory. - * @const - * @type {function(*, Array.<*>, string=): (Node|undefined)} - */ -ol.xml.OBJECT_PROPERTY_NODE_FACTORY = ol.xml.makeSimpleNodeFactory(); - - -/** - * Create an array of `values` to be used with {@link ol.xml.serialize} or - * {@link ol.xml.pushSerializeAndPop}, where `orderedKeys` has to be provided as - * `opt_key` argument. - * @param {Object.<string, V>} object Key-value pairs for the sequence. Keys can - * be a subset of the `orderedKeys`. - * @param {Array.<string>} orderedKeys Keys in the order of the sequence. - * @return {Array.<V>} Values in the order of the sequence. The resulting array - * has the same length as the `orderedKeys` array. Values that are not - * present in `object` will be `undefined` in the resulting array. - * @template V - */ -ol.xml.makeSequence = function(object, orderedKeys) { - var length = orderedKeys.length; - var sequence = new Array(length); - for (var i = 0; i < length; ++i) { - sequence[i] = object[orderedKeys[i]]; - } - return sequence; -}; - - -/** - * Create a namespaced structure, using the same values for each namespace. - * This can be used as a starting point for versioned parsers, when only a few - * values are version specific. - * @param {Array.<string>} namespaceURIs Namespace URIs. - * @param {T} structure Structure. - * @param {Object.<string, T>=} opt_structureNS Namespaced structure to add to. - * @return {Object.<string, T>} Namespaced structure. - * @template T - */ -ol.xml.makeStructureNS = function(namespaceURIs, structure, opt_structureNS) { - /** - * @type {Object.<string, *>} - */ - var structureNS = opt_structureNS !== undefined ? opt_structureNS : {}; - var i, ii; - for (i = 0, ii = namespaceURIs.length; i < ii; ++i) { - structureNS[namespaceURIs[i]] = structure; - } - return structureNS; -}; - - -/** - * Parse a node using the parsers and object stack. - * @param {Object.<string, Object.<string, ol.XmlParser>>} parsersNS - * Parsers by namespace. - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @param {*=} opt_this The object to use as `this`. - */ -ol.xml.parseNode = function(parsersNS, node, objectStack, opt_this) { - var n; - for (n = node.firstElementChild; n; n = n.nextElementSibling) { - var parsers = parsersNS[n.namespaceURI]; - if (parsers !== undefined) { - var parser = parsers[n.localName]; - if (parser !== undefined) { - parser.call(opt_this, n, objectStack); - } - } - } -}; - - -/** - * Push an object on top of the stack, parse and return the popped object. - * @param {T} object Object. - * @param {Object.<string, Object.<string, ol.XmlParser>>} parsersNS - * Parsers by namespace. - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @param {*=} opt_this The object to use as `this`. - * @return {T} Object. - * @template T - */ -ol.xml.pushParseAndPop = function( - object, parsersNS, node, objectStack, opt_this) { - objectStack.push(object); - ol.xml.parseNode(parsersNS, node, objectStack, opt_this); - return objectStack.pop(); -}; - - -/** - * Walk through an array of `values` and call a serializer for each value. - * @param {Object.<string, Object.<string, ol.XmlSerializer>>} serializersNS - * Namespaced serializers. - * @param {function(this: T, *, Array.<*>, (string|undefined)): (Node|undefined)} nodeFactory - * Node factory. The `nodeFactory` creates the node whose namespace and name - * will be used to choose a node writer from `serializersNS`. This - * separation allows us to decide what kind of node to create, depending on - * the value we want to serialize. An example for this would be different - * geometry writers based on the geometry type. - * @param {Array.<*>} values Values to serialize. An example would be an array - * of {@link ol.Feature} instances. - * @param {Array.<*>} objectStack Node stack. - * @param {Array.<string>=} opt_keys Keys of the `values`. Will be passed to the - * `nodeFactory`. This is used for serializing object literals where the - * node name relates to the property key. The array length of `opt_keys` has - * to match the length of `values`. For serializing a sequence, `opt_keys` - * determines the order of the sequence. - * @param {T=} opt_this The object to use as `this` for the node factory and - * serializers. - * @template T - */ -ol.xml.serialize = function( - serializersNS, nodeFactory, values, objectStack, opt_keys, opt_this) { - var length = (opt_keys !== undefined ? opt_keys : values).length; - var value, node; - for (var i = 0; i < length; ++i) { - value = values[i]; - if (value !== undefined) { - node = nodeFactory.call(opt_this, value, objectStack, - opt_keys !== undefined ? opt_keys[i] : undefined); - if (node !== undefined) { - serializersNS[node.namespaceURI][node.localName] - .call(opt_this, node, value, objectStack); - } - } - } -}; - - -/** - * @param {O} object Object. - * @param {Object.<string, Object.<string, ol.XmlSerializer>>} serializersNS - * Namespaced serializers. - * @param {function(this: T, *, Array.<*>, (string|undefined)): (Node|undefined)} nodeFactory - * Node factory. The `nodeFactory` creates the node whose namespace and name - * will be used to choose a node writer from `serializersNS`. This - * separation allows us to decide what kind of node to create, depending on - * the value we want to serialize. An example for this would be different - * geometry writers based on the geometry type. - * @param {Array.<*>} values Values to serialize. An example would be an array - * of {@link ol.Feature} instances. - * @param {Array.<*>} objectStack Node stack. - * @param {Array.<string>=} opt_keys Keys of the `values`. Will be passed to the - * `nodeFactory`. This is used for serializing object literals where the - * node name relates to the property key. The array length of `opt_keys` has - * to match the length of `values`. For serializing a sequence, `opt_keys` - * determines the order of the sequence. - * @param {T=} opt_this The object to use as `this` for the node factory and - * serializers. - * @return {O|undefined} Object. - * @template O, T - */ -ol.xml.pushSerializeAndPop = function(object, - serializersNS, nodeFactory, values, objectStack, opt_keys, opt_this) { - objectStack.push(object); - ol.xml.serialize( - serializersNS, nodeFactory, values, objectStack, opt_keys, opt_this); - return objectStack.pop(); -}; - -goog.provide('ol.featureloader'); - -goog.require('ol'); -goog.require('ol.format.FormatType'); -goog.require('ol.xml'); - - -/** - * @param {string|ol.FeatureUrlFunction} url Feature URL service. - * @param {ol.format.Feature} format Feature format. - * @param {function(this:ol.VectorTile, Array.<ol.Feature>, ol.proj.Projection, ol.Extent)|function(this:ol.source.Vector, Array.<ol.Feature>)} success - * Function called with the loaded features and optionally with the data - * projection. Called with the vector tile or source as `this`. - * @param {function(this:ol.VectorTile)|function(this:ol.source.Vector)} failure - * Function called when loading failed. Called with the vector tile or - * source as `this`. - * @return {ol.FeatureLoader} The feature loader. - */ -ol.featureloader.loadFeaturesXhr = function(url, format, success, failure) { - return ( - /** - * @param {ol.Extent} extent Extent. - * @param {number} resolution Resolution. - * @param {ol.proj.Projection} projection Projection. - * @this {ol.source.Vector|ol.VectorTile} - */ - function(extent, resolution, projection) { - var xhr = new XMLHttpRequest(); - xhr.open('GET', - typeof url === 'function' ? url(extent, resolution, projection) : url, - true); - if (format.getType() == ol.format.FormatType.ARRAY_BUFFER) { - xhr.responseType = 'arraybuffer'; - } - /** - * @param {Event} event Event. - * @private - */ - xhr.onload = function(event) { - // status will be 0 for file:// urls - if (!xhr.status || xhr.status >= 200 && xhr.status < 300) { - var type = format.getType(); - /** @type {Document|Node|Object|string|undefined} */ - var source; - if (type == ol.format.FormatType.JSON || - type == ol.format.FormatType.TEXT) { - source = xhr.responseText; - } else if (type == ol.format.FormatType.XML) { - source = xhr.responseXML; - if (!source) { - source = ol.xml.parse(xhr.responseText); - } - } else if (type == ol.format.FormatType.ARRAY_BUFFER) { - source = /** @type {ArrayBuffer} */ (xhr.response); - } - if (source) { - success.call(this, format.readFeatures(source, - {featureProjection: projection}), - format.readProjection(source), format.getLastExtent()); - } else { - failure.call(this); - } - } else { - failure.call(this); - } - }.bind(this); - /** - * @private - */ - xhr.onerror = function() { - failure.call(this); - }.bind(this); - xhr.send(); - }); -}; - - -/** - * Create an XHR feature loader for a `url` and `format`. The feature loader - * loads features (with XHR), parses the features, and adds them to the - * vector source. - * @param {string|ol.FeatureUrlFunction} url Feature URL service. - * @param {ol.format.Feature} format Feature format. - * @return {ol.FeatureLoader} The feature loader. - * @api - */ -ol.featureloader.xhr = function(url, format) { - return ol.featureloader.loadFeaturesXhr(url, format, - /** - * @param {Array.<ol.Feature>} features The loaded features. - * @param {ol.proj.Projection} dataProjection Data projection. - * @this {ol.source.Vector} - */ - function(features, dataProjection) { - this.addFeatures(features); - }, /* FIXME handle error */ ol.nullFunction); -}; - -goog.provide('ol.format.Feature'); - -goog.require('ol.geom.Geometry'); -goog.require('ol.obj'); -goog.require('ol.proj'); - - -/** - * @classdesc - * Abstract base class; normally only used for creating subclasses and not - * instantiated in apps. - * Base class for feature formats. - * {ol.format.Feature} subclasses provide the ability to decode and encode - * {@link ol.Feature} objects from a variety of commonly used geospatial - * file formats. See the documentation for each format for more details. - * - * @constructor - * @abstract - * @api - */ -ol.format.Feature = function() { - - /** - * @protected - * @type {ol.proj.Projection} - */ - this.defaultDataProjection = null; - - /** - * @protected - * @type {ol.proj.Projection} - */ - this.defaultFeatureProjection = null; - -}; - - -/** - * Adds the data projection to the read options. - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Options. - * @return {olx.format.ReadOptions|undefined} Options. - * @protected - */ -ol.format.Feature.prototype.getReadOptions = function(source, opt_options) { - var options; - if (opt_options) { - options = { - dataProjection: opt_options.dataProjection ? - opt_options.dataProjection : this.readProjection(source), - featureProjection: opt_options.featureProjection - }; - } - return this.adaptOptions(options); -}; - - -/** - * Sets the `defaultDataProjection` on the options, if no `dataProjection` - * is set. - * @param {olx.format.WriteOptions|olx.format.ReadOptions|undefined} options - * Options. - * @protected - * @return {olx.format.WriteOptions|olx.format.ReadOptions|undefined} - * Updated options. - */ -ol.format.Feature.prototype.adaptOptions = function(options) { - return ol.obj.assign({ - dataProjection: this.defaultDataProjection, - featureProjection: this.defaultFeatureProjection - }, options); -}; - - -/** - * Get the extent from the source of the last {@link readFeatures} call. - * @return {ol.Extent} Tile extent. - */ -ol.format.Feature.prototype.getLastExtent = function() { - return null; -}; - - -/** - * @abstract - * @return {ol.format.FormatType} Format. - */ -ol.format.Feature.prototype.getType = function() {}; - - -/** - * Read a single feature from a source. - * - * @abstract - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {ol.Feature} Feature. - */ -ol.format.Feature.prototype.readFeature = function(source, opt_options) {}; - - -/** - * Read all features from a source. - * - * @abstract - * @param {Document|Node|ArrayBuffer|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {Array.<ol.Feature>} Features. - */ -ol.format.Feature.prototype.readFeatures = function(source, opt_options) {}; - - -/** - * Read a single geometry from a source. - * - * @abstract - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {ol.geom.Geometry} Geometry. - */ -ol.format.Feature.prototype.readGeometry = function(source, opt_options) {}; - - -/** - * Read the projection from a source. - * - * @abstract - * @param {Document|Node|Object|string} source Source. - * @return {ol.proj.Projection} Projection. - */ -ol.format.Feature.prototype.readProjection = function(source) {}; - - -/** - * Encode a feature in this format. - * - * @abstract - * @param {ol.Feature} feature Feature. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {string} Result. - */ -ol.format.Feature.prototype.writeFeature = function(feature, opt_options) {}; - - -/** - * Encode an array of features in this format. - * - * @abstract - * @param {Array.<ol.Feature>} features Features. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {string} Result. - */ -ol.format.Feature.prototype.writeFeatures = function(features, opt_options) {}; - - -/** - * Write a single geometry in this format. - * - * @abstract - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {string} Result. - */ -ol.format.Feature.prototype.writeGeometry = function(geometry, opt_options) {}; - - -/** - * @param {ol.geom.Geometry|ol.Extent} geometry Geometry. - * @param {boolean} write Set to true for writing, false for reading. - * @param {(olx.format.WriteOptions|olx.format.ReadOptions)=} opt_options - * Options. - * @return {ol.geom.Geometry|ol.Extent} Transformed geometry. - * @protected - */ -ol.format.Feature.transformWithOptions = function( - geometry, write, opt_options) { - var featureProjection = opt_options ? - ol.proj.get(opt_options.featureProjection) : null; - var dataProjection = opt_options ? - ol.proj.get(opt_options.dataProjection) : null; - /** - * @type {ol.geom.Geometry|ol.Extent} - */ - var transformed; - if (featureProjection && dataProjection && - !ol.proj.equivalent(featureProjection, dataProjection)) { - if (geometry instanceof ol.geom.Geometry) { - transformed = (write ? geometry.clone() : geometry).transform( - write ? featureProjection : dataProjection, - write ? dataProjection : featureProjection); - } else { - // FIXME this is necessary because ol.format.GML treats extents - // as geometries - transformed = ol.proj.transformExtent( - geometry, - dataProjection, - featureProjection); - } - } else { - transformed = geometry; - } - if (write && opt_options && opt_options.decimals !== undefined) { - var power = Math.pow(10, opt_options.decimals); - // if decimals option on write, round each coordinate appropriately - /** - * @param {Array.<number>} coordinates Coordinates. - * @return {Array.<number>} Transformed coordinates. - */ - var transform = function(coordinates) { - for (var i = 0, ii = coordinates.length; i < ii; ++i) { - coordinates[i] = Math.round(coordinates[i] * power) / power; - } - return coordinates; - }; - if (transformed === geometry) { - transformed = transformed.clone(); - } - transformed.applyTransform(transform); - } - return transformed; -}; - -goog.provide('ol.format.JSONFeature'); - -goog.require('ol'); -goog.require('ol.format.Feature'); -goog.require('ol.format.FormatType'); - - -/** - * @classdesc - * Abstract base class; normally only used for creating subclasses and not - * instantiated in apps. - * Base class for JSON feature formats. - * - * @constructor - * @abstract - * @extends {ol.format.Feature} - */ -ol.format.JSONFeature = function() { - ol.format.Feature.call(this); -}; -ol.inherits(ol.format.JSONFeature, ol.format.Feature); - - -/** - * @param {Document|Node|Object|string} source Source. - * @private - * @return {Object} Object. - */ -ol.format.JSONFeature.prototype.getObject_ = function(source) { - if (typeof source === 'string') { - var object = JSON.parse(source); - return object ? /** @type {Object} */ (object) : null; - } else if (source !== null) { - return source; - } else { - return null; - } -}; - - -/** - * @inheritDoc - */ -ol.format.JSONFeature.prototype.getType = function() { - return ol.format.FormatType.JSON; -}; - - -/** - * @inheritDoc - */ -ol.format.JSONFeature.prototype.readFeature = function(source, opt_options) { - return this.readFeatureFromObject( - this.getObject_(source), this.getReadOptions(source, opt_options)); -}; - - -/** - * @inheritDoc - */ -ol.format.JSONFeature.prototype.readFeatures = function(source, opt_options) { - return this.readFeaturesFromObject( - this.getObject_(source), this.getReadOptions(source, opt_options)); -}; - - -/** - * @abstract - * @param {Object} object Object. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @protected - * @return {ol.Feature} Feature. - */ -ol.format.JSONFeature.prototype.readFeatureFromObject = function(object, opt_options) {}; - - -/** - * @abstract - * @param {Object} object Object. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @protected - * @return {Array.<ol.Feature>} Features. - */ -ol.format.JSONFeature.prototype.readFeaturesFromObject = function(object, opt_options) {}; - - -/** - * @inheritDoc - */ -ol.format.JSONFeature.prototype.readGeometry = function(source, opt_options) { - return this.readGeometryFromObject( - this.getObject_(source), this.getReadOptions(source, opt_options)); -}; - - -/** - * @abstract - * @param {Object} object Object. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @protected - * @return {ol.geom.Geometry} Geometry. - */ -ol.format.JSONFeature.prototype.readGeometryFromObject = function(object, opt_options) {}; - - -/** - * @inheritDoc - */ -ol.format.JSONFeature.prototype.readProjection = function(source) { - return this.readProjectionFromObject(this.getObject_(source)); -}; - - -/** - * @abstract - * @param {Object} object Object. - * @protected - * @return {ol.proj.Projection} Projection. - */ -ol.format.JSONFeature.prototype.readProjectionFromObject = function(object) {}; - - -/** - * @inheritDoc - */ -ol.format.JSONFeature.prototype.writeFeature = function(feature, opt_options) { - return JSON.stringify(this.writeFeatureObject(feature, opt_options)); -}; - - -/** - * @abstract - * @param {ol.Feature} feature Feature. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {Object} Object. - */ -ol.format.JSONFeature.prototype.writeFeatureObject = function(feature, opt_options) {}; - - -/** - * @inheritDoc - */ -ol.format.JSONFeature.prototype.writeFeatures = function(features, opt_options) { - return JSON.stringify(this.writeFeaturesObject(features, opt_options)); -}; - - -/** - * @abstract - * @param {Array.<ol.Feature>} features Features. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {Object} Object. - */ -ol.format.JSONFeature.prototype.writeFeaturesObject = function(features, opt_options) {}; - - -/** - * @inheritDoc - */ -ol.format.JSONFeature.prototype.writeGeometry = function(geometry, opt_options) { - return JSON.stringify(this.writeGeometryObject(geometry, opt_options)); -}; - - -/** - * @abstract - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {Object} Object. - */ -ol.format.JSONFeature.prototype.writeGeometryObject = function(geometry, opt_options) {}; - -goog.provide('ol.geom.flat.interpolate'); - -goog.require('ol.array'); -goog.require('ol.math'); - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {number} fraction Fraction. - * @param {Array.<number>=} opt_dest Destination. - * @return {Array.<number>} Destination. - */ -ol.geom.flat.interpolate.lineString = function(flatCoordinates, offset, end, stride, fraction, opt_dest) { - var pointX = NaN; - var pointY = NaN; - var n = (end - offset) / stride; - if (n === 1) { - pointX = flatCoordinates[offset]; - pointY = flatCoordinates[offset + 1]; - } else if (n == 2) { - pointX = (1 - fraction) * flatCoordinates[offset] + - fraction * flatCoordinates[offset + stride]; - pointY = (1 - fraction) * flatCoordinates[offset + 1] + - fraction * flatCoordinates[offset + stride + 1]; - } else if (n !== 0) { - var x1 = flatCoordinates[offset]; - var y1 = flatCoordinates[offset + 1]; - var length = 0; - var cumulativeLengths = [0]; - var i; - for (i = offset + stride; i < end; i += stride) { - var x2 = flatCoordinates[i]; - var y2 = flatCoordinates[i + 1]; - length += Math.sqrt((x2 - x1) * (x2 - x1) + (y2 - y1) * (y2 - y1)); - cumulativeLengths.push(length); - x1 = x2; - y1 = y2; - } - var target = fraction * length; - var index = ol.array.binarySearch(cumulativeLengths, target); - if (index < 0) { - var t = (target - cumulativeLengths[-index - 2]) / - (cumulativeLengths[-index - 1] - cumulativeLengths[-index - 2]); - var o = offset + (-index - 2) * stride; - pointX = ol.math.lerp( - flatCoordinates[o], flatCoordinates[o + stride], t); - pointY = ol.math.lerp( - flatCoordinates[o + 1], flatCoordinates[o + stride + 1], t); - } else { - pointX = flatCoordinates[offset + index * stride]; - pointY = flatCoordinates[offset + index * stride + 1]; - } - } - if (opt_dest) { - opt_dest[0] = pointX; - opt_dest[1] = pointY; - return opt_dest; - } else { - return [pointX, pointY]; - } -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {number} m M. - * @param {boolean} extrapolate Extrapolate. - * @return {ol.Coordinate} Coordinate. - */ -ol.geom.flat.interpolate.lineStringCoordinateAtM = function(flatCoordinates, offset, end, stride, m, extrapolate) { - if (end == offset) { - return null; - } - var coordinate; - if (m < flatCoordinates[offset + stride - 1]) { - if (extrapolate) { - coordinate = flatCoordinates.slice(offset, offset + stride); - coordinate[stride - 1] = m; - return coordinate; - } else { - return null; - } - } else if (flatCoordinates[end - 1] < m) { - if (extrapolate) { - coordinate = flatCoordinates.slice(end - stride, end); - coordinate[stride - 1] = m; - return coordinate; - } else { - return null; - } - } - // FIXME use O(1) search - if (m == flatCoordinates[offset + stride - 1]) { - return flatCoordinates.slice(offset, offset + stride); - } - var lo = offset / stride; - var hi = end / stride; - while (lo < hi) { - var mid = (lo + hi) >> 1; - if (m < flatCoordinates[(mid + 1) * stride - 1]) { - hi = mid; - } else { - lo = mid + 1; - } - } - var m0 = flatCoordinates[lo * stride - 1]; - if (m == m0) { - return flatCoordinates.slice((lo - 1) * stride, (lo - 1) * stride + stride); - } - var m1 = flatCoordinates[(lo + 1) * stride - 1]; - var t = (m - m0) / (m1 - m0); - coordinate = []; - var i; - for (i = 0; i < stride - 1; ++i) { - coordinate.push(ol.math.lerp(flatCoordinates[(lo - 1) * stride + i], - flatCoordinates[lo * stride + i], t)); - } - coordinate.push(m); - return coordinate; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<number>} ends Ends. - * @param {number} stride Stride. - * @param {number} m M. - * @param {boolean} extrapolate Extrapolate. - * @param {boolean} interpolate Interpolate. - * @return {ol.Coordinate} Coordinate. - */ -ol.geom.flat.interpolate.lineStringsCoordinateAtM = function( - flatCoordinates, offset, ends, stride, m, extrapolate, interpolate) { - if (interpolate) { - return ol.geom.flat.interpolate.lineStringCoordinateAtM( - flatCoordinates, offset, ends[ends.length - 1], stride, m, extrapolate); - } - var coordinate; - if (m < flatCoordinates[stride - 1]) { - if (extrapolate) { - coordinate = flatCoordinates.slice(0, stride); - coordinate[stride - 1] = m; - return coordinate; - } else { - return null; - } - } - if (flatCoordinates[flatCoordinates.length - 1] < m) { - if (extrapolate) { - coordinate = flatCoordinates.slice(flatCoordinates.length - stride); - coordinate[stride - 1] = m; - return coordinate; - } else { - return null; - } - } - var i, ii; - for (i = 0, ii = ends.length; i < ii; ++i) { - var end = ends[i]; - if (offset == end) { - continue; - } - if (m < flatCoordinates[offset + stride - 1]) { - return null; - } else if (m <= flatCoordinates[end - 1]) { - return ol.geom.flat.interpolate.lineStringCoordinateAtM( - flatCoordinates, offset, end, stride, m, false); - } - offset = end; - } - return null; -}; - -goog.provide('ol.geom.LineString'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.extent'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.SimpleGeometry'); -goog.require('ol.geom.flat.closest'); -goog.require('ol.geom.flat.deflate'); -goog.require('ol.geom.flat.inflate'); -goog.require('ol.geom.flat.interpolate'); -goog.require('ol.geom.flat.intersectsextent'); -goog.require('ol.geom.flat.length'); -goog.require('ol.geom.flat.segments'); -goog.require('ol.geom.flat.simplify'); - - -/** - * @classdesc - * Linestring geometry. - * - * @constructor - * @extends {ol.geom.SimpleGeometry} - * @param {Array.<ol.Coordinate>} coordinates Coordinates. - * @param {ol.geom.GeometryLayout=} opt_layout Layout. - * @api - */ -ol.geom.LineString = function(coordinates, opt_layout) { - - ol.geom.SimpleGeometry.call(this); - - /** - * @private - * @type {ol.Coordinate} - */ - this.flatMidpoint_ = null; - - /** - * @private - * @type {number} - */ - this.flatMidpointRevision_ = -1; - - /** - * @private - * @type {number} - */ - this.maxDelta_ = -1; - - /** - * @private - * @type {number} - */ - this.maxDeltaRevision_ = -1; - - this.setCoordinates(coordinates, opt_layout); - -}; -ol.inherits(ol.geom.LineString, ol.geom.SimpleGeometry); - - -/** - * Append the passed coordinate to the coordinates of the linestring. - * @param {ol.Coordinate} coordinate Coordinate. - * @api - */ -ol.geom.LineString.prototype.appendCoordinate = function(coordinate) { - if (!this.flatCoordinates) { - this.flatCoordinates = coordinate.slice(); - } else { - ol.array.extend(this.flatCoordinates, coordinate); - } - this.changed(); -}; - - -/** - * Make a complete copy of the geometry. - * @return {!ol.geom.LineString} Clone. - * @override - * @api - */ -ol.geom.LineString.prototype.clone = function() { - var lineString = new ol.geom.LineString(null); - lineString.setFlatCoordinates(this.layout, this.flatCoordinates.slice()); - return lineString; -}; - - -/** - * @inheritDoc - */ -ol.geom.LineString.prototype.closestPointXY = function(x, y, closestPoint, minSquaredDistance) { - if (minSquaredDistance < - ol.extent.closestSquaredDistanceXY(this.getExtent(), x, y)) { - return minSquaredDistance; - } - if (this.maxDeltaRevision_ != this.getRevision()) { - this.maxDelta_ = Math.sqrt(ol.geom.flat.closest.getMaxSquaredDelta( - this.flatCoordinates, 0, this.flatCoordinates.length, this.stride, 0)); - this.maxDeltaRevision_ = this.getRevision(); - } - return ol.geom.flat.closest.getClosestPoint( - this.flatCoordinates, 0, this.flatCoordinates.length, this.stride, - this.maxDelta_, false, x, y, closestPoint, minSquaredDistance); -}; - - -/** - * Iterate over each segment, calling the provided callback. - * If the callback returns a truthy value the function returns that - * value immediately. Otherwise the function returns `false`. - * - * @param {function(this: S, ol.Coordinate, ol.Coordinate): T} callback Function - * called for each segment. - * @param {S=} opt_this The object to be used as the value of 'this' - * within callback. - * @return {T|boolean} Value. - * @template T,S - * @api - */ -ol.geom.LineString.prototype.forEachSegment = function(callback, opt_this) { - return ol.geom.flat.segments.forEach(this.flatCoordinates, 0, - this.flatCoordinates.length, this.stride, callback, opt_this); -}; - - -/** - * Returns the coordinate at `m` using linear interpolation, or `null` if no - * such coordinate exists. - * - * `opt_extrapolate` controls extrapolation beyond the range of Ms in the - * MultiLineString. If `opt_extrapolate` is `true` then Ms less than the first - * M will return the first coordinate and Ms greater than the last M will - * return the last coordinate. - * - * @param {number} m M. - * @param {boolean=} opt_extrapolate Extrapolate. Default is `false`. - * @return {ol.Coordinate} Coordinate. - * @api - */ -ol.geom.LineString.prototype.getCoordinateAtM = function(m, opt_extrapolate) { - if (this.layout != ol.geom.GeometryLayout.XYM && - this.layout != ol.geom.GeometryLayout.XYZM) { - return null; - } - var extrapolate = opt_extrapolate !== undefined ? opt_extrapolate : false; - return ol.geom.flat.interpolate.lineStringCoordinateAtM(this.flatCoordinates, 0, - this.flatCoordinates.length, this.stride, m, extrapolate); -}; - - -/** - * Return the coordinates of the linestring. - * @return {Array.<ol.Coordinate>} Coordinates. - * @override - * @api - */ -ol.geom.LineString.prototype.getCoordinates = function() { - return ol.geom.flat.inflate.coordinates( - this.flatCoordinates, 0, this.flatCoordinates.length, this.stride); -}; - - -/** - * Return the coordinate at the provided fraction along the linestring. - * The `fraction` is a number between 0 and 1, where 0 is the start of the - * linestring and 1 is the end. - * @param {number} fraction Fraction. - * @param {ol.Coordinate=} opt_dest Optional coordinate whose values will - * be modified. If not provided, a new coordinate will be returned. - * @return {ol.Coordinate} Coordinate of the interpolated point. - * @api - */ -ol.geom.LineString.prototype.getCoordinateAt = function(fraction, opt_dest) { - return ol.geom.flat.interpolate.lineString( - this.flatCoordinates, 0, this.flatCoordinates.length, this.stride, - fraction, opt_dest); -}; - - -/** - * Return the length of the linestring on projected plane. - * @return {number} Length (on projected plane). - * @api - */ -ol.geom.LineString.prototype.getLength = function() { - return ol.geom.flat.length.lineString( - this.flatCoordinates, 0, this.flatCoordinates.length, this.stride); -}; - - -/** - * @return {Array.<number>} Flat midpoint. - */ -ol.geom.LineString.prototype.getFlatMidpoint = function() { - if (this.flatMidpointRevision_ != this.getRevision()) { - this.flatMidpoint_ = this.getCoordinateAt(0.5, this.flatMidpoint_); - this.flatMidpointRevision_ = this.getRevision(); - } - return this.flatMidpoint_; -}; - - -/** - * @inheritDoc - */ -ol.geom.LineString.prototype.getSimplifiedGeometryInternal = function(squaredTolerance) { - var simplifiedFlatCoordinates = []; - simplifiedFlatCoordinates.length = ol.geom.flat.simplify.douglasPeucker( - this.flatCoordinates, 0, this.flatCoordinates.length, this.stride, - squaredTolerance, simplifiedFlatCoordinates, 0); - var simplifiedLineString = new ol.geom.LineString(null); - simplifiedLineString.setFlatCoordinates( - ol.geom.GeometryLayout.XY, simplifiedFlatCoordinates); - return simplifiedLineString; -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.LineString.prototype.getType = function() { - return ol.geom.GeometryType.LINE_STRING; -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.LineString.prototype.intersectsExtent = function(extent) { - return ol.geom.flat.intersectsextent.lineString( - this.flatCoordinates, 0, this.flatCoordinates.length, this.stride, - extent); -}; - - -/** - * Set the coordinates of the linestring. - * @param {Array.<ol.Coordinate>} coordinates Coordinates. - * @param {ol.geom.GeometryLayout=} opt_layout Layout. - * @override - * @api - */ -ol.geom.LineString.prototype.setCoordinates = function(coordinates, opt_layout) { - if (!coordinates) { - this.setFlatCoordinates(ol.geom.GeometryLayout.XY, null); - } else { - this.setLayout(opt_layout, coordinates, 1); - if (!this.flatCoordinates) { - this.flatCoordinates = []; - } - this.flatCoordinates.length = ol.geom.flat.deflate.coordinates( - this.flatCoordinates, 0, coordinates, this.stride); - this.changed(); - } -}; - - -/** - * @param {ol.geom.GeometryLayout} layout Layout. - * @param {Array.<number>} flatCoordinates Flat coordinates. - */ -ol.geom.LineString.prototype.setFlatCoordinates = function(layout, flatCoordinates) { - this.setFlatCoordinatesInternal(layout, flatCoordinates); - this.changed(); -}; - -goog.provide('ol.geom.MultiLineString'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.extent'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.LineString'); -goog.require('ol.geom.SimpleGeometry'); -goog.require('ol.geom.flat.closest'); -goog.require('ol.geom.flat.deflate'); -goog.require('ol.geom.flat.inflate'); -goog.require('ol.geom.flat.interpolate'); -goog.require('ol.geom.flat.intersectsextent'); -goog.require('ol.geom.flat.simplify'); - - -/** - * @classdesc - * Multi-linestring geometry. - * - * @constructor - * @extends {ol.geom.SimpleGeometry} - * @param {Array.<Array.<ol.Coordinate>>} coordinates Coordinates. - * @param {ol.geom.GeometryLayout=} opt_layout Layout. - * @api - */ -ol.geom.MultiLineString = function(coordinates, opt_layout) { - - ol.geom.SimpleGeometry.call(this); - - /** - * @type {Array.<number>} - * @private - */ - this.ends_ = []; - - /** - * @private - * @type {number} - */ - this.maxDelta_ = -1; - - /** - * @private - * @type {number} - */ - this.maxDeltaRevision_ = -1; - - this.setCoordinates(coordinates, opt_layout); - -}; -ol.inherits(ol.geom.MultiLineString, ol.geom.SimpleGeometry); - - -/** - * Append the passed linestring to the multilinestring. - * @param {ol.geom.LineString} lineString LineString. - * @api - */ -ol.geom.MultiLineString.prototype.appendLineString = function(lineString) { - if (!this.flatCoordinates) { - this.flatCoordinates = lineString.getFlatCoordinates().slice(); - } else { - ol.array.extend( - this.flatCoordinates, lineString.getFlatCoordinates().slice()); - } - this.ends_.push(this.flatCoordinates.length); - this.changed(); -}; - - -/** - * Make a complete copy of the geometry. - * @return {!ol.geom.MultiLineString} Clone. - * @override - * @api - */ -ol.geom.MultiLineString.prototype.clone = function() { - var multiLineString = new ol.geom.MultiLineString(null); - multiLineString.setFlatCoordinates( - this.layout, this.flatCoordinates.slice(), this.ends_.slice()); - return multiLineString; -}; - - -/** - * @inheritDoc - */ -ol.geom.MultiLineString.prototype.closestPointXY = function(x, y, closestPoint, minSquaredDistance) { - if (minSquaredDistance < - ol.extent.closestSquaredDistanceXY(this.getExtent(), x, y)) { - return minSquaredDistance; - } - if (this.maxDeltaRevision_ != this.getRevision()) { - this.maxDelta_ = Math.sqrt(ol.geom.flat.closest.getsMaxSquaredDelta( - this.flatCoordinates, 0, this.ends_, this.stride, 0)); - this.maxDeltaRevision_ = this.getRevision(); - } - return ol.geom.flat.closest.getsClosestPoint( - this.flatCoordinates, 0, this.ends_, this.stride, - this.maxDelta_, false, x, y, closestPoint, minSquaredDistance); -}; - - -/** - * Returns the coordinate at `m` using linear interpolation, or `null` if no - * such coordinate exists. - * - * `opt_extrapolate` controls extrapolation beyond the range of Ms in the - * MultiLineString. If `opt_extrapolate` is `true` then Ms less than the first - * M will return the first coordinate and Ms greater than the last M will - * return the last coordinate. - * - * `opt_interpolate` controls interpolation between consecutive LineStrings - * within the MultiLineString. If `opt_interpolate` is `true` the coordinates - * will be linearly interpolated between the last coordinate of one LineString - * and the first coordinate of the next LineString. If `opt_interpolate` is - * `false` then the function will return `null` for Ms falling between - * LineStrings. - * - * @param {number} m M. - * @param {boolean=} opt_extrapolate Extrapolate. Default is `false`. - * @param {boolean=} opt_interpolate Interpolate. Default is `false`. - * @return {ol.Coordinate} Coordinate. - * @api - */ -ol.geom.MultiLineString.prototype.getCoordinateAtM = function(m, opt_extrapolate, opt_interpolate) { - if ((this.layout != ol.geom.GeometryLayout.XYM && - this.layout != ol.geom.GeometryLayout.XYZM) || - this.flatCoordinates.length === 0) { - return null; - } - var extrapolate = opt_extrapolate !== undefined ? opt_extrapolate : false; - var interpolate = opt_interpolate !== undefined ? opt_interpolate : false; - return ol.geom.flat.interpolate.lineStringsCoordinateAtM(this.flatCoordinates, 0, - this.ends_, this.stride, m, extrapolate, interpolate); -}; - - -/** - * Return the coordinates of the multilinestring. - * @return {Array.<Array.<ol.Coordinate>>} Coordinates. - * @override - * @api - */ -ol.geom.MultiLineString.prototype.getCoordinates = function() { - return ol.geom.flat.inflate.coordinatess( - this.flatCoordinates, 0, this.ends_, this.stride); -}; - - -/** - * @return {Array.<number>} Ends. - */ -ol.geom.MultiLineString.prototype.getEnds = function() { - return this.ends_; -}; - - -/** - * Return the linestring at the specified index. - * @param {number} index Index. - * @return {ol.geom.LineString} LineString. - * @api - */ -ol.geom.MultiLineString.prototype.getLineString = function(index) { - if (index < 0 || this.ends_.length <= index) { - return null; - } - var lineString = new ol.geom.LineString(null); - lineString.setFlatCoordinates(this.layout, this.flatCoordinates.slice( - index === 0 ? 0 : this.ends_[index - 1], this.ends_[index])); - return lineString; -}; - - -/** - * Return the linestrings of this multilinestring. - * @return {Array.<ol.geom.LineString>} LineStrings. - * @api - */ -ol.geom.MultiLineString.prototype.getLineStrings = function() { - var flatCoordinates = this.flatCoordinates; - var ends = this.ends_; - var layout = this.layout; - /** @type {Array.<ol.geom.LineString>} */ - var lineStrings = []; - var offset = 0; - var i, ii; - for (i = 0, ii = ends.length; i < ii; ++i) { - var end = ends[i]; - var lineString = new ol.geom.LineString(null); - lineString.setFlatCoordinates(layout, flatCoordinates.slice(offset, end)); - lineStrings.push(lineString); - offset = end; - } - return lineStrings; -}; - - -/** - * @return {Array.<number>} Flat midpoints. - */ -ol.geom.MultiLineString.prototype.getFlatMidpoints = function() { - var midpoints = []; - var flatCoordinates = this.flatCoordinates; - var offset = 0; - var ends = this.ends_; - var stride = this.stride; - var i, ii; - for (i = 0, ii = ends.length; i < ii; ++i) { - var end = ends[i]; - var midpoint = ol.geom.flat.interpolate.lineString( - flatCoordinates, offset, end, stride, 0.5); - ol.array.extend(midpoints, midpoint); - offset = end; - } - return midpoints; -}; - - -/** - * @inheritDoc - */ -ol.geom.MultiLineString.prototype.getSimplifiedGeometryInternal = function(squaredTolerance) { - var simplifiedFlatCoordinates = []; - var simplifiedEnds = []; - simplifiedFlatCoordinates.length = ol.geom.flat.simplify.douglasPeuckers( - this.flatCoordinates, 0, this.ends_, this.stride, squaredTolerance, - simplifiedFlatCoordinates, 0, simplifiedEnds); - var simplifiedMultiLineString = new ol.geom.MultiLineString(null); - simplifiedMultiLineString.setFlatCoordinates( - ol.geom.GeometryLayout.XY, simplifiedFlatCoordinates, simplifiedEnds); - return simplifiedMultiLineString; -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.MultiLineString.prototype.getType = function() { - return ol.geom.GeometryType.MULTI_LINE_STRING; -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.MultiLineString.prototype.intersectsExtent = function(extent) { - return ol.geom.flat.intersectsextent.lineStrings( - this.flatCoordinates, 0, this.ends_, this.stride, extent); -}; - - -/** - * Set the coordinates of the multilinestring. - * @param {Array.<Array.<ol.Coordinate>>} coordinates Coordinates. - * @param {ol.geom.GeometryLayout=} opt_layout Layout. - * @override - * @api - */ -ol.geom.MultiLineString.prototype.setCoordinates = function(coordinates, opt_layout) { - if (!coordinates) { - this.setFlatCoordinates(ol.geom.GeometryLayout.XY, null, this.ends_); - } else { - this.setLayout(opt_layout, coordinates, 2); - if (!this.flatCoordinates) { - this.flatCoordinates = []; - } - var ends = ol.geom.flat.deflate.coordinatess( - this.flatCoordinates, 0, coordinates, this.stride, this.ends_); - this.flatCoordinates.length = ends.length === 0 ? 0 : ends[ends.length - 1]; - this.changed(); - } -}; - - -/** - * @param {ol.geom.GeometryLayout} layout Layout. - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {Array.<number>} ends Ends. - */ -ol.geom.MultiLineString.prototype.setFlatCoordinates = function(layout, flatCoordinates, ends) { - this.setFlatCoordinatesInternal(layout, flatCoordinates); - this.ends_ = ends; - this.changed(); -}; - - -/** - * @param {Array.<ol.geom.LineString>} lineStrings LineStrings. - */ -ol.geom.MultiLineString.prototype.setLineStrings = function(lineStrings) { - var layout = this.getLayout(); - var flatCoordinates = []; - var ends = []; - var i, ii; - for (i = 0, ii = lineStrings.length; i < ii; ++i) { - var lineString = lineStrings[i]; - if (i === 0) { - layout = lineString.getLayout(); - } - ol.array.extend(flatCoordinates, lineString.getFlatCoordinates()); - ends.push(flatCoordinates.length); - } - this.setFlatCoordinates(layout, flatCoordinates, ends); -}; - -goog.provide('ol.geom.MultiPoint'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.extent'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.Point'); -goog.require('ol.geom.SimpleGeometry'); -goog.require('ol.geom.flat.deflate'); -goog.require('ol.geom.flat.inflate'); -goog.require('ol.math'); - - -/** - * @classdesc - * Multi-point geometry. - * - * @constructor - * @extends {ol.geom.SimpleGeometry} - * @param {Array.<ol.Coordinate>} coordinates Coordinates. - * @param {ol.geom.GeometryLayout=} opt_layout Layout. - * @api - */ -ol.geom.MultiPoint = function(coordinates, opt_layout) { - ol.geom.SimpleGeometry.call(this); - this.setCoordinates(coordinates, opt_layout); -}; -ol.inherits(ol.geom.MultiPoint, ol.geom.SimpleGeometry); - - -/** - * Append the passed point to this multipoint. - * @param {ol.geom.Point} point Point. - * @api - */ -ol.geom.MultiPoint.prototype.appendPoint = function(point) { - if (!this.flatCoordinates) { - this.flatCoordinates = point.getFlatCoordinates().slice(); - } else { - ol.array.extend(this.flatCoordinates, point.getFlatCoordinates()); - } - this.changed(); -}; - - -/** - * Make a complete copy of the geometry. - * @return {!ol.geom.MultiPoint} Clone. - * @override - * @api - */ -ol.geom.MultiPoint.prototype.clone = function() { - var multiPoint = new ol.geom.MultiPoint(null); - multiPoint.setFlatCoordinates(this.layout, this.flatCoordinates.slice()); - return multiPoint; -}; - - -/** - * @inheritDoc - */ -ol.geom.MultiPoint.prototype.closestPointXY = function(x, y, closestPoint, minSquaredDistance) { - if (minSquaredDistance < - ol.extent.closestSquaredDistanceXY(this.getExtent(), x, y)) { - return minSquaredDistance; - } - var flatCoordinates = this.flatCoordinates; - var stride = this.stride; - var i, ii, j; - for (i = 0, ii = flatCoordinates.length; i < ii; i += stride) { - var squaredDistance = ol.math.squaredDistance( - x, y, flatCoordinates[i], flatCoordinates[i + 1]); - if (squaredDistance < minSquaredDistance) { - minSquaredDistance = squaredDistance; - for (j = 0; j < stride; ++j) { - closestPoint[j] = flatCoordinates[i + j]; - } - closestPoint.length = stride; - } - } - return minSquaredDistance; -}; - - -/** - * Return the coordinates of the multipoint. - * @return {Array.<ol.Coordinate>} Coordinates. - * @override - * @api - */ -ol.geom.MultiPoint.prototype.getCoordinates = function() { - return ol.geom.flat.inflate.coordinates( - this.flatCoordinates, 0, this.flatCoordinates.length, this.stride); -}; - - -/** - * Return the point at the specified index. - * @param {number} index Index. - * @return {ol.geom.Point} Point. - * @api - */ -ol.geom.MultiPoint.prototype.getPoint = function(index) { - var n = !this.flatCoordinates ? - 0 : this.flatCoordinates.length / this.stride; - if (index < 0 || n <= index) { - return null; - } - var point = new ol.geom.Point(null); - point.setFlatCoordinates(this.layout, this.flatCoordinates.slice( - index * this.stride, (index + 1) * this.stride)); - return point; -}; - - -/** - * Return the points of this multipoint. - * @return {Array.<ol.geom.Point>} Points. - * @api - */ -ol.geom.MultiPoint.prototype.getPoints = function() { - var flatCoordinates = this.flatCoordinates; - var layout = this.layout; - var stride = this.stride; - /** @type {Array.<ol.geom.Point>} */ - var points = []; - var i, ii; - for (i = 0, ii = flatCoordinates.length; i < ii; i += stride) { - var point = new ol.geom.Point(null); - point.setFlatCoordinates(layout, flatCoordinates.slice(i, i + stride)); - points.push(point); - } - return points; -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.MultiPoint.prototype.getType = function() { - return ol.geom.GeometryType.MULTI_POINT; -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.MultiPoint.prototype.intersectsExtent = function(extent) { - var flatCoordinates = this.flatCoordinates; - var stride = this.stride; - var i, ii, x, y; - for (i = 0, ii = flatCoordinates.length; i < ii; i += stride) { - x = flatCoordinates[i]; - y = flatCoordinates[i + 1]; - if (ol.extent.containsXY(extent, x, y)) { - return true; - } - } - return false; -}; - - -/** - * Set the coordinates of the multipoint. - * @param {Array.<ol.Coordinate>} coordinates Coordinates. - * @param {ol.geom.GeometryLayout=} opt_layout Layout. - * @override - * @api - */ -ol.geom.MultiPoint.prototype.setCoordinates = function(coordinates, opt_layout) { - if (!coordinates) { - this.setFlatCoordinates(ol.geom.GeometryLayout.XY, null); - } else { - this.setLayout(opt_layout, coordinates, 1); - if (!this.flatCoordinates) { - this.flatCoordinates = []; - } - this.flatCoordinates.length = ol.geom.flat.deflate.coordinates( - this.flatCoordinates, 0, coordinates, this.stride); - this.changed(); - } -}; - - -/** - * @param {ol.geom.GeometryLayout} layout Layout. - * @param {Array.<number>} flatCoordinates Flat coordinates. - */ -ol.geom.MultiPoint.prototype.setFlatCoordinates = function(layout, flatCoordinates) { - this.setFlatCoordinatesInternal(layout, flatCoordinates); - this.changed(); -}; - -goog.provide('ol.geom.flat.center'); - -goog.require('ol.extent'); - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {Array.<Array.<number>>} endss Endss. - * @param {number} stride Stride. - * @return {Array.<number>} Flat centers. - */ -ol.geom.flat.center.linearRingss = function(flatCoordinates, offset, endss, stride) { - var flatCenters = []; - var i, ii; - var extent = ol.extent.createEmpty(); - for (i = 0, ii = endss.length; i < ii; ++i) { - var ends = endss[i]; - extent = ol.extent.createOrUpdateFromFlatCoordinates( - flatCoordinates, offset, ends[0], stride); - flatCenters.push((extent[0] + extent[2]) / 2, (extent[1] + extent[3]) / 2); - offset = ends[ends.length - 1]; - } - return flatCenters; -}; - -goog.provide('ol.geom.MultiPolygon'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.extent'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.MultiPoint'); -goog.require('ol.geom.Polygon'); -goog.require('ol.geom.SimpleGeometry'); -goog.require('ol.geom.flat.area'); -goog.require('ol.geom.flat.center'); -goog.require('ol.geom.flat.closest'); -goog.require('ol.geom.flat.contains'); -goog.require('ol.geom.flat.deflate'); -goog.require('ol.geom.flat.inflate'); -goog.require('ol.geom.flat.interiorpoint'); -goog.require('ol.geom.flat.intersectsextent'); -goog.require('ol.geom.flat.orient'); -goog.require('ol.geom.flat.simplify'); - - -/** - * @classdesc - * Multi-polygon geometry. - * - * @constructor - * @extends {ol.geom.SimpleGeometry} - * @param {Array.<Array.<Array.<ol.Coordinate>>>} coordinates Coordinates. - * @param {ol.geom.GeometryLayout=} opt_layout Layout. - * @api - */ -ol.geom.MultiPolygon = function(coordinates, opt_layout) { - - ol.geom.SimpleGeometry.call(this); - - /** - * @type {Array.<Array.<number>>} - * @private - */ - this.endss_ = []; - - /** - * @private - * @type {number} - */ - this.flatInteriorPointsRevision_ = -1; - - /** - * @private - * @type {Array.<number>} - */ - this.flatInteriorPoints_ = null; - - /** - * @private - * @type {number} - */ - this.maxDelta_ = -1; - - /** - * @private - * @type {number} - */ - this.maxDeltaRevision_ = -1; - - /** - * @private - * @type {number} - */ - this.orientedRevision_ = -1; - - /** - * @private - * @type {Array.<number>} - */ - this.orientedFlatCoordinates_ = null; - - this.setCoordinates(coordinates, opt_layout); - -}; -ol.inherits(ol.geom.MultiPolygon, ol.geom.SimpleGeometry); - - -/** - * Append the passed polygon to this multipolygon. - * @param {ol.geom.Polygon} polygon Polygon. - * @api - */ -ol.geom.MultiPolygon.prototype.appendPolygon = function(polygon) { - /** @type {Array.<number>} */ - var ends; - if (!this.flatCoordinates) { - this.flatCoordinates = polygon.getFlatCoordinates().slice(); - ends = polygon.getEnds().slice(); - this.endss_.push(); - } else { - var offset = this.flatCoordinates.length; - ol.array.extend(this.flatCoordinates, polygon.getFlatCoordinates()); - ends = polygon.getEnds().slice(); - var i, ii; - for (i = 0, ii = ends.length; i < ii; ++i) { - ends[i] += offset; - } - } - this.endss_.push(ends); - this.changed(); -}; - - -/** - * Make a complete copy of the geometry. - * @return {!ol.geom.MultiPolygon} Clone. - * @override - * @api - */ -ol.geom.MultiPolygon.prototype.clone = function() { - var multiPolygon = new ol.geom.MultiPolygon(null); - - var len = this.endss_.length; - var newEndss = new Array(len); - for (var i = 0; i < len; ++i) { - newEndss[i] = this.endss_[i].slice(); - } - - multiPolygon.setFlatCoordinates( - this.layout, this.flatCoordinates.slice(), newEndss); - return multiPolygon; -}; - - -/** - * @inheritDoc - */ -ol.geom.MultiPolygon.prototype.closestPointXY = function(x, y, closestPoint, minSquaredDistance) { - if (minSquaredDistance < - ol.extent.closestSquaredDistanceXY(this.getExtent(), x, y)) { - return minSquaredDistance; - } - if (this.maxDeltaRevision_ != this.getRevision()) { - this.maxDelta_ = Math.sqrt(ol.geom.flat.closest.getssMaxSquaredDelta( - this.flatCoordinates, 0, this.endss_, this.stride, 0)); - this.maxDeltaRevision_ = this.getRevision(); - } - return ol.geom.flat.closest.getssClosestPoint( - this.getOrientedFlatCoordinates(), 0, this.endss_, this.stride, - this.maxDelta_, true, x, y, closestPoint, minSquaredDistance); -}; - - -/** - * @inheritDoc - */ -ol.geom.MultiPolygon.prototype.containsXY = function(x, y) { - return ol.geom.flat.contains.linearRingssContainsXY( - this.getOrientedFlatCoordinates(), 0, this.endss_, this.stride, x, y); -}; - - -/** - * Return the area of the multipolygon on projected plane. - * @return {number} Area (on projected plane). - * @api - */ -ol.geom.MultiPolygon.prototype.getArea = function() { - return ol.geom.flat.area.linearRingss( - this.getOrientedFlatCoordinates(), 0, this.endss_, this.stride); -}; - - -/** - * Get the coordinate array for this geometry. This array has the structure - * of a GeoJSON coordinate array for multi-polygons. - * - * @param {boolean=} opt_right Orient coordinates according to the right-hand - * rule (counter-clockwise for exterior and clockwise for interior rings). - * If `false`, coordinates will be oriented according to the left-hand rule - * (clockwise for exterior and counter-clockwise for interior rings). - * By default, coordinate orientation will depend on how the geometry was - * constructed. - * @return {Array.<Array.<Array.<ol.Coordinate>>>} Coordinates. - * @override - * @api - */ -ol.geom.MultiPolygon.prototype.getCoordinates = function(opt_right) { - var flatCoordinates; - if (opt_right !== undefined) { - flatCoordinates = this.getOrientedFlatCoordinates().slice(); - ol.geom.flat.orient.orientLinearRingss( - flatCoordinates, 0, this.endss_, this.stride, opt_right); - } else { - flatCoordinates = this.flatCoordinates; - } - - return ol.geom.flat.inflate.coordinatesss( - flatCoordinates, 0, this.endss_, this.stride); -}; - - -/** - * @return {Array.<Array.<number>>} Endss. - */ -ol.geom.MultiPolygon.prototype.getEndss = function() { - return this.endss_; -}; - - -/** - * @return {Array.<number>} Flat interior points. - */ -ol.geom.MultiPolygon.prototype.getFlatInteriorPoints = function() { - if (this.flatInteriorPointsRevision_ != this.getRevision()) { - var flatCenters = ol.geom.flat.center.linearRingss( - this.flatCoordinates, 0, this.endss_, this.stride); - this.flatInteriorPoints_ = ol.geom.flat.interiorpoint.linearRingss( - this.getOrientedFlatCoordinates(), 0, this.endss_, this.stride, - flatCenters); - this.flatInteriorPointsRevision_ = this.getRevision(); - } - return this.flatInteriorPoints_; -}; - - -/** - * Return the interior points as {@link ol.geom.MultiPoint multipoint}. - * @return {ol.geom.MultiPoint} Interior points as XYM coordinates, where M is - * the length of the horizontal intersection that the point belongs to. - * @api - */ -ol.geom.MultiPolygon.prototype.getInteriorPoints = function() { - var interiorPoints = new ol.geom.MultiPoint(null); - interiorPoints.setFlatCoordinates(ol.geom.GeometryLayout.XYM, - this.getFlatInteriorPoints().slice()); - return interiorPoints; -}; - - -/** - * @return {Array.<number>} Oriented flat coordinates. - */ -ol.geom.MultiPolygon.prototype.getOrientedFlatCoordinates = function() { - if (this.orientedRevision_ != this.getRevision()) { - var flatCoordinates = this.flatCoordinates; - if (ol.geom.flat.orient.linearRingssAreOriented( - flatCoordinates, 0, this.endss_, this.stride)) { - this.orientedFlatCoordinates_ = flatCoordinates; - } else { - this.orientedFlatCoordinates_ = flatCoordinates.slice(); - this.orientedFlatCoordinates_.length = - ol.geom.flat.orient.orientLinearRingss( - this.orientedFlatCoordinates_, 0, this.endss_, this.stride); - } - this.orientedRevision_ = this.getRevision(); - } - return this.orientedFlatCoordinates_; -}; - - -/** - * @inheritDoc - */ -ol.geom.MultiPolygon.prototype.getSimplifiedGeometryInternal = function(squaredTolerance) { - var simplifiedFlatCoordinates = []; - var simplifiedEndss = []; - simplifiedFlatCoordinates.length = ol.geom.flat.simplify.quantizess( - this.flatCoordinates, 0, this.endss_, this.stride, - Math.sqrt(squaredTolerance), - simplifiedFlatCoordinates, 0, simplifiedEndss); - var simplifiedMultiPolygon = new ol.geom.MultiPolygon(null); - simplifiedMultiPolygon.setFlatCoordinates( - ol.geom.GeometryLayout.XY, simplifiedFlatCoordinates, simplifiedEndss); - return simplifiedMultiPolygon; -}; - - -/** - * Return the polygon at the specified index. - * @param {number} index Index. - * @return {ol.geom.Polygon} Polygon. - * @api - */ -ol.geom.MultiPolygon.prototype.getPolygon = function(index) { - if (index < 0 || this.endss_.length <= index) { - return null; - } - var offset; - if (index === 0) { - offset = 0; - } else { - var prevEnds = this.endss_[index - 1]; - offset = prevEnds[prevEnds.length - 1]; - } - var ends = this.endss_[index].slice(); - var end = ends[ends.length - 1]; - if (offset !== 0) { - var i, ii; - for (i = 0, ii = ends.length; i < ii; ++i) { - ends[i] -= offset; - } - } - var polygon = new ol.geom.Polygon(null); - polygon.setFlatCoordinates( - this.layout, this.flatCoordinates.slice(offset, end), ends); - return polygon; -}; - - -/** - * Return the polygons of this multipolygon. - * @return {Array.<ol.geom.Polygon>} Polygons. - * @api - */ -ol.geom.MultiPolygon.prototype.getPolygons = function() { - var layout = this.layout; - var flatCoordinates = this.flatCoordinates; - var endss = this.endss_; - var polygons = []; - var offset = 0; - var i, ii, j, jj; - for (i = 0, ii = endss.length; i < ii; ++i) { - var ends = endss[i].slice(); - var end = ends[ends.length - 1]; - if (offset !== 0) { - for (j = 0, jj = ends.length; j < jj; ++j) { - ends[j] -= offset; - } - } - var polygon = new ol.geom.Polygon(null); - polygon.setFlatCoordinates( - layout, flatCoordinates.slice(offset, end), ends); - polygons.push(polygon); - offset = end; - } - return polygons; -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.MultiPolygon.prototype.getType = function() { - return ol.geom.GeometryType.MULTI_POLYGON; -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.MultiPolygon.prototype.intersectsExtent = function(extent) { - return ol.geom.flat.intersectsextent.linearRingss( - this.getOrientedFlatCoordinates(), 0, this.endss_, this.stride, extent); -}; - - -/** - * Set the coordinates of the multipolygon. - * @param {Array.<Array.<Array.<ol.Coordinate>>>} coordinates Coordinates. - * @param {ol.geom.GeometryLayout=} opt_layout Layout. - * @override - * @api - */ -ol.geom.MultiPolygon.prototype.setCoordinates = function(coordinates, opt_layout) { - if (!coordinates) { - this.setFlatCoordinates(ol.geom.GeometryLayout.XY, null, this.endss_); - } else { - this.setLayout(opt_layout, coordinates, 3); - if (!this.flatCoordinates) { - this.flatCoordinates = []; - } - var endss = ol.geom.flat.deflate.coordinatesss( - this.flatCoordinates, 0, coordinates, this.stride, this.endss_); - if (endss.length === 0) { - this.flatCoordinates.length = 0; - } else { - var lastEnds = endss[endss.length - 1]; - this.flatCoordinates.length = lastEnds.length === 0 ? - 0 : lastEnds[lastEnds.length - 1]; - } - this.changed(); - } -}; - - -/** - * @param {ol.geom.GeometryLayout} layout Layout. - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {Array.<Array.<number>>} endss Endss. - */ -ol.geom.MultiPolygon.prototype.setFlatCoordinates = function(layout, flatCoordinates, endss) { - this.setFlatCoordinatesInternal(layout, flatCoordinates); - this.endss_ = endss; - this.changed(); -}; - - -/** - * @param {Array.<ol.geom.Polygon>} polygons Polygons. - */ -ol.geom.MultiPolygon.prototype.setPolygons = function(polygons) { - var layout = this.getLayout(); - var flatCoordinates = []; - var endss = []; - var i, ii, ends; - for (i = 0, ii = polygons.length; i < ii; ++i) { - var polygon = polygons[i]; - if (i === 0) { - layout = polygon.getLayout(); - } - var offset = flatCoordinates.length; - ends = polygon.getEnds(); - var j, jj; - for (j = 0, jj = ends.length; j < jj; ++j) { - ends[j] += offset; - } - ol.array.extend(flatCoordinates, polygon.getFlatCoordinates()); - endss.push(ends); - } - this.setFlatCoordinates(layout, flatCoordinates, endss); -}; - -goog.provide('ol.format.EsriJSON'); - -goog.require('ol'); -goog.require('ol.Feature'); -goog.require('ol.asserts'); -goog.require('ol.extent'); -goog.require('ol.format.Feature'); -goog.require('ol.format.JSONFeature'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.LineString'); -goog.require('ol.geom.LinearRing'); -goog.require('ol.geom.MultiLineString'); -goog.require('ol.geom.MultiPoint'); -goog.require('ol.geom.MultiPolygon'); -goog.require('ol.geom.Point'); -goog.require('ol.geom.Polygon'); -goog.require('ol.geom.flat.deflate'); -goog.require('ol.geom.flat.orient'); -goog.require('ol.obj'); -goog.require('ol.proj'); - - -/** - * @classdesc - * Feature format for reading and writing data in the EsriJSON format. - * - * @constructor - * @extends {ol.format.JSONFeature} - * @param {olx.format.EsriJSONOptions=} opt_options Options. - * @api - */ -ol.format.EsriJSON = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - ol.format.JSONFeature.call(this); - - /** - * Name of the geometry attribute for features. - * @type {string|undefined} - * @private - */ - this.geometryName_ = options.geometryName; - -}; -ol.inherits(ol.format.EsriJSON, ol.format.JSONFeature); - - -/** - * @param {EsriJSONGeometry} object Object. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @private - * @return {ol.geom.Geometry} Geometry. - */ -ol.format.EsriJSON.readGeometry_ = function(object, opt_options) { - if (!object) { - return null; - } - /** @type {ol.geom.GeometryType} */ - var type; - if (typeof object.x === 'number' && typeof object.y === 'number') { - type = ol.geom.GeometryType.POINT; - } else if (object.points) { - type = ol.geom.GeometryType.MULTI_POINT; - } else if (object.paths) { - if (object.paths.length === 1) { - type = ol.geom.GeometryType.LINE_STRING; - } else { - type = ol.geom.GeometryType.MULTI_LINE_STRING; - } - } else if (object.rings) { - var layout = ol.format.EsriJSON.getGeometryLayout_(object); - var rings = ol.format.EsriJSON.convertRings_(object.rings, layout); - object = /** @type {EsriJSONGeometry} */(ol.obj.assign({}, object)); - if (rings.length === 1) { - type = ol.geom.GeometryType.POLYGON; - object.rings = rings[0]; - } else { - type = ol.geom.GeometryType.MULTI_POLYGON; - object.rings = rings; - } - } - var geometryReader = ol.format.EsriJSON.GEOMETRY_READERS_[type]; - return /** @type {ol.geom.Geometry} */ ( - ol.format.Feature.transformWithOptions( - geometryReader(object), false, opt_options)); -}; - - -/** - * Determines inner and outer rings. - * Checks if any polygons in this array contain any other polygons in this - * array. It is used for checking for holes. - * Logic inspired by: https://github.com/Esri/terraformer-arcgis-parser - * @param {Array.<!Array.<!Array.<number>>>} rings Rings. - * @param {ol.geom.GeometryLayout} layout Geometry layout. - * @private - * @return {Array.<!Array.<!Array.<number>>>} Transformed rings. - */ -ol.format.EsriJSON.convertRings_ = function(rings, layout) { - var flatRing = []; - var outerRings = []; - var holes = []; - var i, ii; - for (i = 0, ii = rings.length; i < ii; ++i) { - flatRing.length = 0; - ol.geom.flat.deflate.coordinates(flatRing, 0, rings[i], layout.length); - // is this ring an outer ring? is it clockwise? - var clockwise = ol.geom.flat.orient.linearRingIsClockwise(flatRing, 0, - flatRing.length, layout.length); - if (clockwise) { - outerRings.push([rings[i]]); - } else { - holes.push(rings[i]); - } - } - while (holes.length) { - var hole = holes.shift(); - var matched = false; - // loop over all outer rings and see if they contain our hole. - for (i = outerRings.length - 1; i >= 0; i--) { - var outerRing = outerRings[i][0]; - var containsHole = ol.extent.containsExtent( - new ol.geom.LinearRing(outerRing).getExtent(), - new ol.geom.LinearRing(hole).getExtent() - ); - if (containsHole) { - // the hole is contained push it into our polygon - outerRings[i].push(hole); - matched = true; - break; - } - } - if (!matched) { - // no outer rings contain this hole turn it into and outer - // ring (reverse it) - outerRings.push([hole.reverse()]); - } - } - return outerRings; -}; - - -/** - * @param {EsriJSONGeometry} object Object. - * @private - * @return {ol.geom.Geometry} Point. - */ -ol.format.EsriJSON.readPointGeometry_ = function(object) { - var point; - if (object.m !== undefined && object.z !== undefined) { - point = new ol.geom.Point([object.x, object.y, object.z, object.m], - ol.geom.GeometryLayout.XYZM); - } else if (object.z !== undefined) { - point = new ol.geom.Point([object.x, object.y, object.z], - ol.geom.GeometryLayout.XYZ); - } else if (object.m !== undefined) { - point = new ol.geom.Point([object.x, object.y, object.m], - ol.geom.GeometryLayout.XYM); - } else { - point = new ol.geom.Point([object.x, object.y]); - } - return point; -}; - - -/** - * @param {EsriJSONGeometry} object Object. - * @private - * @return {ol.geom.Geometry} LineString. - */ -ol.format.EsriJSON.readLineStringGeometry_ = function(object) { - var layout = ol.format.EsriJSON.getGeometryLayout_(object); - return new ol.geom.LineString(object.paths[0], layout); -}; - - -/** - * @param {EsriJSONGeometry} object Object. - * @private - * @return {ol.geom.Geometry} MultiLineString. - */ -ol.format.EsriJSON.readMultiLineStringGeometry_ = function(object) { - var layout = ol.format.EsriJSON.getGeometryLayout_(object); - return new ol.geom.MultiLineString(object.paths, layout); -}; - - -/** - * @param {EsriJSONGeometry} object Object. - * @private - * @return {ol.geom.GeometryLayout} The geometry layout to use. - */ -ol.format.EsriJSON.getGeometryLayout_ = function(object) { - var layout = ol.geom.GeometryLayout.XY; - if (object.hasZ === true && object.hasM === true) { - layout = ol.geom.GeometryLayout.XYZM; - } else if (object.hasZ === true) { - layout = ol.geom.GeometryLayout.XYZ; - } else if (object.hasM === true) { - layout = ol.geom.GeometryLayout.XYM; - } - return layout; -}; - - -/** - * @param {EsriJSONGeometry} object Object. - * @private - * @return {ol.geom.Geometry} MultiPoint. - */ -ol.format.EsriJSON.readMultiPointGeometry_ = function(object) { - var layout = ol.format.EsriJSON.getGeometryLayout_(object); - return new ol.geom.MultiPoint(object.points, layout); -}; - - -/** - * @param {EsriJSONGeometry} object Object. - * @private - * @return {ol.geom.Geometry} MultiPolygon. - */ -ol.format.EsriJSON.readMultiPolygonGeometry_ = function(object) { - var layout = ol.format.EsriJSON.getGeometryLayout_(object); - return new ol.geom.MultiPolygon( - /** @type {Array.<Array.<Array.<Array.<number>>>>} */(object.rings), - layout); -}; - - -/** - * @param {EsriJSONGeometry} object Object. - * @private - * @return {ol.geom.Geometry} Polygon. - */ -ol.format.EsriJSON.readPolygonGeometry_ = function(object) { - var layout = ol.format.EsriJSON.getGeometryLayout_(object); - return new ol.geom.Polygon(object.rings, layout); -}; - - -/** - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @private - * @return {EsriJSONGeometry} EsriJSON geometry. - */ -ol.format.EsriJSON.writePointGeometry_ = function(geometry, opt_options) { - var coordinates = /** @type {ol.geom.Point} */ (geometry).getCoordinates(); - var esriJSON; - var layout = /** @type {ol.geom.Point} */ (geometry).getLayout(); - if (layout === ol.geom.GeometryLayout.XYZ) { - esriJSON = /** @type {EsriJSONPoint} */ ({ - x: coordinates[0], - y: coordinates[1], - z: coordinates[2] - }); - } else if (layout === ol.geom.GeometryLayout.XYM) { - esriJSON = /** @type {EsriJSONPoint} */ ({ - x: coordinates[0], - y: coordinates[1], - m: coordinates[2] - }); - } else if (layout === ol.geom.GeometryLayout.XYZM) { - esriJSON = /** @type {EsriJSONPoint} */ ({ - x: coordinates[0], - y: coordinates[1], - z: coordinates[2], - m: coordinates[3] - }); - } else if (layout === ol.geom.GeometryLayout.XY) { - esriJSON = /** @type {EsriJSONPoint} */ ({ - x: coordinates[0], - y: coordinates[1] - }); - } else { - ol.asserts.assert(false, 34); // Invalid geometry layout - } - return /** @type {EsriJSONGeometry} */ (esriJSON); -}; - - -/** - * @param {ol.geom.SimpleGeometry} geometry Geometry. - * @private - * @return {Object} Object with boolean hasZ and hasM keys. - */ -ol.format.EsriJSON.getHasZM_ = function(geometry) { - var layout = geometry.getLayout(); - return { - hasZ: (layout === ol.geom.GeometryLayout.XYZ || - layout === ol.geom.GeometryLayout.XYZM), - hasM: (layout === ol.geom.GeometryLayout.XYM || - layout === ol.geom.GeometryLayout.XYZM) - }; -}; - - -/** - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @private - * @return {EsriJSONPolyline} EsriJSON geometry. - */ -ol.format.EsriJSON.writeLineStringGeometry_ = function(geometry, opt_options) { - var hasZM = ol.format.EsriJSON.getHasZM_(/** @type {ol.geom.LineString} */(geometry)); - return /** @type {EsriJSONPolyline} */ ({ - hasZ: hasZM.hasZ, - hasM: hasZM.hasM, - paths: [ - /** @type {ol.geom.LineString} */ (geometry).getCoordinates() - ] - }); -}; - - -/** - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @private - * @return {EsriJSONPolygon} EsriJSON geometry. - */ -ol.format.EsriJSON.writePolygonGeometry_ = function(geometry, opt_options) { - // Esri geometries use the left-hand rule - var hasZM = ol.format.EsriJSON.getHasZM_(/** @type {ol.geom.Polygon} */(geometry)); - return /** @type {EsriJSONPolygon} */ ({ - hasZ: hasZM.hasZ, - hasM: hasZM.hasM, - rings: /** @type {ol.geom.Polygon} */ (geometry).getCoordinates(false) - }); -}; - - -/** - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @private - * @return {EsriJSONPolyline} EsriJSON geometry. - */ -ol.format.EsriJSON.writeMultiLineStringGeometry_ = function(geometry, opt_options) { - var hasZM = ol.format.EsriJSON.getHasZM_(/** @type {ol.geom.MultiLineString} */(geometry)); - return /** @type {EsriJSONPolyline} */ ({ - hasZ: hasZM.hasZ, - hasM: hasZM.hasM, - paths: /** @type {ol.geom.MultiLineString} */ (geometry).getCoordinates() - }); -}; - - -/** - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @private - * @return {EsriJSONMultipoint} EsriJSON geometry. - */ -ol.format.EsriJSON.writeMultiPointGeometry_ = function(geometry, opt_options) { - var hasZM = ol.format.EsriJSON.getHasZM_(/** @type {ol.geom.MultiPoint} */(geometry)); - return /** @type {EsriJSONMultipoint} */ ({ - hasZ: hasZM.hasZ, - hasM: hasZM.hasM, - points: /** @type {ol.geom.MultiPoint} */ (geometry).getCoordinates() - }); -}; - - -/** - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @private - * @return {EsriJSONPolygon} EsriJSON geometry. - */ -ol.format.EsriJSON.writeMultiPolygonGeometry_ = function(geometry, - opt_options) { - var hasZM = ol.format.EsriJSON.getHasZM_(/** @type {ol.geom.MultiPolygon} */(geometry)); - var coordinates = /** @type {ol.geom.MultiPolygon} */ (geometry).getCoordinates(false); - var output = []; - for (var i = 0; i < coordinates.length; i++) { - for (var x = coordinates[i].length - 1; x >= 0; x--) { - output.push(coordinates[i][x]); - } - } - return /** @type {EsriJSONPolygon} */ ({ - hasZ: hasZM.hasZ, - hasM: hasZM.hasM, - rings: output - }); -}; - - -/** - * @const - * @private - * @type {Object.<ol.geom.GeometryType, function(EsriJSONGeometry): ol.geom.Geometry>} - */ -ol.format.EsriJSON.GEOMETRY_READERS_ = {}; -ol.format.EsriJSON.GEOMETRY_READERS_[ol.geom.GeometryType.POINT] = - ol.format.EsriJSON.readPointGeometry_; -ol.format.EsriJSON.GEOMETRY_READERS_[ol.geom.GeometryType.LINE_STRING] = - ol.format.EsriJSON.readLineStringGeometry_; -ol.format.EsriJSON.GEOMETRY_READERS_[ol.geom.GeometryType.POLYGON] = - ol.format.EsriJSON.readPolygonGeometry_; -ol.format.EsriJSON.GEOMETRY_READERS_[ol.geom.GeometryType.MULTI_POINT] = - ol.format.EsriJSON.readMultiPointGeometry_; -ol.format.EsriJSON.GEOMETRY_READERS_[ol.geom.GeometryType.MULTI_LINE_STRING] = - ol.format.EsriJSON.readMultiLineStringGeometry_; -ol.format.EsriJSON.GEOMETRY_READERS_[ol.geom.GeometryType.MULTI_POLYGON] = - ol.format.EsriJSON.readMultiPolygonGeometry_; - - -/** - * @const - * @private - * @type {Object.<string, function(ol.geom.Geometry, olx.format.WriteOptions=): (EsriJSONGeometry)>} - */ -ol.format.EsriJSON.GEOMETRY_WRITERS_ = {}; -ol.format.EsriJSON.GEOMETRY_WRITERS_[ol.geom.GeometryType.POINT] = - ol.format.EsriJSON.writePointGeometry_; -ol.format.EsriJSON.GEOMETRY_WRITERS_[ol.geom.GeometryType.LINE_STRING] = - ol.format.EsriJSON.writeLineStringGeometry_; -ol.format.EsriJSON.GEOMETRY_WRITERS_[ol.geom.GeometryType.POLYGON] = - ol.format.EsriJSON.writePolygonGeometry_; -ol.format.EsriJSON.GEOMETRY_WRITERS_[ol.geom.GeometryType.MULTI_POINT] = - ol.format.EsriJSON.writeMultiPointGeometry_; -ol.format.EsriJSON.GEOMETRY_WRITERS_[ol.geom.GeometryType.MULTI_LINE_STRING] = - ol.format.EsriJSON.writeMultiLineStringGeometry_; -ol.format.EsriJSON.GEOMETRY_WRITERS_[ol.geom.GeometryType.MULTI_POLYGON] = - ol.format.EsriJSON.writeMultiPolygonGeometry_; - - -/** - * Read a feature from a EsriJSON Feature source. Only works for Feature, - * use `readFeatures` to read FeatureCollection source. - * - * @function - * @param {ArrayBuffer|Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {ol.Feature} Feature. - * @api - */ -ol.format.EsriJSON.prototype.readFeature; - - -/** - * Read all features from a EsriJSON source. Works with both Feature and - * FeatureCollection sources. - * - * @function - * @param {ArrayBuffer|Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {Array.<ol.Feature>} Features. - * @api - */ -ol.format.EsriJSON.prototype.readFeatures; - - -/** - * @inheritDoc - */ -ol.format.EsriJSON.prototype.readFeatureFromObject = function( - object, opt_options) { - var esriJSONFeature = /** @type {EsriJSONFeature} */ (object); - var geometry = ol.format.EsriJSON.readGeometry_(esriJSONFeature.geometry, - opt_options); - var feature = new ol.Feature(); - if (this.geometryName_) { - feature.setGeometryName(this.geometryName_); - } - feature.setGeometry(geometry); - if (opt_options && opt_options.idField && - esriJSONFeature.attributes[opt_options.idField]) { - feature.setId(/** @type {number} */( - esriJSONFeature.attributes[opt_options.idField])); - } - if (esriJSONFeature.attributes) { - feature.setProperties(esriJSONFeature.attributes); - } - return feature; -}; - - -/** - * @inheritDoc - */ -ol.format.EsriJSON.prototype.readFeaturesFromObject = function( - object, opt_options) { - var esriJSONObject = /** @type {EsriJSONObject} */ (object); - var options = opt_options ? opt_options : {}; - if (esriJSONObject.features) { - var esriJSONFeatureCollection = /** @type {EsriJSONFeatureCollection} */ - (object); - /** @type {Array.<ol.Feature>} */ - var features = []; - var esriJSONFeatures = esriJSONFeatureCollection.features; - var i, ii; - options.idField = object.objectIdFieldName; - for (i = 0, ii = esriJSONFeatures.length; i < ii; ++i) { - features.push(this.readFeatureFromObject(esriJSONFeatures[i], - options)); - } - return features; - } else { - return [this.readFeatureFromObject(object, options)]; - } -}; - - -/** - * Read a geometry from a EsriJSON source. - * - * @function - * @param {ArrayBuffer|Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {ol.geom.Geometry} Geometry. - * @api - */ -ol.format.EsriJSON.prototype.readGeometry; - - -/** - * @inheritDoc - */ -ol.format.EsriJSON.prototype.readGeometryFromObject = function( - object, opt_options) { - return ol.format.EsriJSON.readGeometry_( - /** @type {EsriJSONGeometry} */(object), opt_options); -}; - - -/** - * Read the projection from a EsriJSON source. - * - * @function - * @param {ArrayBuffer|Document|Node|Object|string} source Source. - * @return {ol.proj.Projection} Projection. - * @api - */ -ol.format.EsriJSON.prototype.readProjection; - - -/** - * @inheritDoc - */ -ol.format.EsriJSON.prototype.readProjectionFromObject = function(object) { - var esriJSONObject = /** @type {EsriJSONObject} */ (object); - if (esriJSONObject.spatialReference && esriJSONObject.spatialReference.wkid) { - var crs = esriJSONObject.spatialReference.wkid; - return ol.proj.get('EPSG:' + crs); - } else { - return null; - } -}; - - -/** - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @private - * @return {EsriJSONGeometry} EsriJSON geometry. - */ -ol.format.EsriJSON.writeGeometry_ = function(geometry, opt_options) { - var geometryWriter = ol.format.EsriJSON.GEOMETRY_WRITERS_[geometry.getType()]; - return geometryWriter(/** @type {ol.geom.Geometry} */( - ol.format.Feature.transformWithOptions(geometry, true, opt_options)), - opt_options); -}; - - -/** - * Encode a geometry as a EsriJSON string. - * - * @function - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {string} EsriJSON. - * @api - */ -ol.format.EsriJSON.prototype.writeGeometry; - - -/** - * Encode a geometry as a EsriJSON object. - * - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {EsriJSONGeometry} Object. - * @override - * @api - */ -ol.format.EsriJSON.prototype.writeGeometryObject = function(geometry, - opt_options) { - return ol.format.EsriJSON.writeGeometry_(geometry, - this.adaptOptions(opt_options)); -}; - - -/** - * Encode a feature as a EsriJSON Feature string. - * - * @function - * @param {ol.Feature} feature Feature. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {string} EsriJSON. - * @api - */ -ol.format.EsriJSON.prototype.writeFeature; - - -/** - * Encode a feature as a esriJSON Feature object. - * - * @param {ol.Feature} feature Feature. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {Object} Object. - * @override - * @api - */ -ol.format.EsriJSON.prototype.writeFeatureObject = function( - feature, opt_options) { - opt_options = this.adaptOptions(opt_options); - var object = {}; - var geometry = feature.getGeometry(); - if (geometry) { - object['geometry'] = - ol.format.EsriJSON.writeGeometry_(geometry, opt_options); - if (opt_options && opt_options.featureProjection) { - object['geometry']['spatialReference'] = /** @type {EsriJSONCRS} */({ - wkid: ol.proj.get( - opt_options.featureProjection).getCode().split(':').pop() - }); - } - } - var properties = feature.getProperties(); - delete properties[feature.getGeometryName()]; - if (!ol.obj.isEmpty(properties)) { - object['attributes'] = properties; - } else { - object['attributes'] = {}; - } - return object; -}; - - -/** - * Encode an array of features as EsriJSON. - * - * @function - * @param {Array.<ol.Feature>} features Features. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {string} EsriJSON. - * @api - */ -ol.format.EsriJSON.prototype.writeFeatures; - - -/** - * Encode an array of features as a EsriJSON object. - * - * @param {Array.<ol.Feature>} features Features. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {Object} EsriJSON Object. - * @override - * @api - */ -ol.format.EsriJSON.prototype.writeFeaturesObject = function(features, opt_options) { - opt_options = this.adaptOptions(opt_options); - var objects = []; - var i, ii; - for (i = 0, ii = features.length; i < ii; ++i) { - objects.push(this.writeFeatureObject(features[i], opt_options)); - } - return /** @type {EsriJSONFeatureCollection} */ ({ - 'features': objects - }); -}; - -goog.provide('ol.format.filter.Filter'); - - -/** - * @classdesc - * Abstract class; normally only used for creating subclasses and not instantiated in apps. - * Base class for WFS GetFeature filters. - * - * deprecated: This class will no longer be exported starting from the next major version. - * - * @constructor - * @abstract - * @param {!string} tagName The XML tag name for this filter. - * @struct - * @api - */ -ol.format.filter.Filter = function(tagName) { - - /** - * @private - * @type {!string} - */ - this.tagName_ = tagName; -}; - -/** - * The XML tag name for a filter. - * @returns {!string} Name. - */ -ol.format.filter.Filter.prototype.getTagName = function() { - return this.tagName_; -}; - -goog.provide('ol.format.filter.LogicalNary'); - -goog.require('ol'); -goog.require('ol.asserts'); -goog.require('ol.format.filter.Filter'); - - -/** - * @classdesc - * Abstract class; normally only used for creating subclasses and not instantiated in apps. - * Base class for WFS GetFeature n-ary logical filters. - * - * @constructor - * @abstract - * @param {!string} tagName The XML tag name for this filter. - * @param {...ol.format.filter.Filter} conditions Conditions. - * @extends {ol.format.filter.Filter} - */ -ol.format.filter.LogicalNary = function(tagName, conditions) { - - ol.format.filter.Filter.call(this, tagName); - - /** - * @public - * @type {Array.<ol.format.filter.Filter>} - */ - this.conditions = Array.prototype.slice.call(arguments, 1); - ol.asserts.assert(this.conditions.length >= 2, 57); // At least 2 conditions are required. -}; -ol.inherits(ol.format.filter.LogicalNary, ol.format.filter.Filter); - -goog.provide('ol.format.filter.And'); - -goog.require('ol'); -goog.require('ol.format.filter.LogicalNary'); - -/** - * @classdesc - * Represents a logical `<And>` operator between two or more filter conditions. - * - * deprecated: This class will no longer be exported starting from the next major version. - * - * @constructor - * @abstract - * @param {...ol.format.filter.Filter} conditions Conditions. - * @extends {ol.format.filter.LogicalNary} - * @api - */ -ol.format.filter.And = function(conditions) { - var params = ['And'].concat(Array.prototype.slice.call(arguments)); - ol.format.filter.LogicalNary.apply(this, params); -}; -ol.inherits(ol.format.filter.And, ol.format.filter.LogicalNary); - -goog.provide('ol.format.filter.Bbox'); - -goog.require('ol'); -goog.require('ol.format.filter.Filter'); - - -/** - * @classdesc - * Represents a `<BBOX>` operator to test whether a geometry-valued property - * intersects a fixed bounding box - * - * @constructor - * @param {!string} geometryName Geometry name to use. - * @param {!ol.Extent} extent Extent. - * @param {string=} opt_srsName SRS name. No srsName attribute will be - * set on geometries when this is not provided. - * @extends {ol.format.filter.Filter} - * @api - */ -ol.format.filter.Bbox = function(geometryName, extent, opt_srsName) { - - ol.format.filter.Filter.call(this, 'BBOX'); - - /** - * @public - * @type {!string} - */ - this.geometryName = geometryName; - - /** - * @public - * @type {ol.Extent} - */ - this.extent = extent; - - /** - * @public - * @type {string|undefined} - */ - this.srsName = opt_srsName; -}; -ol.inherits(ol.format.filter.Bbox, ol.format.filter.Filter); - -goog.provide('ol.format.filter.Comparison'); - -goog.require('ol'); -goog.require('ol.format.filter.Filter'); - - -/** - * @classdesc - * Abstract class; normally only used for creating subclasses and not instantiated in apps. - * Base class for WFS GetFeature property comparison filters. - * - * deprecated: This class will no longer be exported starting from the next major version. - * - * @constructor - * @abstract - * @param {!string} tagName The XML tag name for this filter. - * @param {!string} propertyName Name of the context property to compare. - * @extends {ol.format.filter.Filter} - * @api - */ -ol.format.filter.Comparison = function(tagName, propertyName) { - - ol.format.filter.Filter.call(this, tagName); - - /** - * @public - * @type {!string} - */ - this.propertyName = propertyName; -}; -ol.inherits(ol.format.filter.Comparison, ol.format.filter.Filter); - -goog.provide('ol.format.filter.During'); - -goog.require('ol'); -goog.require('ol.format.filter.Comparison'); - - -/** - * @classdesc - * Represents a `<During>` comparison operator. - * - * @constructor - * @param {!string} propertyName Name of the context property to compare. - * @param {!string} begin The begin date in ISO-8601 format. - * @param {!string} end The end date in ISO-8601 format. - * @extends {ol.format.filter.Comparison} - * @api - */ -ol.format.filter.During = function(propertyName, begin, end) { - ol.format.filter.Comparison.call(this, 'During', propertyName); - - /** - * @public - * @type {!string} - */ - this.begin = begin; - - /** - * @public - * @type {!string} - */ - this.end = end; -}; -ol.inherits(ol.format.filter.During, ol.format.filter.Comparison); - -goog.provide('ol.format.filter.ComparisonBinary'); - -goog.require('ol'); -goog.require('ol.format.filter.Comparison'); - - -/** - * @classdesc - * Abstract class; normally only used for creating subclasses and not instantiated in apps. - * Base class for WFS GetFeature property binary comparison filters. - * - * deprecated: This class will no longer be exported starting from the next major version. - * - * @constructor - * @abstract - * @param {!string} tagName The XML tag name for this filter. - * @param {!string} propertyName Name of the context property to compare. - * @param {!(string|number)} expression The value to compare. - * @param {boolean=} opt_matchCase Case-sensitive? - * @extends {ol.format.filter.Comparison} - * @api - */ -ol.format.filter.ComparisonBinary = function( - tagName, propertyName, expression, opt_matchCase) { - - ol.format.filter.Comparison.call(this, tagName, propertyName); - - /** - * @public - * @type {!(string|number)} - */ - this.expression = expression; - - /** - * @public - * @type {boolean|undefined} - */ - this.matchCase = opt_matchCase; -}; -ol.inherits(ol.format.filter.ComparisonBinary, ol.format.filter.Comparison); - -goog.provide('ol.format.filter.EqualTo'); - -goog.require('ol'); -goog.require('ol.format.filter.ComparisonBinary'); - - -/** - * @classdesc - * Represents a `<PropertyIsEqualTo>` comparison operator. - * - * @constructor - * @param {!string} propertyName Name of the context property to compare. - * @param {!(string|number)} expression The value to compare. - * @param {boolean=} opt_matchCase Case-sensitive? - * @extends {ol.format.filter.ComparisonBinary} - * @api - */ -ol.format.filter.EqualTo = function(propertyName, expression, opt_matchCase) { - ol.format.filter.ComparisonBinary.call(this, 'PropertyIsEqualTo', propertyName, expression, opt_matchCase); -}; -ol.inherits(ol.format.filter.EqualTo, ol.format.filter.ComparisonBinary); - -goog.provide('ol.format.filter.GreaterThan'); - -goog.require('ol'); -goog.require('ol.format.filter.ComparisonBinary'); - - -/** - * @classdesc - * Represents a `<PropertyIsGreaterThan>` comparison operator. - * - * @constructor - * @param {!string} propertyName Name of the context property to compare. - * @param {!number} expression The value to compare. - * @extends {ol.format.filter.ComparisonBinary} - * @api - */ -ol.format.filter.GreaterThan = function(propertyName, expression) { - ol.format.filter.ComparisonBinary.call(this, 'PropertyIsGreaterThan', propertyName, expression); -}; -ol.inherits(ol.format.filter.GreaterThan, ol.format.filter.ComparisonBinary); - -goog.provide('ol.format.filter.GreaterThanOrEqualTo'); - -goog.require('ol'); -goog.require('ol.format.filter.ComparisonBinary'); - - -/** - * @classdesc - * Represents a `<PropertyIsGreaterThanOrEqualTo>` comparison operator. - * - * @constructor - * @param {!string} propertyName Name of the context property to compare. - * @param {!number} expression The value to compare. - * @extends {ol.format.filter.ComparisonBinary} - * @api - */ -ol.format.filter.GreaterThanOrEqualTo = function(propertyName, expression) { - ol.format.filter.ComparisonBinary.call(this, 'PropertyIsGreaterThanOrEqualTo', propertyName, expression); -}; -ol.inherits(ol.format.filter.GreaterThanOrEqualTo, ol.format.filter.ComparisonBinary); - -goog.provide('ol.format.filter.Spatial'); - -goog.require('ol'); -goog.require('ol.format.filter.Filter'); - - -/** - * @classdesc - * Abstract class; normally only used for creating subclasses and not instantiated in apps. - * Represents a spatial operator to test whether a geometry-valued property - * relates to a given geometry. - * - * deprecated: This class will no longer be exported starting from the next major version. - * - * @constructor - * @abstract - * @param {!string} tagName The XML tag name for this filter. - * @param {!string} geometryName Geometry name to use. - * @param {!ol.geom.Geometry} geometry Geometry. - * @param {string=} opt_srsName SRS name. No srsName attribute will be - * set on geometries when this is not provided. - * @extends {ol.format.filter.Filter} - * @api - */ -ol.format.filter.Spatial = function(tagName, geometryName, geometry, opt_srsName) { - - ol.format.filter.Filter.call(this, tagName); - - /** - * @public - * @type {!string} - */ - this.geometryName = geometryName || 'the_geom'; - - /** - * @public - * @type {ol.geom.Geometry} - */ - this.geometry = geometry; - - /** - * @public - * @type {string|undefined} - */ - this.srsName = opt_srsName; -}; -ol.inherits(ol.format.filter.Spatial, ol.format.filter.Filter); - -goog.provide('ol.format.filter.Intersects'); - -goog.require('ol'); -goog.require('ol.format.filter.Spatial'); - - -/** - * @classdesc - * Represents a `<Intersects>` operator to test whether a geometry-valued property - * intersects a given geometry. - * - * @constructor - * @param {!string} geometryName Geometry name to use. - * @param {!ol.geom.Geometry} geometry Geometry. - * @param {string=} opt_srsName SRS name. No srsName attribute will be - * set on geometries when this is not provided. - * @extends {ol.format.filter.Spatial} - * @api - */ -ol.format.filter.Intersects = function(geometryName, geometry, opt_srsName) { - - ol.format.filter.Spatial.call(this, 'Intersects', geometryName, geometry, opt_srsName); - -}; -ol.inherits(ol.format.filter.Intersects, ol.format.filter.Spatial); - -goog.provide('ol.format.filter.IsBetween'); - -goog.require('ol'); -goog.require('ol.format.filter.Comparison'); - - -/** - * @classdesc - * Represents a `<PropertyIsBetween>` comparison operator. - * - * @constructor - * @param {!string} propertyName Name of the context property to compare. - * @param {!number} lowerBoundary The lower bound of the range. - * @param {!number} upperBoundary The upper bound of the range. - * @extends {ol.format.filter.Comparison} - * @api - */ -ol.format.filter.IsBetween = function(propertyName, lowerBoundary, upperBoundary) { - ol.format.filter.Comparison.call(this, 'PropertyIsBetween', propertyName); - - /** - * @public - * @type {!number} - */ - this.lowerBoundary = lowerBoundary; - - /** - * @public - * @type {!number} - */ - this.upperBoundary = upperBoundary; -}; -ol.inherits(ol.format.filter.IsBetween, ol.format.filter.Comparison); - -goog.provide('ol.format.filter.IsLike'); - -goog.require('ol'); -goog.require('ol.format.filter.Comparison'); - - -/** - * @classdesc - * Represents a `<PropertyIsLike>` comparison operator. - * - * @constructor - * @param {!string} propertyName Name of the context property to compare. - * @param {!string} pattern Text pattern. - * @param {string=} opt_wildCard Pattern character which matches any sequence of - * zero or more string characters. Default is '*'. - * @param {string=} opt_singleChar pattern character which matches any single - * string character. Default is '.'. - * @param {string=} opt_escapeChar Escape character which can be used to escape - * the pattern characters. Default is '!'. - * @param {boolean=} opt_matchCase Case-sensitive? - * @extends {ol.format.filter.Comparison} - * @api - */ -ol.format.filter.IsLike = function(propertyName, pattern, - opt_wildCard, opt_singleChar, opt_escapeChar, opt_matchCase) { - ol.format.filter.Comparison.call(this, 'PropertyIsLike', propertyName); - - /** - * @public - * @type {!string} - */ - this.pattern = pattern; - - /** - * @public - * @type {!string} - */ - this.wildCard = (opt_wildCard !== undefined) ? opt_wildCard : '*'; - - /** - * @public - * @type {!string} - */ - this.singleChar = (opt_singleChar !== undefined) ? opt_singleChar : '.'; - - /** - * @public - * @type {!string} - */ - this.escapeChar = (opt_escapeChar !== undefined) ? opt_escapeChar : '!'; - - /** - * @public - * @type {boolean|undefined} - */ - this.matchCase = opt_matchCase; -}; -ol.inherits(ol.format.filter.IsLike, ol.format.filter.Comparison); - -goog.provide('ol.format.filter.IsNull'); - -goog.require('ol'); -goog.require('ol.format.filter.Comparison'); - - -/** - * @classdesc - * Represents a `<PropertyIsNull>` comparison operator. - * - * @constructor - * @param {!string} propertyName Name of the context property to compare. - * @extends {ol.format.filter.Comparison} - * @api - */ -ol.format.filter.IsNull = function(propertyName) { - ol.format.filter.Comparison.call(this, 'PropertyIsNull', propertyName); -}; -ol.inherits(ol.format.filter.IsNull, ol.format.filter.Comparison); - -goog.provide('ol.format.filter.LessThan'); - -goog.require('ol'); -goog.require('ol.format.filter.ComparisonBinary'); - - -/** - * @classdesc - * Represents a `<PropertyIsLessThan>` comparison operator. - * - * @constructor - * @param {!string} propertyName Name of the context property to compare. - * @param {!number} expression The value to compare. - * @extends {ol.format.filter.ComparisonBinary} - * @api - */ -ol.format.filter.LessThan = function(propertyName, expression) { - ol.format.filter.ComparisonBinary.call(this, 'PropertyIsLessThan', propertyName, expression); -}; -ol.inherits(ol.format.filter.LessThan, ol.format.filter.ComparisonBinary); - -goog.provide('ol.format.filter.LessThanOrEqualTo'); - -goog.require('ol'); -goog.require('ol.format.filter.ComparisonBinary'); - - -/** - * @classdesc - * Represents a `<PropertyIsLessThanOrEqualTo>` comparison operator. - * - * @constructor - * @param {!string} propertyName Name of the context property to compare. - * @param {!number} expression The value to compare. - * @extends {ol.format.filter.ComparisonBinary} - * @api - */ -ol.format.filter.LessThanOrEqualTo = function(propertyName, expression) { - ol.format.filter.ComparisonBinary.call(this, 'PropertyIsLessThanOrEqualTo', propertyName, expression); -}; -ol.inherits(ol.format.filter.LessThanOrEqualTo, ol.format.filter.ComparisonBinary); - -goog.provide('ol.format.filter.Not'); - -goog.require('ol'); -goog.require('ol.format.filter.Filter'); - - -/** - * @classdesc - * Represents a logical `<Not>` operator for a filter condition. - * - * @constructor - * @param {!ol.format.filter.Filter} condition Filter condition. - * @extends {ol.format.filter.Filter} - * @api - */ -ol.format.filter.Not = function(condition) { - - ol.format.filter.Filter.call(this, 'Not'); - - /** - * @public - * @type {!ol.format.filter.Filter} - */ - this.condition = condition; -}; -ol.inherits(ol.format.filter.Not, ol.format.filter.Filter); - -goog.provide('ol.format.filter.NotEqualTo'); - -goog.require('ol'); -goog.require('ol.format.filter.ComparisonBinary'); - - -/** - * @classdesc - * Represents a `<PropertyIsNotEqualTo>` comparison operator. - * - * @constructor - * @param {!string} propertyName Name of the context property to compare. - * @param {!(string|number)} expression The value to compare. - * @param {boolean=} opt_matchCase Case-sensitive? - * @extends {ol.format.filter.ComparisonBinary} - * @api - */ -ol.format.filter.NotEqualTo = function(propertyName, expression, opt_matchCase) { - ol.format.filter.ComparisonBinary.call(this, 'PropertyIsNotEqualTo', propertyName, expression, opt_matchCase); -}; -ol.inherits(ol.format.filter.NotEqualTo, ol.format.filter.ComparisonBinary); - -goog.provide('ol.format.filter.Or'); - -goog.require('ol'); -goog.require('ol.format.filter.LogicalNary'); - - -/** - * @classdesc - * Represents a logical `<Or>` operator between two ore more filter conditions. - * - * @constructor - * @param {...ol.format.filter.Filter} conditions Conditions. - * @extends {ol.format.filter.LogicalNary} - * @api - */ -ol.format.filter.Or = function(conditions) { - var params = ['Or'].concat(Array.prototype.slice.call(arguments)); - ol.format.filter.LogicalNary.apply(this, params); -}; -ol.inherits(ol.format.filter.Or, ol.format.filter.LogicalNary); - -goog.provide('ol.format.filter.Within'); - -goog.require('ol'); -goog.require('ol.format.filter.Spatial'); - - -/** - * @classdesc - * Represents a `<Within>` operator to test whether a geometry-valued property - * is within a given geometry. - * - * @constructor - * @param {!string} geometryName Geometry name to use. - * @param {!ol.geom.Geometry} geometry Geometry. - * @param {string=} opt_srsName SRS name. No srsName attribute will be - * set on geometries when this is not provided. - * @extends {ol.format.filter.Spatial} - * @api - */ -ol.format.filter.Within = function(geometryName, geometry, opt_srsName) { - - ol.format.filter.Spatial.call(this, 'Within', geometryName, geometry, opt_srsName); - -}; -ol.inherits(ol.format.filter.Within, ol.format.filter.Spatial); - -goog.provide('ol.format.filter'); - -goog.require('ol.format.filter.And'); -goog.require('ol.format.filter.Bbox'); -goog.require('ol.format.filter.During'); -goog.require('ol.format.filter.EqualTo'); -goog.require('ol.format.filter.GreaterThan'); -goog.require('ol.format.filter.GreaterThanOrEqualTo'); -goog.require('ol.format.filter.Intersects'); -goog.require('ol.format.filter.IsBetween'); -goog.require('ol.format.filter.IsLike'); -goog.require('ol.format.filter.IsNull'); -goog.require('ol.format.filter.LessThan'); -goog.require('ol.format.filter.LessThanOrEqualTo'); -goog.require('ol.format.filter.Not'); -goog.require('ol.format.filter.NotEqualTo'); -goog.require('ol.format.filter.Or'); -goog.require('ol.format.filter.Within'); - - -/** - * Create a logical `<And>` operator between two or more filter conditions. - * - * @param {...ol.format.filter.Filter} conditions Filter conditions. - * @returns {!ol.format.filter.And} `<And>` operator. - * @api - */ -ol.format.filter.and = function(conditions) { - var params = [null].concat(Array.prototype.slice.call(arguments)); - return new (Function.prototype.bind.apply(ol.format.filter.And, params)); -}; - - -/** - * Create a logical `<Or>` operator between two or more filter conditions. - * - * @param {...ol.format.filter.Filter} conditions Filter conditions. - * @returns {!ol.format.filter.Or} `<Or>` operator. - * @api - */ -ol.format.filter.or = function(conditions) { - var params = [null].concat(Array.prototype.slice.call(arguments)); - return new (Function.prototype.bind.apply(ol.format.filter.Or, params)); -}; - - -/** - * Represents a logical `<Not>` operator for a filter condition. - * - * @param {!ol.format.filter.Filter} condition Filter condition. - * @returns {!ol.format.filter.Not} `<Not>` operator. - * @api - */ -ol.format.filter.not = function(condition) { - return new ol.format.filter.Not(condition); -}; - - -/** - * Create a `<BBOX>` operator to test whether a geometry-valued property - * intersects a fixed bounding box - * - * @param {!string} geometryName Geometry name to use. - * @param {!ol.Extent} extent Extent. - * @param {string=} opt_srsName SRS name. No srsName attribute will be - * set on geometries when this is not provided. - * @returns {!ol.format.filter.Bbox} `<BBOX>` operator. - * @api - */ -ol.format.filter.bbox = function(geometryName, extent, opt_srsName) { - return new ol.format.filter.Bbox(geometryName, extent, opt_srsName); -}; - -/** - * Create a `<Intersects>` operator to test whether a geometry-valued property - * intersects a given geometry. - * - * @param {!string} geometryName Geometry name to use. - * @param {!ol.geom.Geometry} geometry Geometry. - * @param {string=} opt_srsName SRS name. No srsName attribute will be - * set on geometries when this is not provided. - * @returns {!ol.format.filter.Intersects} `<Intersects>` operator. - * @api - */ -ol.format.filter.intersects = function(geometryName, geometry, opt_srsName) { - return new ol.format.filter.Intersects(geometryName, geometry, opt_srsName); -}; - -/** - * Create a `<Within>` operator to test whether a geometry-valued property - * is within a given geometry. - * - * @param {!string} geometryName Geometry name to use. - * @param {!ol.geom.Geometry} geometry Geometry. - * @param {string=} opt_srsName SRS name. No srsName attribute will be - * set on geometries when this is not provided. - * @returns {!ol.format.filter.Within} `<Within>` operator. - * @api - */ -ol.format.filter.within = function(geometryName, geometry, opt_srsName) { - return new ol.format.filter.Within(geometryName, geometry, opt_srsName); -}; - - -/** - * Creates a `<PropertyIsEqualTo>` comparison operator. - * - * @param {!string} propertyName Name of the context property to compare. - * @param {!(string|number)} expression The value to compare. - * @param {boolean=} opt_matchCase Case-sensitive? - * @returns {!ol.format.filter.EqualTo} `<PropertyIsEqualTo>` operator. - * @api - */ -ol.format.filter.equalTo = function(propertyName, expression, opt_matchCase) { - return new ol.format.filter.EqualTo(propertyName, expression, opt_matchCase); -}; - - -/** - * Creates a `<PropertyIsNotEqualTo>` comparison operator. - * - * @param {!string} propertyName Name of the context property to compare. - * @param {!(string|number)} expression The value to compare. - * @param {boolean=} opt_matchCase Case-sensitive? - * @returns {!ol.format.filter.NotEqualTo} `<PropertyIsNotEqualTo>` operator. - * @api - */ -ol.format.filter.notEqualTo = function(propertyName, expression, opt_matchCase) { - return new ol.format.filter.NotEqualTo(propertyName, expression, opt_matchCase); -}; - - -/** - * Creates a `<PropertyIsLessThan>` comparison operator. - * - * @param {!string} propertyName Name of the context property to compare. - * @param {!number} expression The value to compare. - * @returns {!ol.format.filter.LessThan} `<PropertyIsLessThan>` operator. - * @api - */ -ol.format.filter.lessThan = function(propertyName, expression) { - return new ol.format.filter.LessThan(propertyName, expression); -}; - - -/** - * Creates a `<PropertyIsLessThanOrEqualTo>` comparison operator. - * - * @param {!string} propertyName Name of the context property to compare. - * @param {!number} expression The value to compare. - * @returns {!ol.format.filter.LessThanOrEqualTo} `<PropertyIsLessThanOrEqualTo>` operator. - * @api - */ -ol.format.filter.lessThanOrEqualTo = function(propertyName, expression) { - return new ol.format.filter.LessThanOrEqualTo(propertyName, expression); -}; - - -/** - * Creates a `<PropertyIsGreaterThan>` comparison operator. - * - * @param {!string} propertyName Name of the context property to compare. - * @param {!number} expression The value to compare. - * @returns {!ol.format.filter.GreaterThan} `<PropertyIsGreaterThan>` operator. - * @api - */ -ol.format.filter.greaterThan = function(propertyName, expression) { - return new ol.format.filter.GreaterThan(propertyName, expression); -}; - - -/** - * Creates a `<PropertyIsGreaterThanOrEqualTo>` comparison operator. - * - * @param {!string} propertyName Name of the context property to compare. - * @param {!number} expression The value to compare. - * @returns {!ol.format.filter.GreaterThanOrEqualTo} `<PropertyIsGreaterThanOrEqualTo>` operator. - * @api - */ -ol.format.filter.greaterThanOrEqualTo = function(propertyName, expression) { - return new ol.format.filter.GreaterThanOrEqualTo(propertyName, expression); -}; - - -/** - * Creates a `<PropertyIsNull>` comparison operator to test whether a property value - * is null. - * - * @param {!string} propertyName Name of the context property to compare. - * @returns {!ol.format.filter.IsNull} `<PropertyIsNull>` operator. - * @api - */ -ol.format.filter.isNull = function(propertyName) { - return new ol.format.filter.IsNull(propertyName); -}; - - -/** - * Creates a `<PropertyIsBetween>` comparison operator to test whether an expression - * value lies within a range given by a lower and upper bound (inclusive). - * - * @param {!string} propertyName Name of the context property to compare. - * @param {!number} lowerBoundary The lower bound of the range. - * @param {!number} upperBoundary The upper bound of the range. - * @returns {!ol.format.filter.IsBetween} `<PropertyIsBetween>` operator. - * @api - */ -ol.format.filter.between = function(propertyName, lowerBoundary, upperBoundary) { - return new ol.format.filter.IsBetween(propertyName, lowerBoundary, upperBoundary); -}; - - -/** - * Represents a `<PropertyIsLike>` comparison operator that matches a string property - * value against a text pattern. - * - * @param {!string} propertyName Name of the context property to compare. - * @param {!string} pattern Text pattern. - * @param {string=} opt_wildCard Pattern character which matches any sequence of - * zero or more string characters. Default is '*'. - * @param {string=} opt_singleChar pattern character which matches any single - * string character. Default is '.'. - * @param {string=} opt_escapeChar Escape character which can be used to escape - * the pattern characters. Default is '!'. - * @param {boolean=} opt_matchCase Case-sensitive? - * @returns {!ol.format.filter.IsLike} `<PropertyIsLike>` operator. - * @api - */ -ol.format.filter.like = function(propertyName, pattern, - opt_wildCard, opt_singleChar, opt_escapeChar, opt_matchCase) { - return new ol.format.filter.IsLike(propertyName, pattern, - opt_wildCard, opt_singleChar, opt_escapeChar, opt_matchCase); -}; - - -/** - * Create a `<During>` temporal operator. - * - * @param {!string} propertyName Name of the context property to compare. - * @param {!string} begin The begin date in ISO-8601 format. - * @param {!string} end The end date in ISO-8601 format. - * @returns {!ol.format.filter.During} `<During>` operator. - * @api - */ -ol.format.filter.during = function(propertyName, begin, end) { - return new ol.format.filter.During(propertyName, begin, end); -}; - -goog.provide('ol.geom.GeometryCollection'); - -goog.require('ol'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.extent'); -goog.require('ol.geom.Geometry'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.obj'); - - -/** - * @classdesc - * An array of {@link ol.geom.Geometry} objects. - * - * @constructor - * @extends {ol.geom.Geometry} - * @param {Array.<ol.geom.Geometry>=} opt_geometries Geometries. - * @api - */ -ol.geom.GeometryCollection = function(opt_geometries) { - - ol.geom.Geometry.call(this); - - /** - * @private - * @type {Array.<ol.geom.Geometry>} - */ - this.geometries_ = opt_geometries ? opt_geometries : null; - - this.listenGeometriesChange_(); -}; -ol.inherits(ol.geom.GeometryCollection, ol.geom.Geometry); - - -/** - * @param {Array.<ol.geom.Geometry>} geometries Geometries. - * @private - * @return {Array.<ol.geom.Geometry>} Cloned geometries. - */ -ol.geom.GeometryCollection.cloneGeometries_ = function(geometries) { - var clonedGeometries = []; - var i, ii; - for (i = 0, ii = geometries.length; i < ii; ++i) { - clonedGeometries.push(geometries[i].clone()); - } - return clonedGeometries; -}; - - -/** - * @private - */ -ol.geom.GeometryCollection.prototype.unlistenGeometriesChange_ = function() { - var i, ii; - if (!this.geometries_) { - return; - } - for (i = 0, ii = this.geometries_.length; i < ii; ++i) { - ol.events.unlisten( - this.geometries_[i], ol.events.EventType.CHANGE, - this.changed, this); - } -}; - - -/** - * @private - */ -ol.geom.GeometryCollection.prototype.listenGeometriesChange_ = function() { - var i, ii; - if (!this.geometries_) { - return; - } - for (i = 0, ii = this.geometries_.length; i < ii; ++i) { - ol.events.listen( - this.geometries_[i], ol.events.EventType.CHANGE, - this.changed, this); - } -}; - - -/** - * Make a complete copy of the geometry. - * @return {!ol.geom.GeometryCollection} Clone. - * @override - * @api - */ -ol.geom.GeometryCollection.prototype.clone = function() { - var geometryCollection = new ol.geom.GeometryCollection(null); - geometryCollection.setGeometries(this.geometries_); - return geometryCollection; -}; - - -/** - * @inheritDoc - */ -ol.geom.GeometryCollection.prototype.closestPointXY = function(x, y, closestPoint, minSquaredDistance) { - if (minSquaredDistance < - ol.extent.closestSquaredDistanceXY(this.getExtent(), x, y)) { - return minSquaredDistance; - } - var geometries = this.geometries_; - var i, ii; - for (i = 0, ii = geometries.length; i < ii; ++i) { - minSquaredDistance = geometries[i].closestPointXY( - x, y, closestPoint, minSquaredDistance); - } - return minSquaredDistance; -}; - - -/** - * @inheritDoc - */ -ol.geom.GeometryCollection.prototype.containsXY = function(x, y) { - var geometries = this.geometries_; - var i, ii; - for (i = 0, ii = geometries.length; i < ii; ++i) { - if (geometries[i].containsXY(x, y)) { - return true; - } - } - return false; -}; - - -/** - * @inheritDoc - */ -ol.geom.GeometryCollection.prototype.computeExtent = function(extent) { - ol.extent.createOrUpdateEmpty(extent); - var geometries = this.geometries_; - for (var i = 0, ii = geometries.length; i < ii; ++i) { - ol.extent.extend(extent, geometries[i].getExtent()); - } - return extent; -}; - - -/** - * Return the geometries that make up this geometry collection. - * @return {Array.<ol.geom.Geometry>} Geometries. - * @api - */ -ol.geom.GeometryCollection.prototype.getGeometries = function() { - return ol.geom.GeometryCollection.cloneGeometries_(this.geometries_); -}; - - -/** - * @return {Array.<ol.geom.Geometry>} Geometries. - */ -ol.geom.GeometryCollection.prototype.getGeometriesArray = function() { - return this.geometries_; -}; - - -/** - * @inheritDoc - */ -ol.geom.GeometryCollection.prototype.getSimplifiedGeometry = function(squaredTolerance) { - if (this.simplifiedGeometryRevision != this.getRevision()) { - ol.obj.clear(this.simplifiedGeometryCache); - this.simplifiedGeometryMaxMinSquaredTolerance = 0; - this.simplifiedGeometryRevision = this.getRevision(); - } - if (squaredTolerance < 0 || - (this.simplifiedGeometryMaxMinSquaredTolerance !== 0 && - squaredTolerance < this.simplifiedGeometryMaxMinSquaredTolerance)) { - return this; - } - var key = squaredTolerance.toString(); - if (this.simplifiedGeometryCache.hasOwnProperty(key)) { - return this.simplifiedGeometryCache[key]; - } else { - var simplifiedGeometries = []; - var geometries = this.geometries_; - var simplified = false; - var i, ii; - for (i = 0, ii = geometries.length; i < ii; ++i) { - var geometry = geometries[i]; - var simplifiedGeometry = geometry.getSimplifiedGeometry(squaredTolerance); - simplifiedGeometries.push(simplifiedGeometry); - if (simplifiedGeometry !== geometry) { - simplified = true; - } - } - if (simplified) { - var simplifiedGeometryCollection = new ol.geom.GeometryCollection(null); - simplifiedGeometryCollection.setGeometriesArray(simplifiedGeometries); - this.simplifiedGeometryCache[key] = simplifiedGeometryCollection; - return simplifiedGeometryCollection; - } else { - this.simplifiedGeometryMaxMinSquaredTolerance = squaredTolerance; - return this; - } - } -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.GeometryCollection.prototype.getType = function() { - return ol.geom.GeometryType.GEOMETRY_COLLECTION; -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.GeometryCollection.prototype.intersectsExtent = function(extent) { - var geometries = this.geometries_; - var i, ii; - for (i = 0, ii = geometries.length; i < ii; ++i) { - if (geometries[i].intersectsExtent(extent)) { - return true; - } - } - return false; -}; - - -/** - * @return {boolean} Is empty. - */ -ol.geom.GeometryCollection.prototype.isEmpty = function() { - return this.geometries_.length === 0; -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.GeometryCollection.prototype.rotate = function(angle, anchor) { - var geometries = this.geometries_; - for (var i = 0, ii = geometries.length; i < ii; ++i) { - geometries[i].rotate(angle, anchor); - } - this.changed(); -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.GeometryCollection.prototype.scale = function(sx, opt_sy, opt_anchor) { - var anchor = opt_anchor; - if (!anchor) { - anchor = ol.extent.getCenter(this.getExtent()); - } - var geometries = this.geometries_; - for (var i = 0, ii = geometries.length; i < ii; ++i) { - geometries[i].scale(sx, opt_sy, anchor); - } - this.changed(); -}; - - -/** - * Set the geometries that make up this geometry collection. - * @param {Array.<ol.geom.Geometry>} geometries Geometries. - * @api - */ -ol.geom.GeometryCollection.prototype.setGeometries = function(geometries) { - this.setGeometriesArray( - ol.geom.GeometryCollection.cloneGeometries_(geometries)); -}; - - -/** - * @param {Array.<ol.geom.Geometry>} geometries Geometries. - */ -ol.geom.GeometryCollection.prototype.setGeometriesArray = function(geometries) { - this.unlistenGeometriesChange_(); - this.geometries_ = geometries; - this.listenGeometriesChange_(); - this.changed(); -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.GeometryCollection.prototype.applyTransform = function(transformFn) { - var geometries = this.geometries_; - var i, ii; - for (i = 0, ii = geometries.length; i < ii; ++i) { - geometries[i].applyTransform(transformFn); - } - this.changed(); -}; - - -/** - * Translate the geometry. - * @param {number} deltaX Delta X. - * @param {number} deltaY Delta Y. - * @override - * @api - */ -ol.geom.GeometryCollection.prototype.translate = function(deltaX, deltaY) { - var geometries = this.geometries_; - var i, ii; - for (i = 0, ii = geometries.length; i < ii; ++i) { - geometries[i].translate(deltaX, deltaY); - } - this.changed(); -}; - - -/** - * @inheritDoc - */ -ol.geom.GeometryCollection.prototype.disposeInternal = function() { - this.unlistenGeometriesChange_(); - ol.geom.Geometry.prototype.disposeInternal.call(this); -}; - -// TODO: serialize dataProjection as crs member when writing -// see https://github.com/openlayers/openlayers/issues/2078 - -goog.provide('ol.format.GeoJSON'); - -goog.require('ol'); -goog.require('ol.asserts'); -goog.require('ol.Feature'); -goog.require('ol.format.Feature'); -goog.require('ol.format.JSONFeature'); -goog.require('ol.geom.GeometryCollection'); -goog.require('ol.geom.LineString'); -goog.require('ol.geom.MultiLineString'); -goog.require('ol.geom.MultiPoint'); -goog.require('ol.geom.MultiPolygon'); -goog.require('ol.geom.Point'); -goog.require('ol.geom.Polygon'); -goog.require('ol.obj'); -goog.require('ol.proj'); - - -/** - * @classdesc - * Feature format for reading and writing data in the GeoJSON format. - * - * @constructor - * @extends {ol.format.JSONFeature} - * @param {olx.format.GeoJSONOptions=} opt_options Options. - * @api - */ -ol.format.GeoJSON = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - ol.format.JSONFeature.call(this); - - /** - * @inheritDoc - */ - this.defaultDataProjection = ol.proj.get( - options.defaultDataProjection ? - options.defaultDataProjection : 'EPSG:4326'); - - - if (options.featureProjection) { - this.defaultFeatureProjection = ol.proj.get(options.featureProjection); - } - - /** - * Name of the geometry attribute for features. - * @type {string|undefined} - * @private - */ - this.geometryName_ = options.geometryName; - -}; -ol.inherits(ol.format.GeoJSON, ol.format.JSONFeature); - - -/** - * @param {GeoJSONGeometry|GeoJSONGeometryCollection} object Object. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @private - * @return {ol.geom.Geometry} Geometry. - */ -ol.format.GeoJSON.readGeometry_ = function(object, opt_options) { - if (!object) { - return null; - } - var geometryReader = ol.format.GeoJSON.GEOMETRY_READERS_[object.type]; - return /** @type {ol.geom.Geometry} */ ( - ol.format.Feature.transformWithOptions( - geometryReader(object), false, opt_options)); -}; - - -/** - * @param {GeoJSONGeometryCollection} object Object. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @private - * @return {ol.geom.GeometryCollection} Geometry collection. - */ -ol.format.GeoJSON.readGeometryCollectionGeometry_ = function( - object, opt_options) { - var geometries = object.geometries.map( - /** - * @param {GeoJSONGeometry} geometry Geometry. - * @return {ol.geom.Geometry} geometry Geometry. - */ - function(geometry) { - return ol.format.GeoJSON.readGeometry_(geometry, opt_options); - }); - return new ol.geom.GeometryCollection(geometries); -}; - - -/** - * @param {GeoJSONGeometry} object Object. - * @private - * @return {ol.geom.Point} Point. - */ -ol.format.GeoJSON.readPointGeometry_ = function(object) { - return new ol.geom.Point(object.coordinates); -}; - - -/** - * @param {GeoJSONGeometry} object Object. - * @private - * @return {ol.geom.LineString} LineString. - */ -ol.format.GeoJSON.readLineStringGeometry_ = function(object) { - return new ol.geom.LineString(object.coordinates); -}; - - -/** - * @param {GeoJSONGeometry} object Object. - * @private - * @return {ol.geom.MultiLineString} MultiLineString. - */ -ol.format.GeoJSON.readMultiLineStringGeometry_ = function(object) { - return new ol.geom.MultiLineString(object.coordinates); -}; - - -/** - * @param {GeoJSONGeometry} object Object. - * @private - * @return {ol.geom.MultiPoint} MultiPoint. - */ -ol.format.GeoJSON.readMultiPointGeometry_ = function(object) { - return new ol.geom.MultiPoint(object.coordinates); -}; - - -/** - * @param {GeoJSONGeometry} object Object. - * @private - * @return {ol.geom.MultiPolygon} MultiPolygon. - */ -ol.format.GeoJSON.readMultiPolygonGeometry_ = function(object) { - return new ol.geom.MultiPolygon(object.coordinates); -}; - - -/** - * @param {GeoJSONGeometry} object Object. - * @private - * @return {ol.geom.Polygon} Polygon. - */ -ol.format.GeoJSON.readPolygonGeometry_ = function(object) { - return new ol.geom.Polygon(object.coordinates); -}; - - -/** - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @private - * @return {GeoJSONGeometry|GeoJSONGeometryCollection} GeoJSON geometry. - */ -ol.format.GeoJSON.writeGeometry_ = function(geometry, opt_options) { - var geometryWriter = ol.format.GeoJSON.GEOMETRY_WRITERS_[geometry.getType()]; - return geometryWriter(/** @type {ol.geom.Geometry} */ ( - ol.format.Feature.transformWithOptions(geometry, true, opt_options)), - opt_options); -}; - - -/** - * @param {ol.geom.Geometry} geometry Geometry. - * @private - * @return {GeoJSONGeometryCollection} Empty GeoJSON geometry collection. - */ -ol.format.GeoJSON.writeEmptyGeometryCollectionGeometry_ = function(geometry) { - return /** @type {GeoJSONGeometryCollection} */ ({ - type: 'GeometryCollection', - geometries: [] - }); -}; - - -/** - * @param {ol.geom.GeometryCollection} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @private - * @return {GeoJSONGeometryCollection} GeoJSON geometry collection. - */ -ol.format.GeoJSON.writeGeometryCollectionGeometry_ = function( - geometry, opt_options) { - var geometries = geometry.getGeometriesArray().map(function(geometry) { - var options = ol.obj.assign({}, opt_options); - delete options.featureProjection; - return ol.format.GeoJSON.writeGeometry_(geometry, options); - }); - return /** @type {GeoJSONGeometryCollection} */ ({ - type: 'GeometryCollection', - geometries: geometries - }); -}; - - -/** - * @param {ol.geom.LineString} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @private - * @return {GeoJSONGeometry} GeoJSON geometry. - */ -ol.format.GeoJSON.writeLineStringGeometry_ = function(geometry, opt_options) { - return /** @type {GeoJSONGeometry} */ ({ - type: 'LineString', - coordinates: geometry.getCoordinates() - }); -}; - - -/** - * @param {ol.geom.MultiLineString} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @private - * @return {GeoJSONGeometry} GeoJSON geometry. - */ -ol.format.GeoJSON.writeMultiLineStringGeometry_ = function(geometry, opt_options) { - return /** @type {GeoJSONGeometry} */ ({ - type: 'MultiLineString', - coordinates: geometry.getCoordinates() - }); -}; - - -/** - * @param {ol.geom.MultiPoint} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @private - * @return {GeoJSONGeometry} GeoJSON geometry. - */ -ol.format.GeoJSON.writeMultiPointGeometry_ = function(geometry, opt_options) { - return /** @type {GeoJSONGeometry} */ ({ - type: 'MultiPoint', - coordinates: geometry.getCoordinates() - }); -}; - - -/** - * @param {ol.geom.MultiPolygon} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @private - * @return {GeoJSONGeometry} GeoJSON geometry. - */ -ol.format.GeoJSON.writeMultiPolygonGeometry_ = function(geometry, opt_options) { - var right; - if (opt_options) { - right = opt_options.rightHanded; - } - return /** @type {GeoJSONGeometry} */ ({ - type: 'MultiPolygon', - coordinates: geometry.getCoordinates(right) - }); -}; - - -/** - * @param {ol.geom.Point} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @private - * @return {GeoJSONGeometry} GeoJSON geometry. - */ -ol.format.GeoJSON.writePointGeometry_ = function(geometry, opt_options) { - return /** @type {GeoJSONGeometry} */ ({ - type: 'Point', - coordinates: geometry.getCoordinates() - }); -}; - - -/** - * @param {ol.geom.Polygon} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @private - * @return {GeoJSONGeometry} GeoJSON geometry. - */ -ol.format.GeoJSON.writePolygonGeometry_ = function(geometry, opt_options) { - var right; - if (opt_options) { - right = opt_options.rightHanded; - } - return /** @type {GeoJSONGeometry} */ ({ - type: 'Polygon', - coordinates: geometry.getCoordinates(right) - }); -}; - - -/** - * @const - * @private - * @type {Object.<string, function(GeoJSONObject): ol.geom.Geometry>} - */ -ol.format.GeoJSON.GEOMETRY_READERS_ = { - 'Point': ol.format.GeoJSON.readPointGeometry_, - 'LineString': ol.format.GeoJSON.readLineStringGeometry_, - 'Polygon': ol.format.GeoJSON.readPolygonGeometry_, - 'MultiPoint': ol.format.GeoJSON.readMultiPointGeometry_, - 'MultiLineString': ol.format.GeoJSON.readMultiLineStringGeometry_, - 'MultiPolygon': ol.format.GeoJSON.readMultiPolygonGeometry_, - 'GeometryCollection': ol.format.GeoJSON.readGeometryCollectionGeometry_ -}; - - -/** - * @const - * @private - * @type {Object.<string, function(ol.geom.Geometry, olx.format.WriteOptions=): (GeoJSONGeometry|GeoJSONGeometryCollection)>} - */ -ol.format.GeoJSON.GEOMETRY_WRITERS_ = { - 'Point': ol.format.GeoJSON.writePointGeometry_, - 'LineString': ol.format.GeoJSON.writeLineStringGeometry_, - 'Polygon': ol.format.GeoJSON.writePolygonGeometry_, - 'MultiPoint': ol.format.GeoJSON.writeMultiPointGeometry_, - 'MultiLineString': ol.format.GeoJSON.writeMultiLineStringGeometry_, - 'MultiPolygon': ol.format.GeoJSON.writeMultiPolygonGeometry_, - 'GeometryCollection': ol.format.GeoJSON.writeGeometryCollectionGeometry_, - 'Circle': ol.format.GeoJSON.writeEmptyGeometryCollectionGeometry_ -}; - - -/** - * Read a feature from a GeoJSON Feature source. Only works for Feature or - * geometry types. Use {@link ol.format.GeoJSON#readFeatures} to read - * FeatureCollection source. If feature at source has an id, it will be used - * as Feature id by calling {@link ol.Feature#setId} internally. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {ol.Feature} Feature. - * @api - */ -ol.format.GeoJSON.prototype.readFeature; - - -/** - * Read all features from a GeoJSON source. Works for all GeoJSON types. - * If the source includes only geometries, features will be created with those - * geometries. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {Array.<ol.Feature>} Features. - * @api - */ -ol.format.GeoJSON.prototype.readFeatures; - - -/** - * @inheritDoc - */ -ol.format.GeoJSON.prototype.readFeatureFromObject = function( - object, opt_options) { - /** - * @type {GeoJSONFeature} - */ - var geoJSONFeature = null; - if (object.type === 'Feature') { - geoJSONFeature = /** @type {GeoJSONFeature} */ (object); - } else { - geoJSONFeature = /** @type {GeoJSONFeature} */ ({ - type: 'Feature', - geometry: /** @type {GeoJSONGeometry|GeoJSONGeometryCollection} */ (object) - }); - } - - var geometry = ol.format.GeoJSON.readGeometry_(geoJSONFeature.geometry, opt_options); - var feature = new ol.Feature(); - if (this.geometryName_) { - feature.setGeometryName(this.geometryName_); - } - feature.setGeometry(geometry); - if (geoJSONFeature.id !== undefined) { - feature.setId(geoJSONFeature.id); - } - if (geoJSONFeature.properties) { - feature.setProperties(geoJSONFeature.properties); - } - return feature; -}; - - -/** - * @inheritDoc - */ -ol.format.GeoJSON.prototype.readFeaturesFromObject = function( - object, opt_options) { - var geoJSONObject = /** @type {GeoJSONObject} */ (object); - /** @type {Array.<ol.Feature>} */ - var features = null; - if (geoJSONObject.type === 'FeatureCollection') { - var geoJSONFeatureCollection = /** @type {GeoJSONFeatureCollection} */ - (object); - features = []; - var geoJSONFeatures = geoJSONFeatureCollection.features; - var i, ii; - for (i = 0, ii = geoJSONFeatures.length; i < ii; ++i) { - features.push(this.readFeatureFromObject(geoJSONFeatures[i], - opt_options)); - } - } else { - features = [this.readFeatureFromObject(object, opt_options)]; - } - return features; -}; - - -/** - * Read a geometry from a GeoJSON source. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {ol.geom.Geometry} Geometry. - * @api - */ -ol.format.GeoJSON.prototype.readGeometry; - - -/** - * @inheritDoc - */ -ol.format.GeoJSON.prototype.readGeometryFromObject = function( - object, opt_options) { - return ol.format.GeoJSON.readGeometry_( - /** @type {GeoJSONGeometry} */ (object), opt_options); -}; - - -/** - * Read the projection from a GeoJSON source. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @return {ol.proj.Projection} Projection. - * @api - */ -ol.format.GeoJSON.prototype.readProjection; - - -/** - * @inheritDoc - */ -ol.format.GeoJSON.prototype.readProjectionFromObject = function(object) { - var geoJSONObject = /** @type {GeoJSONObject} */ (object); - var crs = geoJSONObject.crs; - var projection; - if (crs) { - if (crs.type == 'name') { - projection = ol.proj.get(crs.properties.name); - } else if (crs.type == 'EPSG') { - // 'EPSG' is not part of the GeoJSON specification, but is generated by - // GeoServer. - // TODO: remove this when http://jira.codehaus.org/browse/GEOS-5996 - // is fixed and widely deployed. - projection = ol.proj.get('EPSG:' + crs.properties.code); - } else { - ol.asserts.assert(false, 36); // Unknown SRS type - } - } else { - projection = this.defaultDataProjection; - } - return /** @type {ol.proj.Projection} */ (projection); -}; - - -/** - * Encode a feature as a GeoJSON Feature string. - * - * @function - * @param {ol.Feature} feature Feature. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {string} GeoJSON. - * @override - * @api - */ -ol.format.GeoJSON.prototype.writeFeature; - - -/** - * Encode a feature as a GeoJSON Feature object. - * - * @param {ol.Feature} feature Feature. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {GeoJSONFeature} Object. - * @override - * @api - */ -ol.format.GeoJSON.prototype.writeFeatureObject = function(feature, opt_options) { - opt_options = this.adaptOptions(opt_options); - - var object = /** @type {GeoJSONFeature} */ ({ - 'type': 'Feature' - }); - var id = feature.getId(); - if (id !== undefined) { - object.id = id; - } - var geometry = feature.getGeometry(); - if (geometry) { - object.geometry = - ol.format.GeoJSON.writeGeometry_(geometry, opt_options); - } else { - object.geometry = null; - } - var properties = feature.getProperties(); - delete properties[feature.getGeometryName()]; - if (!ol.obj.isEmpty(properties)) { - object.properties = properties; - } else { - object.properties = null; - } - return object; -}; - - -/** - * Encode an array of features as GeoJSON. - * - * @function - * @param {Array.<ol.Feature>} features Features. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {string} GeoJSON. - * @api - */ -ol.format.GeoJSON.prototype.writeFeatures; - - -/** - * Encode an array of features as a GeoJSON object. - * - * @param {Array.<ol.Feature>} features Features. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {GeoJSONFeatureCollection} GeoJSON Object. - * @override - * @api - */ -ol.format.GeoJSON.prototype.writeFeaturesObject = function(features, opt_options) { - opt_options = this.adaptOptions(opt_options); - var objects = []; - var i, ii; - for (i = 0, ii = features.length; i < ii; ++i) { - objects.push(this.writeFeatureObject(features[i], opt_options)); - } - return /** @type {GeoJSONFeatureCollection} */ ({ - type: 'FeatureCollection', - features: objects - }); -}; - - -/** - * Encode a geometry as a GeoJSON string. - * - * @function - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {string} GeoJSON. - * @api - */ -ol.format.GeoJSON.prototype.writeGeometry; - - -/** - * Encode a geometry as a GeoJSON object. - * - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {GeoJSONGeometry|GeoJSONGeometryCollection} Object. - * @override - * @api - */ -ol.format.GeoJSON.prototype.writeGeometryObject = function(geometry, - opt_options) { - return ol.format.GeoJSON.writeGeometry_(geometry, - this.adaptOptions(opt_options)); -}; - -goog.provide('ol.format.XMLFeature'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.format.Feature'); -goog.require('ol.format.FormatType'); -goog.require('ol.xml'); - - -/** - * @classdesc - * Abstract base class; normally only used for creating subclasses and not - * instantiated in apps. - * Base class for XML feature formats. - * - * @constructor - * @abstract - * @extends {ol.format.Feature} - */ -ol.format.XMLFeature = function() { - - /** - * @type {XMLSerializer} - * @private - */ - this.xmlSerializer_ = new XMLSerializer(); - - ol.format.Feature.call(this); -}; -ol.inherits(ol.format.XMLFeature, ol.format.Feature); - - -/** - * @inheritDoc - */ -ol.format.XMLFeature.prototype.getType = function() { - return ol.format.FormatType.XML; -}; - - -/** - * @inheritDoc - */ -ol.format.XMLFeature.prototype.readFeature = function(source, opt_options) { - if (ol.xml.isDocument(source)) { - return this.readFeatureFromDocument( - /** @type {Document} */ (source), opt_options); - } else if (ol.xml.isNode(source)) { - return this.readFeatureFromNode(/** @type {Node} */ (source), opt_options); - } else if (typeof source === 'string') { - var doc = ol.xml.parse(source); - return this.readFeatureFromDocument(doc, opt_options); - } else { - return null; - } -}; - - -/** - * @param {Document} doc Document. - * @param {olx.format.ReadOptions=} opt_options Options. - * @return {ol.Feature} Feature. - */ -ol.format.XMLFeature.prototype.readFeatureFromDocument = function( - doc, opt_options) { - var features = this.readFeaturesFromDocument(doc, opt_options); - if (features.length > 0) { - return features[0]; - } else { - return null; - } -}; - - -/** - * @param {Node} node Node. - * @param {olx.format.ReadOptions=} opt_options Options. - * @return {ol.Feature} Feature. - */ -ol.format.XMLFeature.prototype.readFeatureFromNode = function(node, opt_options) { - return null; // not implemented -}; - - -/** - * @inheritDoc - */ -ol.format.XMLFeature.prototype.readFeatures = function(source, opt_options) { - if (ol.xml.isDocument(source)) { - return this.readFeaturesFromDocument( - /** @type {Document} */ (source), opt_options); - } else if (ol.xml.isNode(source)) { - return this.readFeaturesFromNode(/** @type {Node} */ (source), opt_options); - } else if (typeof source === 'string') { - var doc = ol.xml.parse(source); - return this.readFeaturesFromDocument(doc, opt_options); - } else { - return []; - } -}; - - -/** - * @param {Document} doc Document. - * @param {olx.format.ReadOptions=} opt_options Options. - * @protected - * @return {Array.<ol.Feature>} Features. - */ -ol.format.XMLFeature.prototype.readFeaturesFromDocument = function( - doc, opt_options) { - /** @type {Array.<ol.Feature>} */ - var features = []; - var n; - for (n = doc.firstChild; n; n = n.nextSibling) { - if (n.nodeType == Node.ELEMENT_NODE) { - ol.array.extend(features, this.readFeaturesFromNode(n, opt_options)); - } - } - return features; -}; - - -/** - * @abstract - * @param {Node} node Node. - * @param {olx.format.ReadOptions=} opt_options Options. - * @protected - * @return {Array.<ol.Feature>} Features. - */ -ol.format.XMLFeature.prototype.readFeaturesFromNode = function(node, opt_options) {}; - - -/** - * @inheritDoc - */ -ol.format.XMLFeature.prototype.readGeometry = function(source, opt_options) { - if (ol.xml.isDocument(source)) { - return this.readGeometryFromDocument( - /** @type {Document} */ (source), opt_options); - } else if (ol.xml.isNode(source)) { - return this.readGeometryFromNode(/** @type {Node} */ (source), opt_options); - } else if (typeof source === 'string') { - var doc = ol.xml.parse(source); - return this.readGeometryFromDocument(doc, opt_options); - } else { - return null; - } -}; - - -/** - * @param {Document} doc Document. - * @param {olx.format.ReadOptions=} opt_options Options. - * @protected - * @return {ol.geom.Geometry} Geometry. - */ -ol.format.XMLFeature.prototype.readGeometryFromDocument = function(doc, opt_options) { - return null; // not implemented -}; - - -/** - * @param {Node} node Node. - * @param {olx.format.ReadOptions=} opt_options Options. - * @protected - * @return {ol.geom.Geometry} Geometry. - */ -ol.format.XMLFeature.prototype.readGeometryFromNode = function(node, opt_options) { - return null; // not implemented -}; - - -/** - * @inheritDoc - */ -ol.format.XMLFeature.prototype.readProjection = function(source) { - if (ol.xml.isDocument(source)) { - return this.readProjectionFromDocument(/** @type {Document} */ (source)); - } else if (ol.xml.isNode(source)) { - return this.readProjectionFromNode(/** @type {Node} */ (source)); - } else if (typeof source === 'string') { - var doc = ol.xml.parse(source); - return this.readProjectionFromDocument(doc); - } else { - return null; - } -}; - - -/** - * @param {Document} doc Document. - * @protected - * @return {ol.proj.Projection} Projection. - */ -ol.format.XMLFeature.prototype.readProjectionFromDocument = function(doc) { - return this.defaultDataProjection; -}; - - -/** - * @param {Node} node Node. - * @protected - * @return {ol.proj.Projection} Projection. - */ -ol.format.XMLFeature.prototype.readProjectionFromNode = function(node) { - return this.defaultDataProjection; -}; - - -/** - * @inheritDoc - */ -ol.format.XMLFeature.prototype.writeFeature = function(feature, opt_options) { - var node = this.writeFeatureNode(feature, opt_options); - return this.xmlSerializer_.serializeToString(node); -}; - - -/** - * @param {ol.Feature} feature Feature. - * @param {olx.format.WriteOptions=} opt_options Options. - * @protected - * @return {Node} Node. - */ -ol.format.XMLFeature.prototype.writeFeatureNode = function(feature, opt_options) { - return null; // not implemented -}; - - -/** - * @inheritDoc - */ -ol.format.XMLFeature.prototype.writeFeatures = function(features, opt_options) { - var node = this.writeFeaturesNode(features, opt_options); - return this.xmlSerializer_.serializeToString(node); -}; - - -/** - * @param {Array.<ol.Feature>} features Features. - * @param {olx.format.WriteOptions=} opt_options Options. - * @return {Node} Node. - */ -ol.format.XMLFeature.prototype.writeFeaturesNode = function(features, opt_options) { - return null; // not implemented -}; - - -/** - * @inheritDoc - */ -ol.format.XMLFeature.prototype.writeGeometry = function(geometry, opt_options) { - var node = this.writeGeometryNode(geometry, opt_options); - return this.xmlSerializer_.serializeToString(node); -}; - - -/** - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Options. - * @return {Node} Node. - */ -ol.format.XMLFeature.prototype.writeGeometryNode = function(geometry, opt_options) { - return null; // not implemented -}; - -// FIXME Envelopes should not be treated as geometries! readEnvelope_ is part -// of GEOMETRY_PARSERS_ and methods using GEOMETRY_PARSERS_ do not expect -// envelopes/extents, only geometries! -goog.provide('ol.format.GMLBase'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.Feature'); -goog.require('ol.format.Feature'); -goog.require('ol.format.XMLFeature'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.LineString'); -goog.require('ol.geom.LinearRing'); -goog.require('ol.geom.MultiLineString'); -goog.require('ol.geom.MultiPoint'); -goog.require('ol.geom.MultiPolygon'); -goog.require('ol.geom.Point'); -goog.require('ol.geom.Polygon'); -goog.require('ol.obj'); -goog.require('ol.proj'); -goog.require('ol.xml'); - - -/** - * @classdesc - * Abstract base class; normally only used for creating subclasses and not - * instantiated in apps. - * Feature base format for reading and writing data in the GML format. - * This class cannot be instantiated, it contains only base content that - * is shared with versioned format classes ol.format.GML2 and - * ol.format.GML3. - * - * @constructor - * @abstract - * @param {olx.format.GMLOptions=} opt_options - * Optional configuration object. - * @extends {ol.format.XMLFeature} - */ -ol.format.GMLBase = function(opt_options) { - var options = /** @type {olx.format.GMLOptions} */ - (opt_options ? opt_options : {}); - - /** - * @protected - * @type {Array.<string>|string|undefined} - */ - this.featureType = options.featureType; - - /** - * @protected - * @type {Object.<string, string>|string|undefined} - */ - this.featureNS = options.featureNS; - - /** - * @protected - * @type {string} - */ - this.srsName = options.srsName; - - /** - * @protected - * @type {string} - */ - this.schemaLocation = ''; - - /** - * @type {Object.<string, Object.<string, Object>>} - */ - this.FEATURE_COLLECTION_PARSERS = {}; - this.FEATURE_COLLECTION_PARSERS[ol.format.GMLBase.GMLNS] = { - 'featureMember': ol.xml.makeReplacer( - ol.format.GMLBase.prototype.readFeaturesInternal), - 'featureMembers': ol.xml.makeReplacer( - ol.format.GMLBase.prototype.readFeaturesInternal) - }; - - ol.format.XMLFeature.call(this); -}; -ol.inherits(ol.format.GMLBase, ol.format.XMLFeature); - - -/** - * @const - * @type {string} - */ -ol.format.GMLBase.GMLNS = 'http://www.opengis.net/gml'; - - -/** - * A regular expression that matches if a string only contains whitespace - * characters. It will e.g. match `''`, `' '`, `'\n'` etc. The non-breaking - * space (0xa0) is explicitly included as IE doesn't include it in its - * definition of `\s`. - * - * Information from `goog.string.isEmptyOrWhitespace`: https://github.com/google/closure-library/blob/e877b1e/closure/goog/string/string.js#L156-L160 - * - * @const - * @type {RegExp} - * @private - */ -ol.format.GMLBase.ONLY_WHITESPACE_RE_ = /^[\s\xa0]*$/; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Array.<ol.Feature> | undefined} Features. - */ -ol.format.GMLBase.prototype.readFeaturesInternal = function(node, objectStack) { - var localName = node.localName; - var features = null; - if (localName == 'FeatureCollection') { - if (node.namespaceURI === 'http://www.opengis.net/wfs') { - features = ol.xml.pushParseAndPop([], - this.FEATURE_COLLECTION_PARSERS, node, - objectStack, this); - } else { - features = ol.xml.pushParseAndPop(null, - this.FEATURE_COLLECTION_PARSERS, node, - objectStack, this); - } - } else if (localName == 'featureMembers' || localName == 'featureMember') { - var context = objectStack[0]; - var featureType = context['featureType']; - var featureNS = context['featureNS']; - var i, ii, prefix = 'p', defaultPrefix = 'p0'; - if (!featureType && node.childNodes) { - featureType = [], featureNS = {}; - for (i = 0, ii = node.childNodes.length; i < ii; ++i) { - var child = node.childNodes[i]; - if (child.nodeType === 1) { - var ft = child.nodeName.split(':').pop(); - if (featureType.indexOf(ft) === -1) { - var key = ''; - var count = 0; - var uri = child.namespaceURI; - for (var candidate in featureNS) { - if (featureNS[candidate] === uri) { - key = candidate; - break; - } - ++count; - } - if (!key) { - key = prefix + count; - featureNS[key] = uri; - } - featureType.push(key + ':' + ft); - } - } - } - if (localName != 'featureMember') { - // recheck featureType for each featureMember - context['featureType'] = featureType; - context['featureNS'] = featureNS; - } - } - if (typeof featureNS === 'string') { - var ns = featureNS; - featureNS = {}; - featureNS[defaultPrefix] = ns; - } - var parsersNS = {}; - var featureTypes = Array.isArray(featureType) ? featureType : [featureType]; - for (var p in featureNS) { - var parsers = {}; - for (i = 0, ii = featureTypes.length; i < ii; ++i) { - var featurePrefix = featureTypes[i].indexOf(':') === -1 ? - defaultPrefix : featureTypes[i].split(':')[0]; - if (featurePrefix === p) { - parsers[featureTypes[i].split(':').pop()] = - (localName == 'featureMembers') ? - ol.xml.makeArrayPusher(this.readFeatureElement, this) : - ol.xml.makeReplacer(this.readFeatureElement, this); - } - } - parsersNS[featureNS[p]] = parsers; - } - if (localName == 'featureMember') { - features = ol.xml.pushParseAndPop(undefined, parsersNS, node, objectStack); - } else { - features = ol.xml.pushParseAndPop([], parsersNS, node, objectStack); - } - } - if (features === null) { - features = []; - } - return features; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {ol.geom.Geometry|undefined} Geometry. - */ -ol.format.GMLBase.prototype.readGeometryElement = function(node, objectStack) { - var context = /** @type {Object} */ (objectStack[0]); - context['srsName'] = node.firstElementChild.getAttribute('srsName'); - context['srsDimension'] = node.firstElementChild.getAttribute('srsDimension'); - /** @type {ol.geom.Geometry} */ - var geometry = ol.xml.pushParseAndPop(null, - this.GEOMETRY_PARSERS_, node, objectStack, this); - if (geometry) { - return /** @type {ol.geom.Geometry} */ ( - ol.format.Feature.transformWithOptions(geometry, false, context)); - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {ol.Feature} Feature. - */ -ol.format.GMLBase.prototype.readFeatureElement = function(node, objectStack) { - var n; - var fid = node.getAttribute('fid') || - ol.xml.getAttributeNS(node, ol.format.GMLBase.GMLNS, 'id'); - var values = {}, geometryName; - for (n = node.firstElementChild; n; n = n.nextElementSibling) { - var localName = n.localName; - // Assume attribute elements have one child node and that the child - // is a text or CDATA node (to be treated as text). - // Otherwise assume it is a geometry node. - if (n.childNodes.length === 0 || - (n.childNodes.length === 1 && - (n.firstChild.nodeType === 3 || n.firstChild.nodeType === 4))) { - var value = ol.xml.getAllTextContent(n, false); - if (ol.format.GMLBase.ONLY_WHITESPACE_RE_.test(value)) { - value = undefined; - } - values[localName] = value; - } else { - // boundedBy is an extent and must not be considered as a geometry - if (localName !== 'boundedBy') { - geometryName = localName; - } - values[localName] = this.readGeometryElement(n, objectStack); - } - } - var feature = new ol.Feature(values); - if (geometryName) { - feature.setGeometryName(geometryName); - } - if (fid) { - feature.setId(fid); - } - return feature; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {ol.geom.Point|undefined} Point. - */ -ol.format.GMLBase.prototype.readPoint = function(node, objectStack) { - var flatCoordinates = - this.readFlatCoordinatesFromNode_(node, objectStack); - if (flatCoordinates) { - var point = new ol.geom.Point(null); - point.setFlatCoordinates(ol.geom.GeometryLayout.XYZ, flatCoordinates); - return point; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {ol.geom.MultiPoint|undefined} MultiPoint. - */ -ol.format.GMLBase.prototype.readMultiPoint = function(node, objectStack) { - /** @type {Array.<Array.<number>>} */ - var coordinates = ol.xml.pushParseAndPop([], - this.MULTIPOINT_PARSERS_, node, objectStack, this); - if (coordinates) { - return new ol.geom.MultiPoint(coordinates); - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {ol.geom.MultiLineString|undefined} MultiLineString. - */ -ol.format.GMLBase.prototype.readMultiLineString = function(node, objectStack) { - /** @type {Array.<ol.geom.LineString>} */ - var lineStrings = ol.xml.pushParseAndPop([], - this.MULTILINESTRING_PARSERS_, node, objectStack, this); - if (lineStrings) { - var multiLineString = new ol.geom.MultiLineString(null); - multiLineString.setLineStrings(lineStrings); - return multiLineString; - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {ol.geom.MultiPolygon|undefined} MultiPolygon. - */ -ol.format.GMLBase.prototype.readMultiPolygon = function(node, objectStack) { - /** @type {Array.<ol.geom.Polygon>} */ - var polygons = ol.xml.pushParseAndPop([], - this.MULTIPOLYGON_PARSERS_, node, objectStack, this); - if (polygons) { - var multiPolygon = new ol.geom.MultiPolygon(null); - multiPolygon.setPolygons(polygons); - return multiPolygon; - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GMLBase.prototype.pointMemberParser_ = function(node, objectStack) { - ol.xml.parseNode(this.POINTMEMBER_PARSERS_, - node, objectStack, this); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GMLBase.prototype.lineStringMemberParser_ = function(node, objectStack) { - ol.xml.parseNode(this.LINESTRINGMEMBER_PARSERS_, - node, objectStack, this); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GMLBase.prototype.polygonMemberParser_ = function(node, objectStack) { - ol.xml.parseNode(this.POLYGONMEMBER_PARSERS_, node, - objectStack, this); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {ol.geom.LineString|undefined} LineString. - */ -ol.format.GMLBase.prototype.readLineString = function(node, objectStack) { - var flatCoordinates = - this.readFlatCoordinatesFromNode_(node, objectStack); - if (flatCoordinates) { - var lineString = new ol.geom.LineString(null); - lineString.setFlatCoordinates(ol.geom.GeometryLayout.XYZ, flatCoordinates); - return lineString; - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Array.<number>|undefined} LinearRing flat coordinates. - */ -ol.format.GMLBase.prototype.readFlatLinearRing_ = function(node, objectStack) { - var ring = ol.xml.pushParseAndPop(null, - this.GEOMETRY_FLAT_COORDINATES_PARSERS_, node, - objectStack, this); - if (ring) { - return ring; - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {ol.geom.LinearRing|undefined} LinearRing. - */ -ol.format.GMLBase.prototype.readLinearRing = function(node, objectStack) { - var flatCoordinates = - this.readFlatCoordinatesFromNode_(node, objectStack); - if (flatCoordinates) { - var ring = new ol.geom.LinearRing(null); - ring.setFlatCoordinates(ol.geom.GeometryLayout.XYZ, flatCoordinates); - return ring; - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {ol.geom.Polygon|undefined} Polygon. - */ -ol.format.GMLBase.prototype.readPolygon = function(node, objectStack) { - /** @type {Array.<Array.<number>>} */ - var flatLinearRings = ol.xml.pushParseAndPop([null], - this.FLAT_LINEAR_RINGS_PARSERS_, node, objectStack, this); - if (flatLinearRings && flatLinearRings[0]) { - var polygon = new ol.geom.Polygon(null); - var flatCoordinates = flatLinearRings[0]; - var ends = [flatCoordinates.length]; - var i, ii; - for (i = 1, ii = flatLinearRings.length; i < ii; ++i) { - ol.array.extend(flatCoordinates, flatLinearRings[i]); - ends.push(flatCoordinates.length); - } - polygon.setFlatCoordinates( - ol.geom.GeometryLayout.XYZ, flatCoordinates, ends); - return polygon; - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Array.<number>} Flat coordinates. - */ -ol.format.GMLBase.prototype.readFlatCoordinatesFromNode_ = function(node, objectStack) { - return ol.xml.pushParseAndPop(null, - this.GEOMETRY_FLAT_COORDINATES_PARSERS_, node, - objectStack, this); -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GMLBase.prototype.MULTIPOINT_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'pointMember': ol.xml.makeArrayPusher( - ol.format.GMLBase.prototype.pointMemberParser_), - 'pointMembers': ol.xml.makeArrayPusher( - ol.format.GMLBase.prototype.pointMemberParser_) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GMLBase.prototype.MULTILINESTRING_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'lineStringMember': ol.xml.makeArrayPusher( - ol.format.GMLBase.prototype.lineStringMemberParser_), - 'lineStringMembers': ol.xml.makeArrayPusher( - ol.format.GMLBase.prototype.lineStringMemberParser_) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GMLBase.prototype.MULTIPOLYGON_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'polygonMember': ol.xml.makeArrayPusher( - ol.format.GMLBase.prototype.polygonMemberParser_), - 'polygonMembers': ol.xml.makeArrayPusher( - ol.format.GMLBase.prototype.polygonMemberParser_) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GMLBase.prototype.POINTMEMBER_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'Point': ol.xml.makeArrayPusher( - ol.format.GMLBase.prototype.readFlatCoordinatesFromNode_) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GMLBase.prototype.LINESTRINGMEMBER_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'LineString': ol.xml.makeArrayPusher( - ol.format.GMLBase.prototype.readLineString) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GMLBase.prototype.POLYGONMEMBER_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'Polygon': ol.xml.makeArrayPusher( - ol.format.GMLBase.prototype.readPolygon) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @protected - */ -ol.format.GMLBase.prototype.RING_PARSERS = { - 'http://www.opengis.net/gml': { - 'LinearRing': ol.xml.makeReplacer( - ol.format.GMLBase.prototype.readFlatLinearRing_) - } -}; - - -/** - * @inheritDoc - */ -ol.format.GMLBase.prototype.readGeometryFromNode = function(node, opt_options) { - var geometry = this.readGeometryElement(node, - [this.getReadOptions(node, opt_options ? opt_options : {})]); - return geometry ? geometry : null; -}; - - -/** - * Read all features from a GML FeatureCollection. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Options. - * @return {Array.<ol.Feature>} Features. - * @api - */ -ol.format.GMLBase.prototype.readFeatures; - - -/** - * @inheritDoc - */ -ol.format.GMLBase.prototype.readFeaturesFromNode = function(node, opt_options) { - var options = { - featureType: this.featureType, - featureNS: this.featureNS - }; - if (opt_options) { - ol.obj.assign(options, this.getReadOptions(node, opt_options)); - } - var features = this.readFeaturesInternal(node, [options]); - return features || []; -}; - - -/** - * @inheritDoc - */ -ol.format.GMLBase.prototype.readProjectionFromNode = function(node) { - return ol.proj.get(this.srsName ? this.srsName : - node.firstElementChild.getAttribute('srsName')); -}; - -goog.provide('ol.format.XSD'); - -goog.require('ol.xml'); -goog.require('ol.string'); - - -/** - * @const - * @type {string} - */ -ol.format.XSD.NAMESPACE_URI = 'http://www.w3.org/2001/XMLSchema'; - - -/** - * @param {Node} node Node. - * @return {boolean|undefined} Boolean. - */ -ol.format.XSD.readBoolean = function(node) { - var s = ol.xml.getAllTextContent(node, false); - return ol.format.XSD.readBooleanString(s); -}; - - -/** - * @param {string} string String. - * @return {boolean|undefined} Boolean. - */ -ol.format.XSD.readBooleanString = function(string) { - var m = /^\s*(true|1)|(false|0)\s*$/.exec(string); - if (m) { - return m[1] !== undefined || false; - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @return {number|undefined} DateTime in seconds. - */ -ol.format.XSD.readDateTime = function(node) { - var s = ol.xml.getAllTextContent(node, false); - var dateTime = Date.parse(s); - return isNaN(dateTime) ? undefined : dateTime / 1000; -}; - - -/** - * @param {Node} node Node. - * @return {number|undefined} Decimal. - */ -ol.format.XSD.readDecimal = function(node) { - var s = ol.xml.getAllTextContent(node, false); - return ol.format.XSD.readDecimalString(s); -}; - - -/** - * @param {string} string String. - * @return {number|undefined} Decimal. - */ -ol.format.XSD.readDecimalString = function(string) { - // FIXME check spec - var m = /^\s*([+\-]?\d*\.?\d+(?:e[+\-]?\d+)?)\s*$/i.exec(string); - if (m) { - return parseFloat(m[1]); - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @return {number|undefined} Non negative integer. - */ -ol.format.XSD.readNonNegativeInteger = function(node) { - var s = ol.xml.getAllTextContent(node, false); - return ol.format.XSD.readNonNegativeIntegerString(s); -}; - - -/** - * @param {string} string String. - * @return {number|undefined} Non negative integer. - */ -ol.format.XSD.readNonNegativeIntegerString = function(string) { - var m = /^\s*(\d+)\s*$/.exec(string); - if (m) { - return parseInt(m[1], 10); - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @return {string|undefined} String. - */ -ol.format.XSD.readString = function(node) { - return ol.xml.getAllTextContent(node, false).trim(); -}; - - -/** - * @param {Node} node Node to append a TextNode with the boolean to. - * @param {boolean} bool Boolean. - */ -ol.format.XSD.writeBooleanTextNode = function(node, bool) { - ol.format.XSD.writeStringTextNode(node, (bool) ? '1' : '0'); -}; - - -/** - * @param {Node} node Node to append a CDATA Section with the string to. - * @param {string} string String. - */ -ol.format.XSD.writeCDATASection = function(node, string) { - node.appendChild(ol.xml.DOCUMENT.createCDATASection(string)); -}; - - -/** - * @param {Node} node Node to append a TextNode with the dateTime to. - * @param {number} dateTime DateTime in seconds. - */ -ol.format.XSD.writeDateTimeTextNode = function(node, dateTime) { - var date = new Date(dateTime * 1000); - var string = date.getUTCFullYear() + '-' + - ol.string.padNumber(date.getUTCMonth() + 1, 2) + '-' + - ol.string.padNumber(date.getUTCDate(), 2) + 'T' + - ol.string.padNumber(date.getUTCHours(), 2) + ':' + - ol.string.padNumber(date.getUTCMinutes(), 2) + ':' + - ol.string.padNumber(date.getUTCSeconds(), 2) + 'Z'; - node.appendChild(ol.xml.DOCUMENT.createTextNode(string)); -}; - - -/** - * @param {Node} node Node to append a TextNode with the decimal to. - * @param {number} decimal Decimal. - */ -ol.format.XSD.writeDecimalTextNode = function(node, decimal) { - var string = decimal.toPrecision(); - node.appendChild(ol.xml.DOCUMENT.createTextNode(string)); -}; - - -/** - * @param {Node} node Node to append a TextNode with the decimal to. - * @param {number} nonNegativeInteger Non negative integer. - */ -ol.format.XSD.writeNonNegativeIntegerTextNode = function(node, nonNegativeInteger) { - var string = nonNegativeInteger.toString(); - node.appendChild(ol.xml.DOCUMENT.createTextNode(string)); -}; - - -/** - * @param {Node} node Node to append a TextNode with the string to. - * @param {string} string String. - */ -ol.format.XSD.writeStringTextNode = function(node, string) { - node.appendChild(ol.xml.DOCUMENT.createTextNode(string)); -}; - -goog.provide('ol.format.GML3'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.extent'); -goog.require('ol.format.Feature'); -goog.require('ol.format.GMLBase'); -goog.require('ol.format.XSD'); -goog.require('ol.geom.Geometry'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.LineString'); -goog.require('ol.geom.MultiLineString'); -goog.require('ol.geom.MultiPolygon'); -goog.require('ol.geom.Polygon'); -goog.require('ol.obj'); -goog.require('ol.proj'); -goog.require('ol.xml'); - - -/** - * @classdesc - * Feature format for reading and writing data in the GML format - * version 3.1.1. - * Currently only supports GML 3.1.1 Simple Features profile. - * - * @constructor - * @param {olx.format.GMLOptions=} opt_options - * Optional configuration object. - * @extends {ol.format.GMLBase} - * @api - */ -ol.format.GML3 = function(opt_options) { - var options = /** @type {olx.format.GMLOptions} */ - (opt_options ? opt_options : {}); - - ol.format.GMLBase.call(this, options); - - /** - * @private - * @type {boolean} - */ - this.surface_ = options.surface !== undefined ? options.surface : false; - - /** - * @private - * @type {boolean} - */ - this.curve_ = options.curve !== undefined ? options.curve : false; - - /** - * @private - * @type {boolean} - */ - this.multiCurve_ = options.multiCurve !== undefined ? - options.multiCurve : true; - - /** - * @private - * @type {boolean} - */ - this.multiSurface_ = options.multiSurface !== undefined ? - options.multiSurface : true; - - /** - * @inheritDoc - */ - this.schemaLocation = options.schemaLocation ? - options.schemaLocation : ol.format.GML3.schemaLocation_; - - /** - * @private - * @type {boolean} - */ - this.hasZ = options.hasZ !== undefined ? - options.hasZ : false; - -}; -ol.inherits(ol.format.GML3, ol.format.GMLBase); - - -/** - * @const - * @type {string} - * @private - */ -ol.format.GML3.schemaLocation_ = ol.format.GMLBase.GMLNS + - ' http://schemas.opengis.net/gml/3.1.1/profiles/gmlsfProfile/' + - '1.0.0/gmlsf.xsd'; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {ol.geom.MultiLineString|undefined} MultiLineString. - */ -ol.format.GML3.prototype.readMultiCurve_ = function(node, objectStack) { - /** @type {Array.<ol.geom.LineString>} */ - var lineStrings = ol.xml.pushParseAndPop([], - this.MULTICURVE_PARSERS_, node, objectStack, this); - if (lineStrings) { - var multiLineString = new ol.geom.MultiLineString(null); - multiLineString.setLineStrings(lineStrings); - return multiLineString; - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {ol.geom.MultiPolygon|undefined} MultiPolygon. - */ -ol.format.GML3.prototype.readMultiSurface_ = function(node, objectStack) { - /** @type {Array.<ol.geom.Polygon>} */ - var polygons = ol.xml.pushParseAndPop([], - this.MULTISURFACE_PARSERS_, node, objectStack, this); - if (polygons) { - var multiPolygon = new ol.geom.MultiPolygon(null); - multiPolygon.setPolygons(polygons); - return multiPolygon; - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GML3.prototype.curveMemberParser_ = function(node, objectStack) { - ol.xml.parseNode(this.CURVEMEMBER_PARSERS_, node, objectStack, this); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GML3.prototype.surfaceMemberParser_ = function(node, objectStack) { - ol.xml.parseNode(this.SURFACEMEMBER_PARSERS_, - node, objectStack, this); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Array.<(Array.<number>)>|undefined} flat coordinates. - */ -ol.format.GML3.prototype.readPatch_ = function(node, objectStack) { - return ol.xml.pushParseAndPop([null], - this.PATCHES_PARSERS_, node, objectStack, this); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Array.<number>|undefined} flat coordinates. - */ -ol.format.GML3.prototype.readSegment_ = function(node, objectStack) { - return ol.xml.pushParseAndPop([null], - this.SEGMENTS_PARSERS_, node, objectStack, this); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Array.<(Array.<number>)>|undefined} flat coordinates. - */ -ol.format.GML3.prototype.readPolygonPatch_ = function(node, objectStack) { - return ol.xml.pushParseAndPop([null], - this.FLAT_LINEAR_RINGS_PARSERS_, node, objectStack, this); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Array.<number>|undefined} flat coordinates. - */ -ol.format.GML3.prototype.readLineStringSegment_ = function(node, objectStack) { - return ol.xml.pushParseAndPop([null], - this.GEOMETRY_FLAT_COORDINATES_PARSERS_, - node, objectStack, this); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GML3.prototype.interiorParser_ = function(node, objectStack) { - /** @type {Array.<number>|undefined} */ - var flatLinearRing = ol.xml.pushParseAndPop(undefined, - this.RING_PARSERS, node, objectStack, this); - if (flatLinearRing) { - var flatLinearRings = /** @type {Array.<Array.<number>>} */ - (objectStack[objectStack.length - 1]); - flatLinearRings.push(flatLinearRing); - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GML3.prototype.exteriorParser_ = function(node, objectStack) { - /** @type {Array.<number>|undefined} */ - var flatLinearRing = ol.xml.pushParseAndPop(undefined, - this.RING_PARSERS, node, objectStack, this); - if (flatLinearRing) { - var flatLinearRings = /** @type {Array.<Array.<number>>} */ - (objectStack[objectStack.length - 1]); - flatLinearRings[0] = flatLinearRing; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {ol.geom.Polygon|undefined} Polygon. - */ -ol.format.GML3.prototype.readSurface_ = function(node, objectStack) { - /** @type {Array.<Array.<number>>} */ - var flatLinearRings = ol.xml.pushParseAndPop([null], - this.SURFACE_PARSERS_, node, objectStack, this); - if (flatLinearRings && flatLinearRings[0]) { - var polygon = new ol.geom.Polygon(null); - var flatCoordinates = flatLinearRings[0]; - var ends = [flatCoordinates.length]; - var i, ii; - for (i = 1, ii = flatLinearRings.length; i < ii; ++i) { - ol.array.extend(flatCoordinates, flatLinearRings[i]); - ends.push(flatCoordinates.length); - } - polygon.setFlatCoordinates( - ol.geom.GeometryLayout.XYZ, flatCoordinates, ends); - return polygon; - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {ol.geom.LineString|undefined} LineString. - */ -ol.format.GML3.prototype.readCurve_ = function(node, objectStack) { - /** @type {Array.<number>} */ - var flatCoordinates = ol.xml.pushParseAndPop([null], - this.CURVE_PARSERS_, node, objectStack, this); - if (flatCoordinates) { - var lineString = new ol.geom.LineString(null); - lineString.setFlatCoordinates(ol.geom.GeometryLayout.XYZ, flatCoordinates); - return lineString; - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {ol.Extent|undefined} Envelope. - */ -ol.format.GML3.prototype.readEnvelope_ = function(node, objectStack) { - /** @type {Array.<number>} */ - var flatCoordinates = ol.xml.pushParseAndPop([null], - this.ENVELOPE_PARSERS_, node, objectStack, this); - return ol.extent.createOrUpdate(flatCoordinates[1][0], - flatCoordinates[1][1], flatCoordinates[2][0], - flatCoordinates[2][1]); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Array.<number>|undefined} Flat coordinates. - */ -ol.format.GML3.prototype.readFlatPos_ = function(node, objectStack) { - var s = ol.xml.getAllTextContent(node, false); - var re = /^\s*([+\-]?\d*\.?\d+(?:[eE][+\-]?\d+)?)\s*/; - /** @type {Array.<number>} */ - var flatCoordinates = []; - var m; - while ((m = re.exec(s))) { - flatCoordinates.push(parseFloat(m[1])); - s = s.substr(m[0].length); - } - if (s !== '') { - return undefined; - } - var context = objectStack[0]; - var containerSrs = context['srsName']; - var axisOrientation = 'enu'; - if (containerSrs) { - var proj = ol.proj.get(containerSrs); - axisOrientation = proj.getAxisOrientation(); - } - if (axisOrientation === 'neu') { - var i, ii; - for (i = 0, ii = flatCoordinates.length; i < ii; i += 3) { - var y = flatCoordinates[i]; - var x = flatCoordinates[i + 1]; - flatCoordinates[i] = x; - flatCoordinates[i + 1] = y; - } - } - var len = flatCoordinates.length; - if (len == 2) { - flatCoordinates.push(0); - } - if (len === 0) { - return undefined; - } - return flatCoordinates; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Array.<number>|undefined} Flat coordinates. - */ -ol.format.GML3.prototype.readFlatPosList_ = function(node, objectStack) { - var s = ol.xml.getAllTextContent(node, false).replace(/^\s*|\s*$/g, ''); - var context = objectStack[0]; - var containerSrs = context['srsName']; - var contextDimension = context['srsDimension']; - var axisOrientation = 'enu'; - if (containerSrs) { - var proj = ol.proj.get(containerSrs); - axisOrientation = proj.getAxisOrientation(); - } - var coords = s.split(/\s+/); - // The "dimension" attribute is from the GML 3.0.1 spec. - var dim = 2; - if (node.getAttribute('srsDimension')) { - dim = ol.format.XSD.readNonNegativeIntegerString( - node.getAttribute('srsDimension')); - } else if (node.getAttribute('dimension')) { - dim = ol.format.XSD.readNonNegativeIntegerString( - node.getAttribute('dimension')); - } else if (node.parentNode.getAttribute('srsDimension')) { - dim = ol.format.XSD.readNonNegativeIntegerString( - node.parentNode.getAttribute('srsDimension')); - } else if (contextDimension) { - dim = ol.format.XSD.readNonNegativeIntegerString(contextDimension); - } - var x, y, z; - var flatCoordinates = []; - for (var i = 0, ii = coords.length; i < ii; i += dim) { - x = parseFloat(coords[i]); - y = parseFloat(coords[i + 1]); - z = (dim === 3) ? parseFloat(coords[i + 2]) : 0; - if (axisOrientation.substr(0, 2) === 'en') { - flatCoordinates.push(x, y, z); - } else { - flatCoordinates.push(y, x, z); - } - } - return flatCoordinates; -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GML3.prototype.GEOMETRY_FLAT_COORDINATES_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'pos': ol.xml.makeReplacer(ol.format.GML3.prototype.readFlatPos_), - 'posList': ol.xml.makeReplacer(ol.format.GML3.prototype.readFlatPosList_) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GML3.prototype.FLAT_LINEAR_RINGS_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'interior': ol.format.GML3.prototype.interiorParser_, - 'exterior': ol.format.GML3.prototype.exteriorParser_ - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GML3.prototype.GEOMETRY_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'Point': ol.xml.makeReplacer(ol.format.GMLBase.prototype.readPoint), - 'MultiPoint': ol.xml.makeReplacer( - ol.format.GMLBase.prototype.readMultiPoint), - 'LineString': ol.xml.makeReplacer( - ol.format.GMLBase.prototype.readLineString), - 'MultiLineString': ol.xml.makeReplacer( - ol.format.GMLBase.prototype.readMultiLineString), - 'LinearRing': ol.xml.makeReplacer( - ol.format.GMLBase.prototype.readLinearRing), - 'Polygon': ol.xml.makeReplacer(ol.format.GMLBase.prototype.readPolygon), - 'MultiPolygon': ol.xml.makeReplacer( - ol.format.GMLBase.prototype.readMultiPolygon), - 'Surface': ol.xml.makeReplacer(ol.format.GML3.prototype.readSurface_), - 'MultiSurface': ol.xml.makeReplacer( - ol.format.GML3.prototype.readMultiSurface_), - 'Curve': ol.xml.makeReplacer(ol.format.GML3.prototype.readCurve_), - 'MultiCurve': ol.xml.makeReplacer( - ol.format.GML3.prototype.readMultiCurve_), - 'Envelope': ol.xml.makeReplacer(ol.format.GML3.prototype.readEnvelope_) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GML3.prototype.MULTICURVE_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'curveMember': ol.xml.makeArrayPusher( - ol.format.GML3.prototype.curveMemberParser_), - 'curveMembers': ol.xml.makeArrayPusher( - ol.format.GML3.prototype.curveMemberParser_) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GML3.prototype.MULTISURFACE_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'surfaceMember': ol.xml.makeArrayPusher( - ol.format.GML3.prototype.surfaceMemberParser_), - 'surfaceMembers': ol.xml.makeArrayPusher( - ol.format.GML3.prototype.surfaceMemberParser_) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GML3.prototype.CURVEMEMBER_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'LineString': ol.xml.makeArrayPusher( - ol.format.GMLBase.prototype.readLineString), - 'Curve': ol.xml.makeArrayPusher(ol.format.GML3.prototype.readCurve_) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GML3.prototype.SURFACEMEMBER_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'Polygon': ol.xml.makeArrayPusher(ol.format.GMLBase.prototype.readPolygon), - 'Surface': ol.xml.makeArrayPusher(ol.format.GML3.prototype.readSurface_) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GML3.prototype.SURFACE_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'patches': ol.xml.makeReplacer(ol.format.GML3.prototype.readPatch_) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GML3.prototype.CURVE_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'segments': ol.xml.makeReplacer(ol.format.GML3.prototype.readSegment_) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GML3.prototype.ENVELOPE_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'lowerCorner': ol.xml.makeArrayPusher( - ol.format.GML3.prototype.readFlatPosList_), - 'upperCorner': ol.xml.makeArrayPusher( - ol.format.GML3.prototype.readFlatPosList_) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GML3.prototype.PATCHES_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'PolygonPatch': ol.xml.makeReplacer( - ol.format.GML3.prototype.readPolygonPatch_) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GML3.prototype.SEGMENTS_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'LineStringSegment': ol.xml.makeReplacer( - ol.format.GML3.prototype.readLineStringSegment_) - } -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.Point} value Point geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML3.prototype.writePos_ = function(node, value, objectStack) { - var context = objectStack[objectStack.length - 1]; - var hasZ = context['hasZ']; - var srsDimension = hasZ ? 3 : 2; - node.setAttribute('srsDimension', srsDimension); - var srsName = context['srsName']; - var axisOrientation = 'enu'; - if (srsName) { - axisOrientation = ol.proj.get(srsName).getAxisOrientation(); - } - var point = value.getCoordinates(); - var coords; - // only 2d for simple features profile - if (axisOrientation.substr(0, 2) === 'en') { - coords = (point[0] + ' ' + point[1]); - } else { - coords = (point[1] + ' ' + point[0]); - } - if (hasZ) { - // For newly created points, Z can be undefined. - var z = point[2] || 0; - coords += ' ' + z; - } - ol.format.XSD.writeStringTextNode(node, coords); -}; - - -/** - * @param {Array.<number>} point Point geometry. - * @param {string=} opt_srsName Optional srsName - * @param {boolean=} opt_hasZ whether the geometry has a Z coordinate (is 3D) or not. - * @return {string} The coords string. - * @private - */ -ol.format.GML3.prototype.getCoords_ = function(point, opt_srsName, opt_hasZ) { - var axisOrientation = 'enu'; - if (opt_srsName) { - axisOrientation = ol.proj.get(opt_srsName).getAxisOrientation(); - } - var coords = ((axisOrientation.substr(0, 2) === 'en') ? - point[0] + ' ' + point[1] : - point[1] + ' ' + point[0]); - if (opt_hasZ) { - // For newly created points, Z can be undefined. - var z = point[2] || 0; - coords += ' ' + z; - } - - return coords; -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.LineString|ol.geom.LinearRing} value Geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML3.prototype.writePosList_ = function(node, value, objectStack) { - var context = objectStack[objectStack.length - 1]; - var hasZ = context['hasZ']; - var srsDimension = hasZ ? 3 : 2; - node.setAttribute('srsDimension', srsDimension); - var srsName = context['srsName']; - // only 2d for simple features profile - var points = value.getCoordinates(); - var len = points.length; - var parts = new Array(len); - var point; - for (var i = 0; i < len; ++i) { - point = points[i]; - parts[i] = this.getCoords_(point, srsName, hasZ); - } - ol.format.XSD.writeStringTextNode(node, parts.join(' ')); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.Point} geometry Point geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML3.prototype.writePoint_ = function(node, geometry, objectStack) { - var context = objectStack[objectStack.length - 1]; - var srsName = context['srsName']; - if (srsName) { - node.setAttribute('srsName', srsName); - } - var pos = ol.xml.createElementNS(node.namespaceURI, 'pos'); - node.appendChild(pos); - this.writePos_(pos, geometry, objectStack); -}; - - -/** - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GML3.ENVELOPE_SERIALIZERS_ = { - 'http://www.opengis.net/gml': { - 'lowerCorner': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'upperCorner': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode) - } -}; - - -/** - * @param {Node} node Node. - * @param {ol.Extent} extent Extent. - * @param {Array.<*>} objectStack Node stack. - */ -ol.format.GML3.prototype.writeEnvelope = function(node, extent, objectStack) { - var context = objectStack[objectStack.length - 1]; - var srsName = context['srsName']; - if (srsName) { - node.setAttribute('srsName', srsName); - } - var keys = ['lowerCorner', 'upperCorner']; - var values = [extent[0] + ' ' + extent[1], extent[2] + ' ' + extent[3]]; - ol.xml.pushSerializeAndPop(/** @type {ol.XmlNodeStackItem} */ - ({node: node}), ol.format.GML3.ENVELOPE_SERIALIZERS_, - ol.xml.OBJECT_PROPERTY_NODE_FACTORY, - values, - objectStack, keys, this); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.LinearRing} geometry LinearRing geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML3.prototype.writeLinearRing_ = function(node, geometry, objectStack) { - var context = objectStack[objectStack.length - 1]; - var srsName = context['srsName']; - if (srsName) { - node.setAttribute('srsName', srsName); - } - var posList = ol.xml.createElementNS(node.namespaceURI, 'posList'); - node.appendChild(posList); - this.writePosList_(posList, geometry, objectStack); -}; - - -/** - * @param {*} value Value. - * @param {Array.<*>} objectStack Object stack. - * @param {string=} opt_nodeName Node name. - * @return {Node} Node. - * @private - */ -ol.format.GML3.prototype.RING_NODE_FACTORY_ = function(value, objectStack, opt_nodeName) { - var context = objectStack[objectStack.length - 1]; - var parentNode = context.node; - var exteriorWritten = context['exteriorWritten']; - if (exteriorWritten === undefined) { - context['exteriorWritten'] = true; - } - return ol.xml.createElementNS(parentNode.namespaceURI, - exteriorWritten !== undefined ? 'interior' : 'exterior'); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.Polygon} geometry Polygon geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML3.prototype.writeSurfaceOrPolygon_ = function(node, geometry, objectStack) { - var context = objectStack[objectStack.length - 1]; - var hasZ = context['hasZ']; - var srsName = context['srsName']; - if (node.nodeName !== 'PolygonPatch' && srsName) { - node.setAttribute('srsName', srsName); - } - if (node.nodeName === 'Polygon' || node.nodeName === 'PolygonPatch') { - var rings = geometry.getLinearRings(); - ol.xml.pushSerializeAndPop( - {node: node, hasZ: hasZ, srsName: srsName}, - ol.format.GML3.RING_SERIALIZERS_, - this.RING_NODE_FACTORY_, - rings, objectStack, undefined, this); - } else if (node.nodeName === 'Surface') { - var patches = ol.xml.createElementNS(node.namespaceURI, 'patches'); - node.appendChild(patches); - this.writeSurfacePatches_( - patches, geometry, objectStack); - } -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.LineString} geometry LineString geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML3.prototype.writeCurveOrLineString_ = function(node, geometry, objectStack) { - var context = objectStack[objectStack.length - 1]; - var srsName = context['srsName']; - if (node.nodeName !== 'LineStringSegment' && srsName) { - node.setAttribute('srsName', srsName); - } - if (node.nodeName === 'LineString' || - node.nodeName === 'LineStringSegment') { - var posList = ol.xml.createElementNS(node.namespaceURI, 'posList'); - node.appendChild(posList); - this.writePosList_(posList, geometry, objectStack); - } else if (node.nodeName === 'Curve') { - var segments = ol.xml.createElementNS(node.namespaceURI, 'segments'); - node.appendChild(segments); - this.writeCurveSegments_(segments, - geometry, objectStack); - } -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.MultiPolygon} geometry MultiPolygon geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML3.prototype.writeMultiSurfaceOrPolygon_ = function(node, geometry, objectStack) { - var context = objectStack[objectStack.length - 1]; - var hasZ = context['hasZ']; - var srsName = context['srsName']; - var surface = context['surface']; - if (srsName) { - node.setAttribute('srsName', srsName); - } - var polygons = geometry.getPolygons(); - ol.xml.pushSerializeAndPop({node: node, hasZ: hasZ, srsName: srsName, surface: surface}, - ol.format.GML3.SURFACEORPOLYGONMEMBER_SERIALIZERS_, - this.MULTIGEOMETRY_MEMBER_NODE_FACTORY_, polygons, - objectStack, undefined, this); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.MultiPoint} geometry MultiPoint geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML3.prototype.writeMultiPoint_ = function(node, geometry, - objectStack) { - var context = objectStack[objectStack.length - 1]; - var srsName = context['srsName']; - var hasZ = context['hasZ']; - if (srsName) { - node.setAttribute('srsName', srsName); - } - var points = geometry.getPoints(); - ol.xml.pushSerializeAndPop({node: node, hasZ: hasZ, srsName: srsName}, - ol.format.GML3.POINTMEMBER_SERIALIZERS_, - ol.xml.makeSimpleNodeFactory('pointMember'), points, - objectStack, undefined, this); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.MultiLineString} geometry MultiLineString geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML3.prototype.writeMultiCurveOrLineString_ = function(node, geometry, objectStack) { - var context = objectStack[objectStack.length - 1]; - var hasZ = context['hasZ']; - var srsName = context['srsName']; - var curve = context['curve']; - if (srsName) { - node.setAttribute('srsName', srsName); - } - var lines = geometry.getLineStrings(); - ol.xml.pushSerializeAndPop({node: node, hasZ: hasZ, srsName: srsName, curve: curve}, - ol.format.GML3.LINESTRINGORCURVEMEMBER_SERIALIZERS_, - this.MULTIGEOMETRY_MEMBER_NODE_FACTORY_, lines, - objectStack, undefined, this); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.LinearRing} ring LinearRing geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML3.prototype.writeRing_ = function(node, ring, objectStack) { - var linearRing = ol.xml.createElementNS(node.namespaceURI, 'LinearRing'); - node.appendChild(linearRing); - this.writeLinearRing_(linearRing, ring, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.Polygon} polygon Polygon geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML3.prototype.writeSurfaceOrPolygonMember_ = function(node, polygon, objectStack) { - var child = this.GEOMETRY_NODE_FACTORY_( - polygon, objectStack); - if (child) { - node.appendChild(child); - this.writeSurfaceOrPolygon_(child, polygon, objectStack); - } -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.Point} point Point geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML3.prototype.writePointMember_ = function(node, point, objectStack) { - var child = ol.xml.createElementNS(node.namespaceURI, 'Point'); - node.appendChild(child); - this.writePoint_(child, point, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.LineString} line LineString geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML3.prototype.writeLineStringOrCurveMember_ = function(node, line, objectStack) { - var child = this.GEOMETRY_NODE_FACTORY_(line, objectStack); - if (child) { - node.appendChild(child); - this.writeCurveOrLineString_(child, line, objectStack); - } -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.Polygon} polygon Polygon geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML3.prototype.writeSurfacePatches_ = function(node, polygon, objectStack) { - var child = ol.xml.createElementNS(node.namespaceURI, 'PolygonPatch'); - node.appendChild(child); - this.writeSurfaceOrPolygon_(child, polygon, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.LineString} line LineString geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML3.prototype.writeCurveSegments_ = function(node, line, objectStack) { - var child = ol.xml.createElementNS(node.namespaceURI, - 'LineStringSegment'); - node.appendChild(child); - this.writeCurveOrLineString_(child, line, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.Geometry|ol.Extent} geometry Geometry. - * @param {Array.<*>} objectStack Node stack. - */ -ol.format.GML3.prototype.writeGeometryElement = function(node, geometry, objectStack) { - var context = /** @type {olx.format.WriteOptions} */ (objectStack[objectStack.length - 1]); - var item = ol.obj.assign({}, context); - item.node = node; - var value; - if (Array.isArray(geometry)) { - if (context.dataProjection) { - value = ol.proj.transformExtent( - geometry, context.featureProjection, context.dataProjection); - } else { - value = geometry; - } - } else { - value = - ol.format.Feature.transformWithOptions(/** @type {ol.geom.Geometry} */ (geometry), true, context); - } - ol.xml.pushSerializeAndPop(/** @type {ol.XmlNodeStackItem} */ - (item), ol.format.GML3.GEOMETRY_SERIALIZERS_, - this.GEOMETRY_NODE_FACTORY_, [value], - objectStack, undefined, this); -}; - - -/** - * @param {Node} node Node. - * @param {ol.Feature} feature Feature. - * @param {Array.<*>} objectStack Node stack. - */ -ol.format.GML3.prototype.writeFeatureElement = function(node, feature, objectStack) { - var fid = feature.getId(); - if (fid) { - node.setAttribute('fid', fid); - } - var context = /** @type {Object} */ (objectStack[objectStack.length - 1]); - var featureNS = context['featureNS']; - var geometryName = feature.getGeometryName(); - if (!context.serializers) { - context.serializers = {}; - context.serializers[featureNS] = {}; - } - var properties = feature.getProperties(); - var keys = [], values = []; - for (var key in properties) { - var value = properties[key]; - if (value !== null) { - keys.push(key); - values.push(value); - if (key == geometryName || value instanceof ol.geom.Geometry) { - if (!(key in context.serializers[featureNS])) { - context.serializers[featureNS][key] = ol.xml.makeChildAppender( - this.writeGeometryElement, this); - } - } else { - if (!(key in context.serializers[featureNS])) { - context.serializers[featureNS][key] = ol.xml.makeChildAppender( - ol.format.XSD.writeStringTextNode); - } - } - } - } - var item = ol.obj.assign({}, context); - item.node = node; - ol.xml.pushSerializeAndPop(/** @type {ol.XmlNodeStackItem} */ - (item), context.serializers, - ol.xml.makeSimpleNodeFactory(undefined, featureNS), - values, - objectStack, keys); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<ol.Feature>} features Features. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML3.prototype.writeFeatureMembers_ = function(node, features, objectStack) { - var context = /** @type {Object} */ (objectStack[objectStack.length - 1]); - var featureType = context['featureType']; - var featureNS = context['featureNS']; - var serializers = {}; - serializers[featureNS] = {}; - serializers[featureNS][featureType] = ol.xml.makeChildAppender( - this.writeFeatureElement, this); - var item = ol.obj.assign({}, context); - item.node = node; - ol.xml.pushSerializeAndPop(/** @type {ol.XmlNodeStackItem} */ - (item), - serializers, - ol.xml.makeSimpleNodeFactory(featureType, featureNS), features, - objectStack); -}; - - -/** - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GML3.SURFACEORPOLYGONMEMBER_SERIALIZERS_ = { - 'http://www.opengis.net/gml': { - 'surfaceMember': ol.xml.makeChildAppender( - ol.format.GML3.prototype.writeSurfaceOrPolygonMember_), - 'polygonMember': ol.xml.makeChildAppender( - ol.format.GML3.prototype.writeSurfaceOrPolygonMember_) - } -}; - - -/** - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GML3.POINTMEMBER_SERIALIZERS_ = { - 'http://www.opengis.net/gml': { - 'pointMember': ol.xml.makeChildAppender( - ol.format.GML3.prototype.writePointMember_) - } -}; - - -/** - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GML3.LINESTRINGORCURVEMEMBER_SERIALIZERS_ = { - 'http://www.opengis.net/gml': { - 'lineStringMember': ol.xml.makeChildAppender( - ol.format.GML3.prototype.writeLineStringOrCurveMember_), - 'curveMember': ol.xml.makeChildAppender( - ol.format.GML3.prototype.writeLineStringOrCurveMember_) - } -}; - - -/** - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GML3.RING_SERIALIZERS_ = { - 'http://www.opengis.net/gml': { - 'exterior': ol.xml.makeChildAppender(ol.format.GML3.prototype.writeRing_), - 'interior': ol.xml.makeChildAppender(ol.format.GML3.prototype.writeRing_) - } -}; - - -/** - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GML3.GEOMETRY_SERIALIZERS_ = { - 'http://www.opengis.net/gml': { - 'Curve': ol.xml.makeChildAppender( - ol.format.GML3.prototype.writeCurveOrLineString_), - 'MultiCurve': ol.xml.makeChildAppender( - ol.format.GML3.prototype.writeMultiCurveOrLineString_), - 'Point': ol.xml.makeChildAppender(ol.format.GML3.prototype.writePoint_), - 'MultiPoint': ol.xml.makeChildAppender( - ol.format.GML3.prototype.writeMultiPoint_), - 'LineString': ol.xml.makeChildAppender( - ol.format.GML3.prototype.writeCurveOrLineString_), - 'MultiLineString': ol.xml.makeChildAppender( - ol.format.GML3.prototype.writeMultiCurveOrLineString_), - 'LinearRing': ol.xml.makeChildAppender( - ol.format.GML3.prototype.writeLinearRing_), - 'Polygon': ol.xml.makeChildAppender( - ol.format.GML3.prototype.writeSurfaceOrPolygon_), - 'MultiPolygon': ol.xml.makeChildAppender( - ol.format.GML3.prototype.writeMultiSurfaceOrPolygon_), - 'Surface': ol.xml.makeChildAppender( - ol.format.GML3.prototype.writeSurfaceOrPolygon_), - 'MultiSurface': ol.xml.makeChildAppender( - ol.format.GML3.prototype.writeMultiSurfaceOrPolygon_), - 'Envelope': ol.xml.makeChildAppender( - ol.format.GML3.prototype.writeEnvelope) - } -}; - - -/** - * @const - * @type {Object.<string, string>} - * @private - */ -ol.format.GML3.MULTIGEOMETRY_TO_MEMBER_NODENAME_ = { - 'MultiLineString': 'lineStringMember', - 'MultiCurve': 'curveMember', - 'MultiPolygon': 'polygonMember', - 'MultiSurface': 'surfaceMember' -}; - - -/** - * @const - * @param {*} value Value. - * @param {Array.<*>} objectStack Object stack. - * @param {string=} opt_nodeName Node name. - * @return {Node|undefined} Node. - * @private - */ -ol.format.GML3.prototype.MULTIGEOMETRY_MEMBER_NODE_FACTORY_ = function(value, objectStack, opt_nodeName) { - var parentNode = objectStack[objectStack.length - 1].node; - return ol.xml.createElementNS('http://www.opengis.net/gml', - ol.format.GML3.MULTIGEOMETRY_TO_MEMBER_NODENAME_[parentNode.nodeName]); -}; - - -/** - * @const - * @param {*} value Value. - * @param {Array.<*>} objectStack Object stack. - * @param {string=} opt_nodeName Node name. - * @return {Node|undefined} Node. - * @private - */ -ol.format.GML3.prototype.GEOMETRY_NODE_FACTORY_ = function(value, objectStack, opt_nodeName) { - var context = objectStack[objectStack.length - 1]; - var multiSurface = context['multiSurface']; - var surface = context['surface']; - var curve = context['curve']; - var multiCurve = context['multiCurve']; - var nodeName; - if (!Array.isArray(value)) { - nodeName = /** @type {ol.geom.Geometry} */ (value).getType(); - if (nodeName === 'MultiPolygon' && multiSurface === true) { - nodeName = 'MultiSurface'; - } else if (nodeName === 'Polygon' && surface === true) { - nodeName = 'Surface'; - } else if (nodeName === 'LineString' && curve === true) { - nodeName = 'Curve'; - } else if (nodeName === 'MultiLineString' && multiCurve === true) { - nodeName = 'MultiCurve'; - } - } else { - nodeName = 'Envelope'; - } - return ol.xml.createElementNS('http://www.opengis.net/gml', - nodeName); -}; - - -/** - * Encode a geometry in GML 3.1.1 Simple Features. - * - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Options. - * @return {Node} Node. - * @override - * @api - */ -ol.format.GML3.prototype.writeGeometryNode = function(geometry, opt_options) { - opt_options = this.adaptOptions(opt_options); - var geom = ol.xml.createElementNS('http://www.opengis.net/gml', 'geom'); - var context = {node: geom, hasZ: this.hasZ, srsName: this.srsName, - curve: this.curve_, surface: this.surface_, - multiSurface: this.multiSurface_, multiCurve: this.multiCurve_}; - if (opt_options) { - ol.obj.assign(context, opt_options); - } - this.writeGeometryElement(geom, geometry, [context]); - return geom; -}; - - -/** - * Encode an array of features in GML 3.1.1 Simple Features. - * - * @function - * @param {Array.<ol.Feature>} features Features. - * @param {olx.format.WriteOptions=} opt_options Options. - * @return {string} Result. - * @api - */ -ol.format.GML3.prototype.writeFeatures; - - -/** - * Encode an array of features in the GML 3.1.1 format as an XML node. - * - * @param {Array.<ol.Feature>} features Features. - * @param {olx.format.WriteOptions=} opt_options Options. - * @return {Node} Node. - * @override - * @api - */ -ol.format.GML3.prototype.writeFeaturesNode = function(features, opt_options) { - opt_options = this.adaptOptions(opt_options); - var node = ol.xml.createElementNS('http://www.opengis.net/gml', - 'featureMembers'); - ol.xml.setAttributeNS(node, 'http://www.w3.org/2001/XMLSchema-instance', - 'xsi:schemaLocation', this.schemaLocation); - var context = { - srsName: this.srsName, - hasZ: this.hasZ, - curve: this.curve_, - surface: this.surface_, - multiSurface: this.multiSurface_, - multiCurve: this.multiCurve_, - featureNS: this.featureNS, - featureType: this.featureType - }; - if (opt_options) { - ol.obj.assign(context, opt_options); - } - this.writeFeatureMembers_(node, features, [context]); - return node; -}; - -goog.provide('ol.format.GML'); - -goog.require('ol.format.GML3'); - - -/** - * @classdesc - * Feature format for reading and writing data in the GML format - * version 3.1.1. - * Currently only supports GML 3.1.1 Simple Features profile. - * - * @constructor - * @param {olx.format.GMLOptions=} opt_options - * Optional configuration object. - * @extends {ol.format.GMLBase} - * @api - */ -ol.format.GML = ol.format.GML3; - - -/** - * Encode an array of features in GML 3.1.1 Simple Features. - * - * @function - * @param {Array.<ol.Feature>} features Features. - * @param {olx.format.WriteOptions=} opt_options Options. - * @return {string} Result. - * @api - */ -ol.format.GML.prototype.writeFeatures; - - -/** - * Encode an array of features in the GML 3.1.1 format as an XML node. - * - * @function - * @param {Array.<ol.Feature>} features Features. - * @param {olx.format.WriteOptions=} opt_options Options. - * @return {Node} Node. - * @api - */ -ol.format.GML.prototype.writeFeaturesNode; - -goog.provide('ol.format.GML2'); - -goog.require('ol'); -goog.require('ol.extent'); -goog.require('ol.format.Feature'); -goog.require('ol.format.GMLBase'); -goog.require('ol.format.XSD'); -goog.require('ol.geom.Geometry'); -goog.require('ol.obj'); -goog.require('ol.proj'); -goog.require('ol.xml'); - - -/** - * @classdesc - * Feature format for reading and writing data in the GML format, - * version 2.1.2. - * - * @constructor - * @param {olx.format.GMLOptions=} opt_options Optional configuration object. - * @extends {ol.format.GMLBase} - * @api - */ -ol.format.GML2 = function(opt_options) { - var options = /** @type {olx.format.GMLOptions} */ - (opt_options ? opt_options : {}); - - ol.format.GMLBase.call(this, options); - - this.FEATURE_COLLECTION_PARSERS[ol.format.GMLBase.GMLNS][ - 'featureMember'] = - ol.xml.makeArrayPusher(ol.format.GMLBase.prototype.readFeaturesInternal); - - /** - * @inheritDoc - */ - this.schemaLocation = options.schemaLocation ? - options.schemaLocation : ol.format.GML2.schemaLocation_; - -}; -ol.inherits(ol.format.GML2, ol.format.GMLBase); - - -/** - * @const - * @type {string} - * @private - */ -ol.format.GML2.schemaLocation_ = ol.format.GMLBase.GMLNS + - ' http://schemas.opengis.net/gml/2.1.2/feature.xsd'; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Array.<number>|undefined} Flat coordinates. - */ -ol.format.GML2.prototype.readFlatCoordinates_ = function(node, objectStack) { - var s = ol.xml.getAllTextContent(node, false).replace(/^\s*|\s*$/g, ''); - var context = /** @type {ol.XmlNodeStackItem} */ (objectStack[0]); - var containerSrs = context['srsName']; - var axisOrientation = 'enu'; - if (containerSrs) { - var proj = ol.proj.get(containerSrs); - if (proj) { - axisOrientation = proj.getAxisOrientation(); - } - } - var coordsGroups = s.trim().split(/\s+/); - var x, y, z; - var flatCoordinates = []; - for (var i = 0, ii = coordsGroups.length; i < ii; i++) { - var coords = coordsGroups[i].split(/,+/); - x = parseFloat(coords[0]); - y = parseFloat(coords[1]); - z = (coords.length === 3) ? parseFloat(coords[2]) : 0; - if (axisOrientation.substr(0, 2) === 'en') { - flatCoordinates.push(x, y, z); - } else { - flatCoordinates.push(y, x, z); - } - } - return flatCoordinates; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {ol.Extent|undefined} Envelope. - */ -ol.format.GML2.prototype.readBox_ = function(node, objectStack) { - /** @type {Array.<number>} */ - var flatCoordinates = ol.xml.pushParseAndPop([null], - this.BOX_PARSERS_, node, objectStack, this); - return ol.extent.createOrUpdate(flatCoordinates[1][0], - flatCoordinates[1][1], flatCoordinates[1][3], - flatCoordinates[1][4]); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GML2.prototype.innerBoundaryIsParser_ = function(node, objectStack) { - /** @type {Array.<number>|undefined} */ - var flatLinearRing = ol.xml.pushParseAndPop(undefined, - this.RING_PARSERS, node, objectStack, this); - if (flatLinearRing) { - var flatLinearRings = /** @type {Array.<Array.<number>>} */ - (objectStack[objectStack.length - 1]); - flatLinearRings.push(flatLinearRing); - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GML2.prototype.outerBoundaryIsParser_ = function(node, objectStack) { - /** @type {Array.<number>|undefined} */ - var flatLinearRing = ol.xml.pushParseAndPop(undefined, - this.RING_PARSERS, node, objectStack, this); - if (flatLinearRing) { - var flatLinearRings = /** @type {Array.<Array.<number>>} */ - (objectStack[objectStack.length - 1]); - flatLinearRings[0] = flatLinearRing; - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GML2.prototype.GEOMETRY_FLAT_COORDINATES_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'coordinates': ol.xml.makeReplacer( - ol.format.GML2.prototype.readFlatCoordinates_) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GML2.prototype.FLAT_LINEAR_RINGS_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'innerBoundaryIs': ol.format.GML2.prototype.innerBoundaryIsParser_, - 'outerBoundaryIs': ol.format.GML2.prototype.outerBoundaryIsParser_ - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GML2.prototype.BOX_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'coordinates': ol.xml.makeArrayPusher( - ol.format.GML2.prototype.readFlatCoordinates_) - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GML2.prototype.GEOMETRY_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'Point': ol.xml.makeReplacer(ol.format.GMLBase.prototype.readPoint), - 'MultiPoint': ol.xml.makeReplacer( - ol.format.GMLBase.prototype.readMultiPoint), - 'LineString': ol.xml.makeReplacer( - ol.format.GMLBase.prototype.readLineString), - 'MultiLineString': ol.xml.makeReplacer( - ol.format.GMLBase.prototype.readMultiLineString), - 'LinearRing': ol.xml.makeReplacer( - ol.format.GMLBase.prototype.readLinearRing), - 'Polygon': ol.xml.makeReplacer(ol.format.GMLBase.prototype.readPolygon), - 'MultiPolygon': ol.xml.makeReplacer( - ol.format.GMLBase.prototype.readMultiPolygon), - 'Box': ol.xml.makeReplacer(ol.format.GML2.prototype.readBox_) - } -}; - - -/** - * @const - * @param {*} value Value. - * @param {Array.<*>} objectStack Object stack. - * @param {string=} opt_nodeName Node name. - * @return {Node|undefined} Node. - * @private - */ -ol.format.GML2.prototype.GEOMETRY_NODE_FACTORY_ = function(value, objectStack, opt_nodeName) { - var context = objectStack[objectStack.length - 1]; - var multiSurface = context['multiSurface']; - var surface = context['surface']; - var multiCurve = context['multiCurve']; - var nodeName; - if (!Array.isArray(value)) { - nodeName = /** @type {ol.geom.Geometry} */ (value).getType(); - if (nodeName === 'MultiPolygon' && multiSurface === true) { - nodeName = 'MultiSurface'; - } else if (nodeName === 'Polygon' && surface === true) { - nodeName = 'Surface'; - } else if (nodeName === 'MultiLineString' && multiCurve === true) { - nodeName = 'MultiCurve'; - } - } else { - nodeName = 'Envelope'; - } - return ol.xml.createElementNS('http://www.opengis.net/gml', - nodeName); -}; - - -/** - * @param {Node} node Node. - * @param {ol.Feature} feature Feature. - * @param {Array.<*>} objectStack Node stack. - */ -ol.format.GML2.prototype.writeFeatureElement = function(node, feature, objectStack) { - var fid = feature.getId(); - if (fid) { - node.setAttribute('fid', fid); - } - var context = /** @type {Object} */ (objectStack[objectStack.length - 1]); - var featureNS = context['featureNS']; - var geometryName = feature.getGeometryName(); - if (!context.serializers) { - context.serializers = {}; - context.serializers[featureNS] = {}; - } - var properties = feature.getProperties(); - var keys = [], values = []; - for (var key in properties) { - var value = properties[key]; - if (value !== null) { - keys.push(key); - values.push(value); - if (key == geometryName || value instanceof ol.geom.Geometry) { - if (!(key in context.serializers[featureNS])) { - context.serializers[featureNS][key] = ol.xml.makeChildAppender( - this.writeGeometryElement, this); - } - } else { - if (!(key in context.serializers[featureNS])) { - context.serializers[featureNS][key] = ol.xml.makeChildAppender( - ol.format.XSD.writeStringTextNode); - } - } - } - } - var item = ol.obj.assign({}, context); - item.node = node; - ol.xml.pushSerializeAndPop(/** @type {ol.XmlNodeStackItem} */ - (item), context.serializers, - ol.xml.makeSimpleNodeFactory(undefined, featureNS), - values, - objectStack, keys); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.Geometry|ol.Extent} geometry Geometry. - * @param {Array.<*>} objectStack Node stack. - */ -ol.format.GML2.prototype.writeGeometryElement = function(node, geometry, objectStack) { - var context = /** @type {olx.format.WriteOptions} */ (objectStack[objectStack.length - 1]); - var item = ol.obj.assign({}, context); - item.node = node; - var value; - if (Array.isArray(geometry)) { - if (context.dataProjection) { - value = ol.proj.transformExtent( - geometry, context.featureProjection, context.dataProjection); - } else { - value = geometry; - } - } else { - value = - ol.format.Feature.transformWithOptions(/** @type {ol.geom.Geometry} */ (geometry), true, context); - } - ol.xml.pushSerializeAndPop(/** @type {ol.XmlNodeStackItem} */ - (item), ol.format.GML2.GEOMETRY_SERIALIZERS_, - this.GEOMETRY_NODE_FACTORY_, [value], - objectStack, undefined, this); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.LineString} geometry LineString geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML2.prototype.writeCurveOrLineString_ = function(node, geometry, objectStack) { - var context = objectStack[objectStack.length - 1]; - var srsName = context['srsName']; - if (node.nodeName !== 'LineStringSegment' && srsName) { - node.setAttribute('srsName', srsName); - } - if (node.nodeName === 'LineString' || - node.nodeName === 'LineStringSegment') { - var coordinates = this.createCoordinatesNode_(node.namespaceURI); - node.appendChild(coordinates); - this.writeCoordinates_(coordinates, geometry, objectStack); - } else if (node.nodeName === 'Curve') { - var segments = ol.xml.createElementNS(node.namespaceURI, 'segments'); - node.appendChild(segments); - this.writeCurveSegments_(segments, - geometry, objectStack); - } -}; - - -/** - * @param {string} namespaceURI XML namespace. - * @returns {Node} coordinates node. - * @private - */ -ol.format.GML2.prototype.createCoordinatesNode_ = function(namespaceURI) { - var coordinates = ol.xml.createElementNS(namespaceURI, 'coordinates'); - coordinates.setAttribute('decimal', '.'); - coordinates.setAttribute('cs', ','); - coordinates.setAttribute('ts', ' '); - - return coordinates; -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.LineString|ol.geom.LinearRing} value Geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML2.prototype.writeCoordinates_ = function(node, value, objectStack) { - var context = objectStack[objectStack.length - 1]; - var hasZ = context['hasZ']; - var srsName = context['srsName']; - // only 2d for simple features profile - var points = value.getCoordinates(); - var len = points.length; - var parts = new Array(len); - var point; - for (var i = 0; i < len; ++i) { - point = points[i]; - parts[i] = this.getCoords_(point, srsName, hasZ); - } - ol.format.XSD.writeStringTextNode(node, parts.join(' ')); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.LineString} line LineString geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML2.prototype.writeCurveSegments_ = function(node, line, objectStack) { - var child = ol.xml.createElementNS(node.namespaceURI, - 'LineStringSegment'); - node.appendChild(child); - this.writeCurveOrLineString_(child, line, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.Polygon} geometry Polygon geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML2.prototype.writeSurfaceOrPolygon_ = function(node, geometry, objectStack) { - var context = objectStack[objectStack.length - 1]; - var hasZ = context['hasZ']; - var srsName = context['srsName']; - if (node.nodeName !== 'PolygonPatch' && srsName) { - node.setAttribute('srsName', srsName); - } - if (node.nodeName === 'Polygon' || node.nodeName === 'PolygonPatch') { - var rings = geometry.getLinearRings(); - ol.xml.pushSerializeAndPop( - {node: node, hasZ: hasZ, srsName: srsName}, - ol.format.GML2.RING_SERIALIZERS_, - this.RING_NODE_FACTORY_, - rings, objectStack, undefined, this); - } else if (node.nodeName === 'Surface') { - var patches = ol.xml.createElementNS(node.namespaceURI, 'patches'); - node.appendChild(patches); - this.writeSurfacePatches_( - patches, geometry, objectStack); - } -}; - - -/** - * @param {*} value Value. - * @param {Array.<*>} objectStack Object stack. - * @param {string=} opt_nodeName Node name. - * @return {Node} Node. - * @private - */ -ol.format.GML2.prototype.RING_NODE_FACTORY_ = function(value, objectStack, opt_nodeName) { - var context = objectStack[objectStack.length - 1]; - var parentNode = context.node; - var exteriorWritten = context['exteriorWritten']; - if (exteriorWritten === undefined) { - context['exteriorWritten'] = true; - } - return ol.xml.createElementNS(parentNode.namespaceURI, - exteriorWritten !== undefined ? 'innerBoundaryIs' : 'outerBoundaryIs'); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.Polygon} polygon Polygon geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML2.prototype.writeSurfacePatches_ = function(node, polygon, objectStack) { - var child = ol.xml.createElementNS(node.namespaceURI, 'PolygonPatch'); - node.appendChild(child); - this.writeSurfaceOrPolygon_(child, polygon, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.LinearRing} ring LinearRing geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML2.prototype.writeRing_ = function(node, ring, objectStack) { - var linearRing = ol.xml.createElementNS(node.namespaceURI, 'LinearRing'); - node.appendChild(linearRing); - this.writeLinearRing_(linearRing, ring, objectStack); -}; - - -/** - * @param {Array.<number>} point Point geometry. - * @param {string=} opt_srsName Optional srsName - * @param {boolean=} opt_hasZ whether the geometry has a Z coordinate (is 3D) or not. - * @return {string} The coords string. - * @private - */ -ol.format.GML2.prototype.getCoords_ = function(point, opt_srsName, opt_hasZ) { - var axisOrientation = 'enu'; - if (opt_srsName) { - axisOrientation = ol.proj.get(opt_srsName).getAxisOrientation(); - } - var coords = ((axisOrientation.substr(0, 2) === 'en') ? - point[0] + ',' + point[1] : - point[1] + ',' + point[0]); - if (opt_hasZ) { - // For newly created points, Z can be undefined. - var z = point[2] || 0; - coords += ',' + z; - } - - return coords; -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.MultiLineString} geometry MultiLineString geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML2.prototype.writeMultiCurveOrLineString_ = function(node, geometry, objectStack) { - var context = objectStack[objectStack.length - 1]; - var hasZ = context['hasZ']; - var srsName = context['srsName']; - var curve = context['curve']; - if (srsName) { - node.setAttribute('srsName', srsName); - } - var lines = geometry.getLineStrings(); - ol.xml.pushSerializeAndPop({node: node, hasZ: hasZ, srsName: srsName, curve: curve}, - ol.format.GML2.LINESTRINGORCURVEMEMBER_SERIALIZERS_, - this.MULTIGEOMETRY_MEMBER_NODE_FACTORY_, lines, - objectStack, undefined, this); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.Point} geometry Point geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML2.prototype.writePoint_ = function(node, geometry, objectStack) { - var context = objectStack[objectStack.length - 1]; - var hasZ = context['hasZ']; - var srsName = context['srsName']; - if (srsName) { - node.setAttribute('srsName', srsName); - } - var coordinates = this.createCoordinatesNode_(node.namespaceURI); - node.appendChild(coordinates); - var point = geometry.getCoordinates(); - var coord = this.getCoords_(point, srsName, hasZ); - ol.format.XSD.writeStringTextNode(coordinates, coord); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.MultiPoint} geometry MultiPoint geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML2.prototype.writeMultiPoint_ = function(node, geometry, - objectStack) { - var context = objectStack[objectStack.length - 1]; - var hasZ = context['hasZ']; - var srsName = context['srsName']; - if (srsName) { - node.setAttribute('srsName', srsName); - } - var points = geometry.getPoints(); - ol.xml.pushSerializeAndPop({node: node, hasZ: hasZ, srsName: srsName}, - ol.format.GML2.POINTMEMBER_SERIALIZERS_, - ol.xml.makeSimpleNodeFactory('pointMember'), points, - objectStack, undefined, this); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.Point} point Point geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML2.prototype.writePointMember_ = function(node, point, objectStack) { - var child = ol.xml.createElementNS(node.namespaceURI, 'Point'); - node.appendChild(child); - this.writePoint_(child, point, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.LineString} line LineString geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML2.prototype.writeLineStringOrCurveMember_ = function(node, line, objectStack) { - var child = this.GEOMETRY_NODE_FACTORY_(line, objectStack); - if (child) { - node.appendChild(child); - this.writeCurveOrLineString_(child, line, objectStack); - } -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.LinearRing} geometry LinearRing geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML2.prototype.writeLinearRing_ = function(node, geometry, objectStack) { - var context = objectStack[objectStack.length - 1]; - var srsName = context['srsName']; - if (srsName) { - node.setAttribute('srsName', srsName); - } - var coordinates = this.createCoordinatesNode_(node.namespaceURI); - node.appendChild(coordinates); - this.writeCoordinates_(coordinates, geometry, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.MultiPolygon} geometry MultiPolygon geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML2.prototype.writeMultiSurfaceOrPolygon_ = function(node, geometry, objectStack) { - var context = objectStack[objectStack.length - 1]; - var hasZ = context['hasZ']; - var srsName = context['srsName']; - var surface = context['surface']; - if (srsName) { - node.setAttribute('srsName', srsName); - } - var polygons = geometry.getPolygons(); - ol.xml.pushSerializeAndPop({node: node, hasZ: hasZ, srsName: srsName, surface: surface}, - ol.format.GML2.SURFACEORPOLYGONMEMBER_SERIALIZERS_, - this.MULTIGEOMETRY_MEMBER_NODE_FACTORY_, polygons, - objectStack, undefined, this); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.Polygon} polygon Polygon geometry. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML2.prototype.writeSurfaceOrPolygonMember_ = function(node, polygon, objectStack) { - var child = this.GEOMETRY_NODE_FACTORY_( - polygon, objectStack); - if (child) { - node.appendChild(child); - this.writeSurfaceOrPolygon_(child, polygon, objectStack); - } -}; - - -/** - * @param {Node} node Node. - * @param {ol.Extent} extent Extent. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GML2.prototype.writeEnvelope = function(node, extent, objectStack) { - var context = objectStack[objectStack.length - 1]; - var srsName = context['srsName']; - if (srsName) { - node.setAttribute('srsName', srsName); - } - var keys = ['lowerCorner', 'upperCorner']; - var values = [extent[0] + ' ' + extent[1], extent[2] + ' ' + extent[3]]; - ol.xml.pushSerializeAndPop(/** @type {ol.XmlNodeStackItem} */ - ({node: node}), ol.format.GML2.ENVELOPE_SERIALIZERS_, - ol.xml.OBJECT_PROPERTY_NODE_FACTORY, - values, - objectStack, keys, this); -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GML2.GEOMETRY_SERIALIZERS_ = { - 'http://www.opengis.net/gml': { - 'Curve': ol.xml.makeChildAppender( - ol.format.GML2.prototype.writeCurveOrLineString_), - 'MultiCurve': ol.xml.makeChildAppender( - ol.format.GML2.prototype.writeMultiCurveOrLineString_), - 'Point': ol.xml.makeChildAppender(ol.format.GML2.prototype.writePoint_), - 'MultiPoint': ol.xml.makeChildAppender( - ol.format.GML2.prototype.writeMultiPoint_), - 'LineString': ol.xml.makeChildAppender( - ol.format.GML2.prototype.writeCurveOrLineString_), - 'MultiLineString': ol.xml.makeChildAppender( - ol.format.GML2.prototype.writeMultiCurveOrLineString_), - 'LinearRing': ol.xml.makeChildAppender( - ol.format.GML2.prototype.writeLinearRing_), - 'Polygon': ol.xml.makeChildAppender( - ol.format.GML2.prototype.writeSurfaceOrPolygon_), - 'MultiPolygon': ol.xml.makeChildAppender( - ol.format.GML2.prototype.writeMultiSurfaceOrPolygon_), - 'Surface': ol.xml.makeChildAppender( - ol.format.GML2.prototype.writeSurfaceOrPolygon_), - 'MultiSurface': ol.xml.makeChildAppender( - ol.format.GML2.prototype.writeMultiSurfaceOrPolygon_), - 'Envelope': ol.xml.makeChildAppender( - ol.format.GML2.prototype.writeEnvelope) - } -}; - - -/** - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GML2.RING_SERIALIZERS_ = { - 'http://www.opengis.net/gml': { - 'outerBoundaryIs': ol.xml.makeChildAppender(ol.format.GML2.prototype.writeRing_), - 'innerBoundaryIs': ol.xml.makeChildAppender(ol.format.GML2.prototype.writeRing_) - } -}; - - -/** - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GML2.POINTMEMBER_SERIALIZERS_ = { - 'http://www.opengis.net/gml': { - 'pointMember': ol.xml.makeChildAppender( - ol.format.GML2.prototype.writePointMember_) - } -}; - - -/** - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GML2.LINESTRINGORCURVEMEMBER_SERIALIZERS_ = { - 'http://www.opengis.net/gml': { - 'lineStringMember': ol.xml.makeChildAppender( - ol.format.GML2.prototype.writeLineStringOrCurveMember_), - 'curveMember': ol.xml.makeChildAppender( - ol.format.GML2.prototype.writeLineStringOrCurveMember_) - } -}; - - -/** - * @const - * @param {*} value Value. - * @param {Array.<*>} objectStack Object stack. - * @param {string=} opt_nodeName Node name. - * @return {Node|undefined} Node. - * @private - */ -ol.format.GML2.prototype.MULTIGEOMETRY_MEMBER_NODE_FACTORY_ = function(value, objectStack, opt_nodeName) { - var parentNode = objectStack[objectStack.length - 1].node; - return ol.xml.createElementNS('http://www.opengis.net/gml', - ol.format.GML2.MULTIGEOMETRY_TO_MEMBER_NODENAME_[parentNode.nodeName]); -}; - -/** - * @const - * @type {Object.<string, string>} - * @private - */ -ol.format.GML2.MULTIGEOMETRY_TO_MEMBER_NODENAME_ = { - 'MultiLineString': 'lineStringMember', - 'MultiCurve': 'curveMember', - 'MultiPolygon': 'polygonMember', - 'MultiSurface': 'surfaceMember' -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GML2.SURFACEORPOLYGONMEMBER_SERIALIZERS_ = { - 'http://www.opengis.net/gml': { - 'surfaceMember': ol.xml.makeChildAppender( - ol.format.GML2.prototype.writeSurfaceOrPolygonMember_), - 'polygonMember': ol.xml.makeChildAppender( - ol.format.GML2.prototype.writeSurfaceOrPolygonMember_) - } -}; - - -/** - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GML2.ENVELOPE_SERIALIZERS_ = { - 'http://www.opengis.net/gml': { - 'lowerCorner': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'upperCorner': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode) - } -}; - -goog.provide('ol.format.GPX'); - -goog.require('ol'); -goog.require('ol.Feature'); -goog.require('ol.array'); -goog.require('ol.format.Feature'); -goog.require('ol.format.XMLFeature'); -goog.require('ol.format.XSD'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.LineString'); -goog.require('ol.geom.MultiLineString'); -goog.require('ol.geom.Point'); -goog.require('ol.proj'); -goog.require('ol.xml'); - - -/** - * @classdesc - * Feature format for reading and writing data in the GPX format. - * - * @constructor - * @extends {ol.format.XMLFeature} - * @param {olx.format.GPXOptions=} opt_options Options. - * @api - */ -ol.format.GPX = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - ol.format.XMLFeature.call(this); - - /** - * @inheritDoc - */ - this.defaultDataProjection = ol.proj.get('EPSG:4326'); - - /** - * @type {function(ol.Feature, Node)|undefined} - * @private - */ - this.readExtensions_ = options.readExtensions; -}; -ol.inherits(ol.format.GPX, ol.format.XMLFeature); - - -/** - * @const - * @private - * @type {Array.<string>} - */ -ol.format.GPX.NAMESPACE_URIS_ = [ - null, - 'http://www.topografix.com/GPX/1/0', - 'http://www.topografix.com/GPX/1/1' -]; - - -/** - * @const - * @type {string} - * @private - */ -ol.format.GPX.SCHEMA_LOCATION_ = 'http://www.topografix.com/GPX/1/1 ' + - 'http://www.topografix.com/GPX/1/1/gpx.xsd'; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {ol.LayoutOptions} layoutOptions Layout options. - * @param {Node} node Node. - * @param {Object} values Values. - * @private - * @return {Array.<number>} Flat coordinates. - */ -ol.format.GPX.appendCoordinate_ = function(flatCoordinates, layoutOptions, node, values) { - flatCoordinates.push( - parseFloat(node.getAttribute('lon')), - parseFloat(node.getAttribute('lat'))); - if ('ele' in values) { - flatCoordinates.push(/** @type {number} */ (values['ele'])); - delete values['ele']; - layoutOptions.hasZ = true; - } else { - flatCoordinates.push(0); - } - if ('time' in values) { - flatCoordinates.push(/** @type {number} */ (values['time'])); - delete values['time']; - layoutOptions.hasM = true; - } else { - flatCoordinates.push(0); - } - return flatCoordinates; -}; - - -/** - * Choose GeometryLayout based on flags in layoutOptions and adjust flatCoordinates - * and ends arrays by shrinking them accordingly (removing unused zero entries). - * - * @param {ol.LayoutOptions} layoutOptions Layout options. - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {Array.<number>=} ends Ends. - * @return {ol.geom.GeometryLayout} Layout. - */ -ol.format.GPX.applyLayoutOptions_ = function(layoutOptions, flatCoordinates, ends) { - var layout = ol.geom.GeometryLayout.XY; - var stride = 2; - if (layoutOptions.hasZ && layoutOptions.hasM) { - layout = ol.geom.GeometryLayout.XYZM; - stride = 4; - } else if (layoutOptions.hasZ) { - layout = ol.geom.GeometryLayout.XYZ; - stride = 3; - } else if (layoutOptions.hasM) { - layout = ol.geom.GeometryLayout.XYM; - stride = 3; - } - if (stride !== 4) { - var i, ii; - for (i = 0, ii = flatCoordinates.length / 4; i < ii; i++) { - flatCoordinates[i * stride] = flatCoordinates[i * 4]; - flatCoordinates[i * stride + 1] = flatCoordinates[i * 4 + 1]; - if (layoutOptions.hasZ) { - flatCoordinates[i * stride + 2] = flatCoordinates[i * 4 + 2]; - } - if (layoutOptions.hasM) { - flatCoordinates[i * stride + 2] = flatCoordinates[i * 4 + 3]; - } - } - flatCoordinates.length = flatCoordinates.length / 4 * stride; - if (ends) { - for (i = 0, ii = ends.length; i < ii; i++) { - ends[i] = ends[i] / 4 * stride; - } - } - } - return layout; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GPX.parseLink_ = function(node, objectStack) { - var values = /** @type {Object} */ (objectStack[objectStack.length - 1]); - var href = node.getAttribute('href'); - if (href !== null) { - values['link'] = href; - } - ol.xml.parseNode(ol.format.GPX.LINK_PARSERS_, node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GPX.parseExtensions_ = function(node, objectStack) { - var values = /** @type {Object} */ (objectStack[objectStack.length - 1]); - values['extensionsNode_'] = node; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GPX.parseRtePt_ = function(node, objectStack) { - var values = ol.xml.pushParseAndPop( - {}, ol.format.GPX.RTEPT_PARSERS_, node, objectStack); - if (values) { - var rteValues = /** @type {Object} */ (objectStack[objectStack.length - 1]); - var flatCoordinates = /** @type {Array.<number>} */ - (rteValues['flatCoordinates']); - var layoutOptions = /** @type {ol.LayoutOptions} */ - (rteValues['layoutOptions']); - ol.format.GPX.appendCoordinate_(flatCoordinates, layoutOptions, node, values); - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GPX.parseTrkPt_ = function(node, objectStack) { - var values = ol.xml.pushParseAndPop( - {}, ol.format.GPX.TRKPT_PARSERS_, node, objectStack); - if (values) { - var trkValues = /** @type {Object} */ (objectStack[objectStack.length - 1]); - var flatCoordinates = /** @type {Array.<number>} */ - (trkValues['flatCoordinates']); - var layoutOptions = /** @type {ol.LayoutOptions} */ - (trkValues['layoutOptions']); - ol.format.GPX.appendCoordinate_(flatCoordinates, layoutOptions, node, values); - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GPX.parseTrkSeg_ = function(node, objectStack) { - var values = /** @type {Object} */ (objectStack[objectStack.length - 1]); - ol.xml.parseNode(ol.format.GPX.TRKSEG_PARSERS_, node, objectStack); - var flatCoordinates = /** @type {Array.<number>} */ - (values['flatCoordinates']); - var ends = /** @type {Array.<number>} */ (values['ends']); - ends.push(flatCoordinates.length); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {ol.Feature|undefined} Track. - */ -ol.format.GPX.readRte_ = function(node, objectStack) { - var options = /** @type {olx.format.ReadOptions} */ (objectStack[0]); - var values = ol.xml.pushParseAndPop({ - 'flatCoordinates': [], - 'layoutOptions': {} - }, ol.format.GPX.RTE_PARSERS_, node, objectStack); - if (!values) { - return undefined; - } - var flatCoordinates = /** @type {Array.<number>} */ - (values['flatCoordinates']); - delete values['flatCoordinates']; - var layoutOptions = /** @type {ol.LayoutOptions} */ (values['layoutOptions']); - delete values['layoutOptions']; - var layout = ol.format.GPX.applyLayoutOptions_(layoutOptions, flatCoordinates); - var geometry = new ol.geom.LineString(null); - geometry.setFlatCoordinates(layout, flatCoordinates); - ol.format.Feature.transformWithOptions(geometry, false, options); - var feature = new ol.Feature(geometry); - feature.setProperties(values); - return feature; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {ol.Feature|undefined} Track. - */ -ol.format.GPX.readTrk_ = function(node, objectStack) { - var options = /** @type {olx.format.ReadOptions} */ (objectStack[0]); - var values = ol.xml.pushParseAndPop({ - 'flatCoordinates': [], - 'ends': [], - 'layoutOptions': {} - }, ol.format.GPX.TRK_PARSERS_, node, objectStack); - if (!values) { - return undefined; - } - var flatCoordinates = /** @type {Array.<number>} */ - (values['flatCoordinates']); - delete values['flatCoordinates']; - var ends = /** @type {Array.<number>} */ (values['ends']); - delete values['ends']; - var layoutOptions = /** @type {ol.LayoutOptions} */ (values['layoutOptions']); - delete values['layoutOptions']; - var layout = ol.format.GPX.applyLayoutOptions_(layoutOptions, flatCoordinates, ends); - var geometry = new ol.geom.MultiLineString(null); - geometry.setFlatCoordinates(layout, flatCoordinates, ends); - ol.format.Feature.transformWithOptions(geometry, false, options); - var feature = new ol.Feature(geometry); - feature.setProperties(values); - return feature; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {ol.Feature|undefined} Waypoint. - */ -ol.format.GPX.readWpt_ = function(node, objectStack) { - var options = /** @type {olx.format.ReadOptions} */ (objectStack[0]); - var values = ol.xml.pushParseAndPop( - {}, ol.format.GPX.WPT_PARSERS_, node, objectStack); - if (!values) { - return undefined; - } - var layoutOptions = /** @type {ol.LayoutOptions} */ ({}); - var coordinates = ol.format.GPX.appendCoordinate_([], layoutOptions, node, values); - var layout = ol.format.GPX.applyLayoutOptions_(layoutOptions, coordinates); - var geometry = new ol.geom.Point(coordinates, layout); - ol.format.Feature.transformWithOptions(geometry, false, options); - var feature = new ol.Feature(geometry); - feature.setProperties(values); - return feature; -}; - - -/** - * @const - * @type {Object.<string, function(Node, Array.<*>): (ol.Feature|undefined)>} - * @private - */ -ol.format.GPX.FEATURE_READER_ = { - 'rte': ol.format.GPX.readRte_, - 'trk': ol.format.GPX.readTrk_, - 'wpt': ol.format.GPX.readWpt_ -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GPX.GPX_PARSERS_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, { - 'rte': ol.xml.makeArrayPusher(ol.format.GPX.readRte_), - 'trk': ol.xml.makeArrayPusher(ol.format.GPX.readTrk_), - 'wpt': ol.xml.makeArrayPusher(ol.format.GPX.readWpt_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GPX.LINK_PARSERS_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, { - 'text': - ol.xml.makeObjectPropertySetter(ol.format.XSD.readString, 'linkText'), - 'type': - ol.xml.makeObjectPropertySetter(ol.format.XSD.readString, 'linkType') - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GPX.RTE_PARSERS_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, { - 'name': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'cmt': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'desc': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'src': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'link': ol.format.GPX.parseLink_, - 'number': - ol.xml.makeObjectPropertySetter(ol.format.XSD.readNonNegativeInteger), - 'extensions': ol.format.GPX.parseExtensions_, - 'type': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'rtept': ol.format.GPX.parseRtePt_ - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GPX.RTEPT_PARSERS_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, { - 'ele': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'time': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDateTime) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GPX.TRK_PARSERS_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, { - 'name': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'cmt': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'desc': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'src': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'link': ol.format.GPX.parseLink_, - 'number': - ol.xml.makeObjectPropertySetter(ol.format.XSD.readNonNegativeInteger), - 'type': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'extensions': ol.format.GPX.parseExtensions_, - 'trkseg': ol.format.GPX.parseTrkSeg_ - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GPX.TRKSEG_PARSERS_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, { - 'trkpt': ol.format.GPX.parseTrkPt_ - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GPX.TRKPT_PARSERS_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, { - 'ele': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'time': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDateTime) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.GPX.WPT_PARSERS_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, { - 'ele': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'time': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDateTime), - 'magvar': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'geoidheight': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'name': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'cmt': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'desc': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'src': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'link': ol.format.GPX.parseLink_, - 'sym': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'type': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'fix': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'sat': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readNonNegativeInteger), - 'hdop': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'vdop': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'pdop': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'ageofdgpsdata': - ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'dgpsid': - ol.xml.makeObjectPropertySetter(ol.format.XSD.readNonNegativeInteger), - 'extensions': ol.format.GPX.parseExtensions_ - }); - - -/** - * @param {Array.<ol.Feature>} features List of features. - * @private - */ -ol.format.GPX.prototype.handleReadExtensions_ = function(features) { - if (!features) { - features = []; - } - for (var i = 0, ii = features.length; i < ii; ++i) { - var feature = features[i]; - if (this.readExtensions_) { - var extensionsNode = feature.get('extensionsNode_') || null; - this.readExtensions_(feature, extensionsNode); - } - feature.set('extensionsNode_', undefined); - } -}; - - -/** - * Read the first feature from a GPX source. - * Routes (`<rte>`) are converted into LineString geometries, and tracks (`<trk>`) - * into MultiLineString. Any properties on route and track waypoints are ignored. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {ol.Feature} Feature. - * @api - */ -ol.format.GPX.prototype.readFeature; - - -/** - * @inheritDoc - */ -ol.format.GPX.prototype.readFeatureFromNode = function(node, opt_options) { - if (!ol.array.includes(ol.format.GPX.NAMESPACE_URIS_, node.namespaceURI)) { - return null; - } - var featureReader = ol.format.GPX.FEATURE_READER_[node.localName]; - if (!featureReader) { - return null; - } - var feature = featureReader(node, [this.getReadOptions(node, opt_options)]); - if (!feature) { - return null; - } - this.handleReadExtensions_([feature]); - return feature; -}; - - -/** - * Read all features from a GPX source. - * Routes (`<rte>`) are converted into LineString geometries, and tracks (`<trk>`) - * into MultiLineString. Any properties on route and track waypoints are ignored. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {Array.<ol.Feature>} Features. - * @api - */ -ol.format.GPX.prototype.readFeatures; - - -/** - * @inheritDoc - */ -ol.format.GPX.prototype.readFeaturesFromNode = function(node, opt_options) { - if (!ol.array.includes(ol.format.GPX.NAMESPACE_URIS_, node.namespaceURI)) { - return []; - } - if (node.localName == 'gpx') { - /** @type {Array.<ol.Feature>} */ - var features = ol.xml.pushParseAndPop([], ol.format.GPX.GPX_PARSERS_, - node, [this.getReadOptions(node, opt_options)]); - if (features) { - this.handleReadExtensions_(features); - return features; - } else { - return []; - } - } - return []; -}; - - -/** - * Read the projection from a GPX source. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @return {ol.proj.Projection} Projection. - * @api - */ -ol.format.GPX.prototype.readProjection; - - -/** - * @param {Node} node Node. - * @param {string} value Value for the link's `href` attribute. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.GPX.writeLink_ = function(node, value, objectStack) { - node.setAttribute('href', value); - var context = objectStack[objectStack.length - 1]; - var properties = context['properties']; - var link = [ - properties['linkText'], - properties['linkType'] - ]; - ol.xml.pushSerializeAndPop(/** @type {ol.XmlNodeStackItem} */ ({node: node}), - ol.format.GPX.LINK_SERIALIZERS_, ol.xml.OBJECT_PROPERTY_NODE_FACTORY, - link, objectStack, ol.format.GPX.LINK_SEQUENCE_); -}; - - -/** - * @param {Node} node Node. - * @param {ol.Coordinate} coordinate Coordinate. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GPX.writeWptType_ = function(node, coordinate, objectStack) { - var context = objectStack[objectStack.length - 1]; - var parentNode = context.node; - var namespaceURI = parentNode.namespaceURI; - var properties = context['properties']; - //FIXME Projection handling - ol.xml.setAttributeNS(node, null, 'lat', coordinate[1]); - ol.xml.setAttributeNS(node, null, 'lon', coordinate[0]); - var geometryLayout = context['geometryLayout']; - switch (geometryLayout) { - case ol.geom.GeometryLayout.XYZM: - if (coordinate[3] !== 0) { - properties['time'] = coordinate[3]; - } - // fall through - case ol.geom.GeometryLayout.XYZ: - if (coordinate[2] !== 0) { - properties['ele'] = coordinate[2]; - } - break; - case ol.geom.GeometryLayout.XYM: - if (coordinate[2] !== 0) { - properties['time'] = coordinate[2]; - } - break; - default: - // pass - } - var orderedKeys = (node.nodeName == 'rtept') ? - ol.format.GPX.RTEPT_TYPE_SEQUENCE_[namespaceURI] : - ol.format.GPX.WPT_TYPE_SEQUENCE_[namespaceURI]; - var values = ol.xml.makeSequence(properties, orderedKeys); - ol.xml.pushSerializeAndPop(/** @type {ol.XmlNodeStackItem} */ - ({node: node, 'properties': properties}), - ol.format.GPX.WPT_TYPE_SERIALIZERS_, ol.xml.OBJECT_PROPERTY_NODE_FACTORY, - values, objectStack, orderedKeys); -}; - - -/** - * @param {Node} node Node. - * @param {ol.Feature} feature Feature. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GPX.writeRte_ = function(node, feature, objectStack) { - var options = /** @type {olx.format.WriteOptions} */ (objectStack[0]); - var properties = feature.getProperties(); - var context = {node: node, 'properties': properties}; - var geometry = feature.getGeometry(); - if (geometry) { - geometry = /** @type {ol.geom.LineString} */ - (ol.format.Feature.transformWithOptions(geometry, true, options)); - context['geometryLayout'] = geometry.getLayout(); - properties['rtept'] = geometry.getCoordinates(); - } - var parentNode = objectStack[objectStack.length - 1].node; - var orderedKeys = ol.format.GPX.RTE_SEQUENCE_[parentNode.namespaceURI]; - var values = ol.xml.makeSequence(properties, orderedKeys); - ol.xml.pushSerializeAndPop(context, - ol.format.GPX.RTE_SERIALIZERS_, ol.xml.OBJECT_PROPERTY_NODE_FACTORY, - values, objectStack, orderedKeys); -}; - - -/** - * @param {Node} node Node. - * @param {ol.Feature} feature Feature. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GPX.writeTrk_ = function(node, feature, objectStack) { - var options = /** @type {olx.format.WriteOptions} */ (objectStack[0]); - var properties = feature.getProperties(); - /** @type {ol.XmlNodeStackItem} */ - var context = {node: node, 'properties': properties}; - var geometry = feature.getGeometry(); - if (geometry) { - geometry = /** @type {ol.geom.MultiLineString} */ - (ol.format.Feature.transformWithOptions(geometry, true, options)); - properties['trkseg'] = geometry.getLineStrings(); - } - var parentNode = objectStack[objectStack.length - 1].node; - var orderedKeys = ol.format.GPX.TRK_SEQUENCE_[parentNode.namespaceURI]; - var values = ol.xml.makeSequence(properties, orderedKeys); - ol.xml.pushSerializeAndPop(context, - ol.format.GPX.TRK_SERIALIZERS_, ol.xml.OBJECT_PROPERTY_NODE_FACTORY, - values, objectStack, orderedKeys); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.LineString} lineString LineString. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GPX.writeTrkSeg_ = function(node, lineString, objectStack) { - /** @type {ol.XmlNodeStackItem} */ - var context = {node: node, 'geometryLayout': lineString.getLayout(), - 'properties': {}}; - ol.xml.pushSerializeAndPop(context, - ol.format.GPX.TRKSEG_SERIALIZERS_, ol.format.GPX.TRKSEG_NODE_FACTORY_, - lineString.getCoordinates(), objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {ol.Feature} feature Feature. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.GPX.writeWpt_ = function(node, feature, objectStack) { - var options = /** @type {olx.format.WriteOptions} */ (objectStack[0]); - var context = objectStack[objectStack.length - 1]; - context['properties'] = feature.getProperties(); - var geometry = feature.getGeometry(); - if (geometry) { - geometry = /** @type {ol.geom.Point} */ - (ol.format.Feature.transformWithOptions(geometry, true, options)); - context['geometryLayout'] = geometry.getLayout(); - ol.format.GPX.writeWptType_(node, geometry.getCoordinates(), objectStack); - } -}; - - -/** - * @const - * @type {Array.<string>} - * @private - */ -ol.format.GPX.LINK_SEQUENCE_ = ['text', 'type']; - - -/** - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GPX.LINK_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, { - 'text': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'type': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode) - }); - - -/** - * @const - * @type {Object.<string, Array.<string>>} - * @private - */ -ol.format.GPX.RTE_SEQUENCE_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, [ - 'name', 'cmt', 'desc', 'src', 'link', 'number', 'type', 'rtept' - ]); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GPX.RTE_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, { - 'name': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'cmt': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'desc': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'src': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'link': ol.xml.makeChildAppender(ol.format.GPX.writeLink_), - 'number': ol.xml.makeChildAppender( - ol.format.XSD.writeNonNegativeIntegerTextNode), - 'type': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'rtept': ol.xml.makeArraySerializer(ol.xml.makeChildAppender( - ol.format.GPX.writeWptType_)) - }); - - -/** - * @const - * @type {Object.<string, Array.<string>>} - * @private - */ -ol.format.GPX.RTEPT_TYPE_SEQUENCE_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, [ - 'ele', 'time' - ]); - - -/** - * @const - * @type {Object.<string, Array.<string>>} - * @private - */ -ol.format.GPX.TRK_SEQUENCE_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, [ - 'name', 'cmt', 'desc', 'src', 'link', 'number', 'type', 'trkseg' - ]); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GPX.TRK_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, { - 'name': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'cmt': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'desc': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'src': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'link': ol.xml.makeChildAppender(ol.format.GPX.writeLink_), - 'number': ol.xml.makeChildAppender( - ol.format.XSD.writeNonNegativeIntegerTextNode), - 'type': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'trkseg': ol.xml.makeArraySerializer(ol.xml.makeChildAppender( - ol.format.GPX.writeTrkSeg_)) - }); - - -/** - * @const - * @type {function(*, Array.<*>, string=): (Node|undefined)} - * @private - */ -ol.format.GPX.TRKSEG_NODE_FACTORY_ = ol.xml.makeSimpleNodeFactory('trkpt'); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GPX.TRKSEG_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, { - 'trkpt': ol.xml.makeChildAppender(ol.format.GPX.writeWptType_) - }); - - -/** - * @const - * @type {Object.<string, Array.<string>>} - * @private - */ -ol.format.GPX.WPT_TYPE_SEQUENCE_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, [ - 'ele', 'time', 'magvar', 'geoidheight', 'name', 'cmt', 'desc', 'src', - 'link', 'sym', 'type', 'fix', 'sat', 'hdop', 'vdop', 'pdop', - 'ageofdgpsdata', 'dgpsid' - ]); - - -/** - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GPX.WPT_TYPE_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, { - 'ele': ol.xml.makeChildAppender(ol.format.XSD.writeDecimalTextNode), - 'time': ol.xml.makeChildAppender(ol.format.XSD.writeDateTimeTextNode), - 'magvar': ol.xml.makeChildAppender(ol.format.XSD.writeDecimalTextNode), - 'geoidheight': ol.xml.makeChildAppender( - ol.format.XSD.writeDecimalTextNode), - 'name': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'cmt': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'desc': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'src': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'link': ol.xml.makeChildAppender(ol.format.GPX.writeLink_), - 'sym': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'type': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'fix': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'sat': ol.xml.makeChildAppender( - ol.format.XSD.writeNonNegativeIntegerTextNode), - 'hdop': ol.xml.makeChildAppender(ol.format.XSD.writeDecimalTextNode), - 'vdop': ol.xml.makeChildAppender(ol.format.XSD.writeDecimalTextNode), - 'pdop': ol.xml.makeChildAppender(ol.format.XSD.writeDecimalTextNode), - 'ageofdgpsdata': ol.xml.makeChildAppender( - ol.format.XSD.writeDecimalTextNode), - 'dgpsid': ol.xml.makeChildAppender( - ol.format.XSD.writeNonNegativeIntegerTextNode) - }); - - -/** - * @const - * @type {Object.<string, string>} - * @private - */ -ol.format.GPX.GEOMETRY_TYPE_TO_NODENAME_ = { - 'Point': 'wpt', - 'LineString': 'rte', - 'MultiLineString': 'trk' -}; - - -/** - * @const - * @param {*} value Value. - * @param {Array.<*>} objectStack Object stack. - * @param {string=} opt_nodeName Node name. - * @return {Node|undefined} Node. - * @private - */ -ol.format.GPX.GPX_NODE_FACTORY_ = function(value, objectStack, opt_nodeName) { - var geometry = /** @type {ol.Feature} */ (value).getGeometry(); - if (geometry) { - var nodeName = ol.format.GPX.GEOMETRY_TYPE_TO_NODENAME_[geometry.getType()]; - if (nodeName) { - var parentNode = objectStack[objectStack.length - 1].node; - return ol.xml.createElementNS(parentNode.namespaceURI, nodeName); - } - } -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.GPX.GPX_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.GPX.NAMESPACE_URIS_, { - 'rte': ol.xml.makeChildAppender(ol.format.GPX.writeRte_), - 'trk': ol.xml.makeChildAppender(ol.format.GPX.writeTrk_), - 'wpt': ol.xml.makeChildAppender(ol.format.GPX.writeWpt_) - }); - - -/** - * Encode an array of features in the GPX format. - * LineString geometries are output as routes (`<rte>`), and MultiLineString - * as tracks (`<trk>`). - * - * @function - * @param {Array.<ol.Feature>} features Features. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {string} Result. - * @api - */ -ol.format.GPX.prototype.writeFeatures; - - -/** - * Encode an array of features in the GPX format as an XML node. - * LineString geometries are output as routes (`<rte>`), and MultiLineString - * as tracks (`<trk>`). - * - * @param {Array.<ol.Feature>} features Features. - * @param {olx.format.WriteOptions=} opt_options Options. - * @return {Node} Node. - * @override - * @api - */ -ol.format.GPX.prototype.writeFeaturesNode = function(features, opt_options) { - opt_options = this.adaptOptions(opt_options); - //FIXME Serialize metadata - var gpx = ol.xml.createElementNS('http://www.topografix.com/GPX/1/1', 'gpx'); - var xmlnsUri = 'http://www.w3.org/2000/xmlns/'; - var xmlSchemaInstanceUri = 'http://www.w3.org/2001/XMLSchema-instance'; - ol.xml.setAttributeNS(gpx, xmlnsUri, 'xmlns:xsi', xmlSchemaInstanceUri); - ol.xml.setAttributeNS(gpx, xmlSchemaInstanceUri, 'xsi:schemaLocation', - ol.format.GPX.SCHEMA_LOCATION_); - gpx.setAttribute('version', '1.1'); - gpx.setAttribute('creator', 'OpenLayers'); - - ol.xml.pushSerializeAndPop(/** @type {ol.XmlNodeStackItem} */ - ({node: gpx}), ol.format.GPX.GPX_SERIALIZERS_, - ol.format.GPX.GPX_NODE_FACTORY_, features, [opt_options]); - return gpx; -}; - -goog.provide('ol.format.IGCZ'); - -/** - * IGC altitude/z. One of 'barometric', 'gps', 'none'. - * @enum {string} - */ -ol.format.IGCZ = { - BAROMETRIC: 'barometric', - GPS: 'gps', - NONE: 'none' -}; - -goog.provide('ol.format.TextFeature'); - -goog.require('ol'); -goog.require('ol.format.Feature'); -goog.require('ol.format.FormatType'); - - -/** - * @classdesc - * Abstract base class; normally only used for creating subclasses and not - * instantiated in apps. - * Base class for text feature formats. - * - * @constructor - * @abstract - * @extends {ol.format.Feature} - */ -ol.format.TextFeature = function() { - ol.format.Feature.call(this); -}; -ol.inherits(ol.format.TextFeature, ol.format.Feature); - - -/** - * @param {Document|Node|Object|string} source Source. - * @private - * @return {string} Text. - */ -ol.format.TextFeature.prototype.getText_ = function(source) { - if (typeof source === 'string') { - return source; - } else { - return ''; - } -}; - - -/** - * @inheritDoc - */ -ol.format.TextFeature.prototype.getType = function() { - return ol.format.FormatType.TEXT; -}; - - -/** - * @inheritDoc - */ -ol.format.TextFeature.prototype.readFeature = function(source, opt_options) { - return this.readFeatureFromText( - this.getText_(source), this.adaptOptions(opt_options)); -}; - - -/** - * @abstract - * @param {string} text Text. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @protected - * @return {ol.Feature} Feature. - */ -ol.format.TextFeature.prototype.readFeatureFromText = function(text, opt_options) {}; - - -/** - * @inheritDoc - */ -ol.format.TextFeature.prototype.readFeatures = function(source, opt_options) { - return this.readFeaturesFromText( - this.getText_(source), this.adaptOptions(opt_options)); -}; - - -/** - * @abstract - * @param {string} text Text. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @protected - * @return {Array.<ol.Feature>} Features. - */ -ol.format.TextFeature.prototype.readFeaturesFromText = function(text, opt_options) {}; - - -/** - * @inheritDoc - */ -ol.format.TextFeature.prototype.readGeometry = function(source, opt_options) { - return this.readGeometryFromText( - this.getText_(source), this.adaptOptions(opt_options)); -}; - - -/** - * @abstract - * @param {string} text Text. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @protected - * @return {ol.geom.Geometry} Geometry. - */ -ol.format.TextFeature.prototype.readGeometryFromText = function(text, opt_options) {}; - - -/** - * @inheritDoc - */ -ol.format.TextFeature.prototype.readProjection = function(source) { - return this.readProjectionFromText(this.getText_(source)); -}; - - -/** - * @param {string} text Text. - * @protected - * @return {ol.proj.Projection} Projection. - */ -ol.format.TextFeature.prototype.readProjectionFromText = function(text) { - return this.defaultDataProjection; -}; - - -/** - * @inheritDoc - */ -ol.format.TextFeature.prototype.writeFeature = function(feature, opt_options) { - return this.writeFeatureText(feature, this.adaptOptions(opt_options)); -}; - - -/** - * @abstract - * @param {ol.Feature} feature Features. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @protected - * @return {string} Text. - */ -ol.format.TextFeature.prototype.writeFeatureText = function(feature, opt_options) {}; - - -/** - * @inheritDoc - */ -ol.format.TextFeature.prototype.writeFeatures = function( - features, opt_options) { - return this.writeFeaturesText(features, this.adaptOptions(opt_options)); -}; - - -/** - * @abstract - * @param {Array.<ol.Feature>} features Features. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @protected - * @return {string} Text. - */ -ol.format.TextFeature.prototype.writeFeaturesText = function(features, opt_options) {}; - - -/** - * @inheritDoc - */ -ol.format.TextFeature.prototype.writeGeometry = function( - geometry, opt_options) { - return this.writeGeometryText(geometry, this.adaptOptions(opt_options)); -}; - - -/** - * @abstract - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @protected - * @return {string} Text. - */ -ol.format.TextFeature.prototype.writeGeometryText = function(geometry, opt_options) {}; - -goog.provide('ol.format.IGC'); - -goog.require('ol'); -goog.require('ol.Feature'); -goog.require('ol.format.Feature'); -goog.require('ol.format.IGCZ'); -goog.require('ol.format.TextFeature'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.LineString'); -goog.require('ol.proj'); - - -/** - * @classdesc - * Feature format for `*.igc` flight recording files. - * - * @constructor - * @extends {ol.format.TextFeature} - * @param {olx.format.IGCOptions=} opt_options Options. - * @api - */ -ol.format.IGC = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - ol.format.TextFeature.call(this); - - /** - * @inheritDoc - */ - this.defaultDataProjection = ol.proj.get('EPSG:4326'); - - /** - * @private - * @type {ol.format.IGCZ} - */ - this.altitudeMode_ = options.altitudeMode ? - options.altitudeMode : ol.format.IGCZ.NONE; - -}; -ol.inherits(ol.format.IGC, ol.format.TextFeature); - - -/** - * @const - * @type {RegExp} - * @private - */ -ol.format.IGC.B_RECORD_RE_ = - /^B(\d{2})(\d{2})(\d{2})(\d{2})(\d{5})([NS])(\d{3})(\d{5})([EW])([AV])(\d{5})(\d{5})/; - - -/** - * @const - * @type {RegExp} - * @private - */ -ol.format.IGC.H_RECORD_RE_ = /^H.([A-Z]{3}).*?:(.*)/; - - -/** - * @const - * @type {RegExp} - * @private - */ -ol.format.IGC.HFDTE_RECORD_RE_ = /^HFDTE(\d{2})(\d{2})(\d{2})/; - - -/** - * A regular expression matching the newline characters `\r\n`, `\r` and `\n`. - * - * @const - * @type {RegExp} - * @private - */ -ol.format.IGC.NEWLINE_RE_ = /\r\n|\r|\n/; - - -/** - * Read the feature from the IGC source. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {ol.Feature} Feature. - * @api - */ -ol.format.IGC.prototype.readFeature; - - -/** - * @inheritDoc - */ -ol.format.IGC.prototype.readFeatureFromText = function(text, opt_options) { - var altitudeMode = this.altitudeMode_; - var lines = text.split(ol.format.IGC.NEWLINE_RE_); - /** @type {Object.<string, string>} */ - var properties = {}; - var flatCoordinates = []; - var year = 2000; - var month = 0; - var day = 1; - var lastDateTime = -1; - var i, ii; - for (i = 0, ii = lines.length; i < ii; ++i) { - var line = lines[i]; - var m; - if (line.charAt(0) == 'B') { - m = ol.format.IGC.B_RECORD_RE_.exec(line); - if (m) { - var hour = parseInt(m[1], 10); - var minute = parseInt(m[2], 10); - var second = parseInt(m[3], 10); - var y = parseInt(m[4], 10) + parseInt(m[5], 10) / 60000; - if (m[6] == 'S') { - y = -y; - } - var x = parseInt(m[7], 10) + parseInt(m[8], 10) / 60000; - if (m[9] == 'W') { - x = -x; - } - flatCoordinates.push(x, y); - if (altitudeMode != ol.format.IGCZ.NONE) { - var z; - if (altitudeMode == ol.format.IGCZ.GPS) { - z = parseInt(m[11], 10); - } else if (altitudeMode == ol.format.IGCZ.BAROMETRIC) { - z = parseInt(m[12], 10); - } else { - z = 0; - } - flatCoordinates.push(z); - } - var dateTime = Date.UTC(year, month, day, hour, minute, second); - // Detect UTC midnight wrap around. - if (dateTime < lastDateTime) { - dateTime = Date.UTC(year, month, day + 1, hour, minute, second); - } - flatCoordinates.push(dateTime / 1000); - lastDateTime = dateTime; - } - } else if (line.charAt(0) == 'H') { - m = ol.format.IGC.HFDTE_RECORD_RE_.exec(line); - if (m) { - day = parseInt(m[1], 10); - month = parseInt(m[2], 10) - 1; - year = 2000 + parseInt(m[3], 10); - } else { - m = ol.format.IGC.H_RECORD_RE_.exec(line); - if (m) { - properties[m[1]] = m[2].trim(); - } - } - } - } - if (flatCoordinates.length === 0) { - return null; - } - var lineString = new ol.geom.LineString(null); - var layout = altitudeMode == ol.format.IGCZ.NONE ? - ol.geom.GeometryLayout.XYM : ol.geom.GeometryLayout.XYZM; - lineString.setFlatCoordinates(layout, flatCoordinates); - var feature = new ol.Feature(ol.format.Feature.transformWithOptions( - lineString, false, opt_options)); - feature.setProperties(properties); - return feature; -}; - - -/** - * Read the feature from the source. As IGC sources contain a single - * feature, this will return the feature in an array. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {Array.<ol.Feature>} Features. - * @api - */ -ol.format.IGC.prototype.readFeatures; - - -/** - * @inheritDoc - */ -ol.format.IGC.prototype.readFeaturesFromText = function(text, opt_options) { - var feature = this.readFeatureFromText(text, opt_options); - if (feature) { - return [feature]; - } else { - return []; - } -}; - - -/** - * Read the projection from the IGC source. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @return {ol.proj.Projection} Projection. - * @api - */ -ol.format.IGC.prototype.readProjection; - - -/** - * Not implemented. - * @inheritDoc - */ -ol.format.IGC.prototype.writeFeatureText = function(feature, opt_options) {}; - - -/** - * Not implemented. - * @inheritDoc - */ -ol.format.IGC.prototype.writeFeaturesText = function(features, opt_options) {}; - - -/** - * Not implemented. - * @inheritDoc - */ -ol.format.IGC.prototype.writeGeometryText = function(geometry, opt_options) {}; - - -/** - * Not implemented. - * @inheritDoc - */ -ol.format.IGC.prototype.readGeometryFromText = function(text, opt_options) {}; - -goog.provide('ol.style.IconAnchorUnits'); - -/** - * Icon anchor units. One of 'fraction', 'pixels'. - * @enum {string} - */ -ol.style.IconAnchorUnits = { - FRACTION: 'fraction', - PIXELS: 'pixels' -}; - -goog.provide('ol.style.IconImage'); - -goog.require('ol'); -goog.require('ol.dom'); -goog.require('ol.events'); -goog.require('ol.events.EventTarget'); -goog.require('ol.events.EventType'); -goog.require('ol.ImageState'); -goog.require('ol.style'); - - -/** - * @constructor - * @param {Image|HTMLCanvasElement} image Image. - * @param {string|undefined} src Src. - * @param {ol.Size} size Size. - * @param {?string} crossOrigin Cross origin. - * @param {ol.ImageState} imageState Image state. - * @param {ol.Color} color Color. - * @extends {ol.events.EventTarget} - */ -ol.style.IconImage = function(image, src, size, crossOrigin, imageState, - color) { - - ol.events.EventTarget.call(this); - - /** - * @private - * @type {Image|HTMLCanvasElement} - */ - this.hitDetectionImage_ = null; - - /** - * @private - * @type {Image|HTMLCanvasElement} - */ - this.image_ = !image ? new Image() : image; - - if (crossOrigin !== null) { - this.image_.crossOrigin = crossOrigin; - } - - /** - * @private - * @type {HTMLCanvasElement} - */ - this.canvas_ = color ? - /** @type {HTMLCanvasElement} */ (document.createElement('CANVAS')) : - null; - - /** - * @private - * @type {ol.Color} - */ - this.color_ = color; - - /** - * @private - * @type {Array.<ol.EventsKey>} - */ - this.imageListenerKeys_ = null; - - /** - * @private - * @type {ol.ImageState} - */ - this.imageState_ = imageState; - - /** - * @private - * @type {ol.Size} - */ - this.size_ = size; - - /** - * @private - * @type {string|undefined} - */ - this.src_ = src; - - /** - * @private - * @type {boolean} - */ - this.tainting_ = false; - if (this.imageState_ == ol.ImageState.LOADED) { - this.determineTainting_(); - } - -}; -ol.inherits(ol.style.IconImage, ol.events.EventTarget); - - -/** - * @param {Image|HTMLCanvasElement} image Image. - * @param {string} src Src. - * @param {ol.Size} size Size. - * @param {?string} crossOrigin Cross origin. - * @param {ol.ImageState} imageState Image state. - * @param {ol.Color} color Color. - * @return {ol.style.IconImage} Icon image. - */ -ol.style.IconImage.get = function(image, src, size, crossOrigin, imageState, - color) { - var iconImageCache = ol.style.iconImageCache; - var iconImage = iconImageCache.get(src, crossOrigin, color); - if (!iconImage) { - iconImage = new ol.style.IconImage( - image, src, size, crossOrigin, imageState, color); - iconImageCache.set(src, crossOrigin, color, iconImage); - } - return iconImage; -}; - - -/** - * @private - */ -ol.style.IconImage.prototype.determineTainting_ = function() { - var context = ol.dom.createCanvasContext2D(1, 1); - try { - context.drawImage(this.image_, 0, 0); - context.getImageData(0, 0, 1, 1); - } catch (e) { - this.tainting_ = true; - } -}; - - -/** - * @private - */ -ol.style.IconImage.prototype.dispatchChangeEvent_ = function() { - this.dispatchEvent(ol.events.EventType.CHANGE); -}; - - -/** - * @private - */ -ol.style.IconImage.prototype.handleImageError_ = function() { - this.imageState_ = ol.ImageState.ERROR; - this.unlistenImage_(); - this.dispatchChangeEvent_(); -}; - - -/** - * @private - */ -ol.style.IconImage.prototype.handleImageLoad_ = function() { - this.imageState_ = ol.ImageState.LOADED; - if (this.size_) { - this.image_.width = this.size_[0]; - this.image_.height = this.size_[1]; - } - this.size_ = [this.image_.width, this.image_.height]; - this.unlistenImage_(); - this.determineTainting_(); - this.replaceColor_(); - this.dispatchChangeEvent_(); -}; - - -/** - * @param {number} pixelRatio Pixel ratio. - * @return {Image|HTMLCanvasElement} Image or Canvas element. - */ -ol.style.IconImage.prototype.getImage = function(pixelRatio) { - return this.canvas_ ? this.canvas_ : this.image_; -}; - - -/** - * @return {ol.ImageState} Image state. - */ -ol.style.IconImage.prototype.getImageState = function() { - return this.imageState_; -}; - - -/** - * @param {number} pixelRatio Pixel ratio. - * @return {Image|HTMLCanvasElement} Image element. - */ -ol.style.IconImage.prototype.getHitDetectionImage = function(pixelRatio) { - if (!this.hitDetectionImage_) { - if (this.tainting_) { - var width = this.size_[0]; - var height = this.size_[1]; - var context = ol.dom.createCanvasContext2D(width, height); - context.fillRect(0, 0, width, height); - this.hitDetectionImage_ = context.canvas; - } else { - this.hitDetectionImage_ = this.image_; - } - } - return this.hitDetectionImage_; -}; - - -/** - * @return {ol.Size} Image size. - */ -ol.style.IconImage.prototype.getSize = function() { - return this.size_; -}; - - -/** - * @return {string|undefined} Image src. - */ -ol.style.IconImage.prototype.getSrc = function() { - return this.src_; -}; - - -/** - * Load not yet loaded URI. - */ -ol.style.IconImage.prototype.load = function() { - if (this.imageState_ == ol.ImageState.IDLE) { - this.imageState_ = ol.ImageState.LOADING; - this.imageListenerKeys_ = [ - ol.events.listenOnce(this.image_, ol.events.EventType.ERROR, - this.handleImageError_, this), - ol.events.listenOnce(this.image_, ol.events.EventType.LOAD, - this.handleImageLoad_, this) - ]; - try { - this.image_.src = this.src_; - } catch (e) { - this.handleImageError_(); - } - } -}; - - -/** - * @private - */ -ol.style.IconImage.prototype.replaceColor_ = function() { - if (this.tainting_ || this.color_ === null) { - return; - } - - this.canvas_.width = this.image_.width; - this.canvas_.height = this.image_.height; - - var ctx = this.canvas_.getContext('2d'); - ctx.drawImage(this.image_, 0, 0); - - var imgData = ctx.getImageData(0, 0, this.image_.width, this.image_.height); - var data = imgData.data; - var r = this.color_[0] / 255.0; - var g = this.color_[1] / 255.0; - var b = this.color_[2] / 255.0; - - for (var i = 0, ii = data.length; i < ii; i += 4) { - data[i] *= r; - data[i + 1] *= g; - data[i + 2] *= b; - } - ctx.putImageData(imgData, 0, 0); -}; - - -/** - * Discards event handlers which listen for load completion or errors. - * - * @private - */ -ol.style.IconImage.prototype.unlistenImage_ = function() { - this.imageListenerKeys_.forEach(ol.events.unlistenByKey); - this.imageListenerKeys_ = null; -}; - -goog.provide('ol.style.IconOrigin'); - -/** - * Icon origin. One of 'bottom-left', 'bottom-right', 'top-left', 'top-right'. - * @enum {string} - */ -ol.style.IconOrigin = { - BOTTOM_LEFT: 'bottom-left', - BOTTOM_RIGHT: 'bottom-right', - TOP_LEFT: 'top-left', - TOP_RIGHT: 'top-right' -}; - -goog.provide('ol.style.Icon'); - -goog.require('ol'); -goog.require('ol.ImageState'); -goog.require('ol.asserts'); -goog.require('ol.color'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.style.IconAnchorUnits'); -goog.require('ol.style.IconImage'); -goog.require('ol.style.IconOrigin'); -goog.require('ol.style.Image'); - - -/** - * @classdesc - * Set icon style for vector features. - * - * @constructor - * @param {olx.style.IconOptions=} opt_options Options. - * @extends {ol.style.Image} - * @api - */ -ol.style.Icon = function(opt_options) { - - var options = opt_options || {}; - - /** - * @private - * @type {Array.<number>} - */ - this.anchor_ = options.anchor !== undefined ? options.anchor : [0.5, 0.5]; - - /** - * @private - * @type {Array.<number>} - */ - this.normalizedAnchor_ = null; - - /** - * @private - * @type {ol.style.IconOrigin} - */ - this.anchorOrigin_ = options.anchorOrigin !== undefined ? - options.anchorOrigin : ol.style.IconOrigin.TOP_LEFT; - - /** - * @private - * @type {ol.style.IconAnchorUnits} - */ - this.anchorXUnits_ = options.anchorXUnits !== undefined ? - options.anchorXUnits : ol.style.IconAnchorUnits.FRACTION; - - /** - * @private - * @type {ol.style.IconAnchorUnits} - */ - this.anchorYUnits_ = options.anchorYUnits !== undefined ? - options.anchorYUnits : ol.style.IconAnchorUnits.FRACTION; - - /** - * @private - * @type {?string} - */ - this.crossOrigin_ = - options.crossOrigin !== undefined ? options.crossOrigin : null; - - /** - * @type {Image|HTMLCanvasElement} - */ - var image = options.img !== undefined ? options.img : null; - - /** - * @type {ol.Size} - */ - var imgSize = options.imgSize !== undefined ? options.imgSize : null; - - /** - * @type {string|undefined} - */ - var src = options.src; - - ol.asserts.assert(!(src !== undefined && image), - 4); // `image` and `src` cannot be provided at the same time - ol.asserts.assert(!image || (image && imgSize), - 5); // `imgSize` must be set when `image` is provided - - if ((src === undefined || src.length === 0) && image) { - src = image.src || ol.getUid(image).toString(); - } - ol.asserts.assert(src !== undefined && src.length > 0, - 6); // A defined and non-empty `src` or `image` must be provided - - /** - * @type {ol.ImageState} - */ - var imageState = options.src !== undefined ? - ol.ImageState.IDLE : ol.ImageState.LOADED; - - /** - * @private - * @type {ol.Color} - */ - this.color_ = options.color !== undefined ? ol.color.asArray(options.color) : - null; - - /** - * @private - * @type {ol.style.IconImage} - */ - this.iconImage_ = ol.style.IconImage.get( - image, /** @type {string} */ (src), imgSize, this.crossOrigin_, imageState, this.color_); - - /** - * @private - * @type {Array.<number>} - */ - this.offset_ = options.offset !== undefined ? options.offset : [0, 0]; - - /** - * @private - * @type {ol.style.IconOrigin} - */ - this.offsetOrigin_ = options.offsetOrigin !== undefined ? - options.offsetOrigin : ol.style.IconOrigin.TOP_LEFT; - - /** - * @private - * @type {Array.<number>} - */ - this.origin_ = null; - - /** - * @private - * @type {ol.Size} - */ - this.size_ = options.size !== undefined ? options.size : null; - - /** - * @type {number} - */ - var opacity = options.opacity !== undefined ? options.opacity : 1; - - /** - * @type {boolean} - */ - var rotateWithView = options.rotateWithView !== undefined ? - options.rotateWithView : false; - - /** - * @type {number} - */ - var rotation = options.rotation !== undefined ? options.rotation : 0; - - /** - * @type {number} - */ - var scale = options.scale !== undefined ? options.scale : 1; - - /** - * @type {boolean} - */ - var snapToPixel = options.snapToPixel !== undefined ? - options.snapToPixel : true; - - ol.style.Image.call(this, { - opacity: opacity, - rotation: rotation, - scale: scale, - snapToPixel: snapToPixel, - rotateWithView: rotateWithView - }); - -}; -ol.inherits(ol.style.Icon, ol.style.Image); - - -/** - * Clones the style. The underlying Image/HTMLCanvasElement is not cloned. - * @return {ol.style.Icon} The cloned style. - * @api - */ -ol.style.Icon.prototype.clone = function() { - return new ol.style.Icon({ - anchor: this.anchor_.slice(), - anchorOrigin: this.anchorOrigin_, - anchorXUnits: this.anchorXUnits_, - anchorYUnits: this.anchorYUnits_, - crossOrigin: this.crossOrigin_, - color: (this.color_ && this.color_.slice) ? this.color_.slice() : this.color_ || undefined, - src: this.getSrc(), - offset: this.offset_.slice(), - offsetOrigin: this.offsetOrigin_, - size: this.size_ !== null ? this.size_.slice() : undefined, - opacity: this.getOpacity(), - scale: this.getScale(), - snapToPixel: this.getSnapToPixel(), - rotation: this.getRotation(), - rotateWithView: this.getRotateWithView() - }); -}; - - -/** - * @inheritDoc - * @api - */ -ol.style.Icon.prototype.getAnchor = function() { - if (this.normalizedAnchor_) { - return this.normalizedAnchor_; - } - var anchor = this.anchor_; - var size = this.getSize(); - if (this.anchorXUnits_ == ol.style.IconAnchorUnits.FRACTION || - this.anchorYUnits_ == ol.style.IconAnchorUnits.FRACTION) { - if (!size) { - return null; - } - anchor = this.anchor_.slice(); - if (this.anchorXUnits_ == ol.style.IconAnchorUnits.FRACTION) { - anchor[0] *= size[0]; - } - if (this.anchorYUnits_ == ol.style.IconAnchorUnits.FRACTION) { - anchor[1] *= size[1]; - } - } - - if (this.anchorOrigin_ != ol.style.IconOrigin.TOP_LEFT) { - if (!size) { - return null; - } - if (anchor === this.anchor_) { - anchor = this.anchor_.slice(); - } - if (this.anchorOrigin_ == ol.style.IconOrigin.TOP_RIGHT || - this.anchorOrigin_ == ol.style.IconOrigin.BOTTOM_RIGHT) { - anchor[0] = -anchor[0] + size[0]; - } - if (this.anchorOrigin_ == ol.style.IconOrigin.BOTTOM_LEFT || - this.anchorOrigin_ == ol.style.IconOrigin.BOTTOM_RIGHT) { - anchor[1] = -anchor[1] + size[1]; - } - } - this.normalizedAnchor_ = anchor; - return this.normalizedAnchor_; -}; - - -/** - * Get the icon color. - * @return {ol.Color} Color. - * @api - */ -ol.style.Icon.prototype.getColor = function() { - return this.color_; -}; - - -/** - * Get the image icon. - * @param {number} pixelRatio Pixel ratio. - * @return {Image|HTMLCanvasElement} Image or Canvas element. - * @override - * @api - */ -ol.style.Icon.prototype.getImage = function(pixelRatio) { - return this.iconImage_.getImage(pixelRatio); -}; - - -/** - * @override - */ -ol.style.Icon.prototype.getImageSize = function() { - return this.iconImage_.getSize(); -}; - - -/** - * @override - */ -ol.style.Icon.prototype.getHitDetectionImageSize = function() { - return this.getImageSize(); -}; - - -/** - * @override - */ -ol.style.Icon.prototype.getImageState = function() { - return this.iconImage_.getImageState(); -}; - - -/** - * @override - */ -ol.style.Icon.prototype.getHitDetectionImage = function(pixelRatio) { - return this.iconImage_.getHitDetectionImage(pixelRatio); -}; - - -/** - * @inheritDoc - * @api - */ -ol.style.Icon.prototype.getOrigin = function() { - if (this.origin_) { - return this.origin_; - } - var offset = this.offset_; - - if (this.offsetOrigin_ != ol.style.IconOrigin.TOP_LEFT) { - var size = this.getSize(); - var iconImageSize = this.iconImage_.getSize(); - if (!size || !iconImageSize) { - return null; - } - offset = offset.slice(); - if (this.offsetOrigin_ == ol.style.IconOrigin.TOP_RIGHT || - this.offsetOrigin_ == ol.style.IconOrigin.BOTTOM_RIGHT) { - offset[0] = iconImageSize[0] - size[0] - offset[0]; - } - if (this.offsetOrigin_ == ol.style.IconOrigin.BOTTOM_LEFT || - this.offsetOrigin_ == ol.style.IconOrigin.BOTTOM_RIGHT) { - offset[1] = iconImageSize[1] - size[1] - offset[1]; - } - } - this.origin_ = offset; - return this.origin_; -}; - - -/** - * Get the image URL. - * @return {string|undefined} Image src. - * @api - */ -ol.style.Icon.prototype.getSrc = function() { - return this.iconImage_.getSrc(); -}; - - -/** - * @inheritDoc - * @api - */ -ol.style.Icon.prototype.getSize = function() { - return !this.size_ ? this.iconImage_.getSize() : this.size_; -}; - - -/** - * @override - */ -ol.style.Icon.prototype.listenImageChange = function(listener, thisArg) { - return ol.events.listen(this.iconImage_, ol.events.EventType.CHANGE, - listener, thisArg); -}; - - -/** - * Load not yet loaded URI. - * When rendering a feature with an icon style, the vector renderer will - * automatically call this method. However, you might want to call this - * method yourself for preloading or other purposes. - * @override - * @api - */ -ol.style.Icon.prototype.load = function() { - this.iconImage_.load(); -}; - - -/** - * @override - */ -ol.style.Icon.prototype.unlistenImageChange = function(listener, thisArg) { - ol.events.unlisten(this.iconImage_, ol.events.EventType.CHANGE, - listener, thisArg); -}; - -goog.provide('ol.style.Text'); - - -goog.require('ol.style.Fill'); -goog.require('ol.style.TextPlacement'); - - -/** - * @classdesc - * Set text style for vector features. - * - * @constructor - * @param {olx.style.TextOptions=} opt_options Options. - * @api - */ -ol.style.Text = function(opt_options) { - - var options = opt_options || {}; - - /** - * @private - * @type {string|undefined} - */ - this.font_ = options.font; - - /** - * @private - * @type {number|undefined} - */ - this.rotation_ = options.rotation; - - /** - * @private - * @type {boolean|undefined} - */ - this.rotateWithView_ = options.rotateWithView; - - /** - * @private - * @type {number|undefined} - */ - this.scale_ = options.scale; - - /** - * @private - * @type {string|undefined} - */ - this.text_ = options.text; - - /** - * @private - * @type {string|undefined} - */ - this.textAlign_ = options.textAlign; - - /** - * @private - * @type {string|undefined} - */ - this.textBaseline_ = options.textBaseline; - - /** - * @private - * @type {ol.style.Fill} - */ - this.fill_ = options.fill !== undefined ? options.fill : - new ol.style.Fill({color: ol.style.Text.DEFAULT_FILL_COLOR_}); - - /** - * @private - * @type {number} - */ - this.maxAngle_ = options.maxAngle !== undefined ? options.maxAngle : Math.PI / 4; - - /** - * @private - * @type {ol.style.TextPlacement|string} - */ - this.placement_ = options.placement !== undefined ? options.placement : ol.style.TextPlacement.POINT; - - /** - * @private - * @type {boolean} - */ - this.exceedLength_ = options.exceedLength !== undefined ? options.exceedLength : false; - - /** - * @private - * @type {ol.style.Stroke} - */ - this.stroke_ = options.stroke !== undefined ? options.stroke : null; - - /** - * @private - * @type {number} - */ - this.offsetX_ = options.offsetX !== undefined ? options.offsetX : 0; - - /** - * @private - * @type {number} - */ - this.offsetY_ = options.offsetY !== undefined ? options.offsetY : 0; -}; - - -/** - * The default fill color to use if no fill was set at construction time; a - * blackish `#333`. - * - * @const {string} - * @private - */ -ol.style.Text.DEFAULT_FILL_COLOR_ = '#333'; - - -/** - * Clones the style. - * @return {ol.style.Text} The cloned style. - * @api - */ -ol.style.Text.prototype.clone = function() { - return new ol.style.Text({ - font: this.getFont(), - placement: this.getPlacement(), - maxAngle: this.getMaxAngle(), - exceedLength: this.getExceedLength(), - rotation: this.getRotation(), - rotateWithView: this.getRotateWithView(), - scale: this.getScale(), - text: this.getText(), - textAlign: this.getTextAlign(), - textBaseline: this.getTextBaseline(), - fill: this.getFill() ? this.getFill().clone() : undefined, - stroke: this.getStroke() ? this.getStroke().clone() : undefined, - offsetX: this.getOffsetX(), - offsetY: this.getOffsetY() - }); -}; - - -/** - * Get the `exceedLength` configuration. - * @return {boolean} Let text exceed the length of the path they follow. - * @api - */ -ol.style.Text.prototype.getExceedLength = function() { - return this.exceedLength_; -}; - - -/** - * Get the font name. - * @return {string|undefined} Font. - * @api - */ -ol.style.Text.prototype.getFont = function() { - return this.font_; -}; - - -/** - * Get the maximum angle between adjacent characters. - * @return {number} Angle in radians. - * @api - */ -ol.style.Text.prototype.getMaxAngle = function() { - return this.maxAngle_; -}; - - -/** - * Get the label placement. - * @return {ol.style.TextPlacement|string} Text placement. - * @api - */ -ol.style.Text.prototype.getPlacement = function() { - return this.placement_; -}; - - -/** - * Get the x-offset for the text. - * @return {number} Horizontal text offset. - * @api - */ -ol.style.Text.prototype.getOffsetX = function() { - return this.offsetX_; -}; - - -/** - * Get the y-offset for the text. - * @return {number} Vertical text offset. - * @api - */ -ol.style.Text.prototype.getOffsetY = function() { - return this.offsetY_; -}; - - -/** - * Get the fill style for the text. - * @return {ol.style.Fill} Fill style. - * @api - */ -ol.style.Text.prototype.getFill = function() { - return this.fill_; -}; - - -/** - * Determine whether the text rotates with the map. - * @return {boolean|undefined} Rotate with map. - * @api - */ -ol.style.Text.prototype.getRotateWithView = function() { - return this.rotateWithView_; -}; - - -/** - * Get the text rotation. - * @return {number|undefined} Rotation. - * @api - */ -ol.style.Text.prototype.getRotation = function() { - return this.rotation_; -}; - - -/** - * Get the text scale. - * @return {number|undefined} Scale. - * @api - */ -ol.style.Text.prototype.getScale = function() { - return this.scale_; -}; - - -/** - * Get the stroke style for the text. - * @return {ol.style.Stroke} Stroke style. - * @api - */ -ol.style.Text.prototype.getStroke = function() { - return this.stroke_; -}; - - -/** - * Get the text to be rendered. - * @return {string|undefined} Text. - * @api - */ -ol.style.Text.prototype.getText = function() { - return this.text_; -}; - - -/** - * Get the text alignment. - * @return {string|undefined} Text align. - * @api - */ -ol.style.Text.prototype.getTextAlign = function() { - return this.textAlign_; -}; - - -/** - * Get the text baseline. - * @return {string|undefined} Text baseline. - * @api - */ -ol.style.Text.prototype.getTextBaseline = function() { - return this.textBaseline_; -}; - - -/** - * Set the `exceedLength` property. - * - * @param {boolean} exceedLength Let text exceed the path that it follows. - * @api - */ -ol.style.Text.prototype.setExceedLength = function(exceedLength) { - this.exceedLength_ = exceedLength; -}; - - -/** - * Set the font. - * - * @param {string|undefined} font Font. - * @api - */ -ol.style.Text.prototype.setFont = function(font) { - this.font_ = font; -}; - - -/** - * Set the maximum angle between adjacent characters. - * - * @param {number} maxAngle Angle in radians. - * @api - */ -ol.style.Text.prototype.setMaxAngle = function(maxAngle) { - this.maxAngle_ = maxAngle; -}; - - -/** - * Set the x offset. - * - * @param {number} offsetX Horizontal text offset. - * @api - */ -ol.style.Text.prototype.setOffsetX = function(offsetX) { - this.offsetX_ = offsetX; -}; - - -/** - * Set the y offset. - * - * @param {number} offsetY Vertical text offset. - * @api - */ -ol.style.Text.prototype.setOffsetY = function(offsetY) { - this.offsetY_ = offsetY; -}; - - -/** - * Set the text placement. - * - * @param {ol.style.TextPlacement|string} placement Placement. - * @api - */ -ol.style.Text.prototype.setPlacement = function(placement) { - this.placement_ = placement; -}; - - -/** - * Set the fill. - * - * @param {ol.style.Fill} fill Fill style. - * @api - */ -ol.style.Text.prototype.setFill = function(fill) { - this.fill_ = fill; -}; - - -/** - * Set the rotation. - * - * @param {number|undefined} rotation Rotation. - * @api - */ -ol.style.Text.prototype.setRotation = function(rotation) { - this.rotation_ = rotation; -}; - - -/** - * Set the scale. - * - * @param {number|undefined} scale Scale. - * @api - */ -ol.style.Text.prototype.setScale = function(scale) { - this.scale_ = scale; -}; - - -/** - * Set the stroke. - * - * @param {ol.style.Stroke} stroke Stroke style. - * @api - */ -ol.style.Text.prototype.setStroke = function(stroke) { - this.stroke_ = stroke; -}; - - -/** - * Set the text. - * - * @param {string|undefined} text Text. - * @api - */ -ol.style.Text.prototype.setText = function(text) { - this.text_ = text; -}; - - -/** - * Set the text alignment. - * - * @param {string|undefined} textAlign Text align. - * @api - */ -ol.style.Text.prototype.setTextAlign = function(textAlign) { - this.textAlign_ = textAlign; -}; - - -/** - * Set the text baseline. - * - * @param {string|undefined} textBaseline Text baseline. - * @api - */ -ol.style.Text.prototype.setTextBaseline = function(textBaseline) { - this.textBaseline_ = textBaseline; -}; - -// FIXME http://earth.google.com/kml/1.0 namespace? -// FIXME why does node.getAttribute return an unknown type? -// FIXME serialize arbitrary feature properties -// FIXME don't parse style if extractStyles is false - -goog.provide('ol.format.KML'); - -goog.require('ol'); -goog.require('ol.Feature'); -goog.require('ol.array'); -goog.require('ol.asserts'); -goog.require('ol.color'); -goog.require('ol.format.Feature'); -goog.require('ol.format.XMLFeature'); -goog.require('ol.format.XSD'); -goog.require('ol.geom.GeometryCollection'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.LineString'); -goog.require('ol.geom.MultiLineString'); -goog.require('ol.geom.MultiPoint'); -goog.require('ol.geom.MultiPolygon'); -goog.require('ol.geom.Point'); -goog.require('ol.geom.Polygon'); -goog.require('ol.math'); -goog.require('ol.proj'); -goog.require('ol.style.Fill'); -goog.require('ol.style.Icon'); -goog.require('ol.style.IconAnchorUnits'); -goog.require('ol.style.IconOrigin'); -goog.require('ol.style.Stroke'); -goog.require('ol.style.Style'); -goog.require('ol.style.Text'); -goog.require('ol.xml'); - - -/** - * @classdesc - * Feature format for reading and writing data in the KML format. - * - * Note that the KML format uses the URL() constructor. Older browsers such as IE - * which do not support this will need a URL polyfill to be loaded before use. - * - * @constructor - * @extends {ol.format.XMLFeature} - * @param {olx.format.KMLOptions=} opt_options Options. - * @api - */ -ol.format.KML = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - ol.format.XMLFeature.call(this); - - if (!ol.format.KML.DEFAULT_STYLE_ARRAY_) { - ol.format.KML.createStyleDefaults_(); - } - - /** - * @inheritDoc - */ - this.defaultDataProjection = ol.proj.get('EPSG:4326'); - - /** - * @private - * @type {Array.<ol.style.Style>} - */ - this.defaultStyle_ = options.defaultStyle ? - options.defaultStyle : ol.format.KML.DEFAULT_STYLE_ARRAY_; - - /** - * @private - * @type {boolean} - */ - this.extractStyles_ = options.extractStyles !== undefined ? - options.extractStyles : true; - - /** - * @private - * @type {boolean} - */ - this.writeStyles_ = options.writeStyles !== undefined ? - options.writeStyles : true; - - /** - * @private - * @type {Object.<string, (Array.<ol.style.Style>|string)>} - */ - this.sharedStyles_ = {}; - - /** - * @private - * @type {boolean} - */ - this.showPointNames_ = options.showPointNames !== undefined ? - options.showPointNames : true; - -}; -ol.inherits(ol.format.KML, ol.format.XMLFeature); - - -/** - * @const - * @type {Array.<string>} - * @private - */ -ol.format.KML.GX_NAMESPACE_URIS_ = [ - 'http://www.google.com/kml/ext/2.2' -]; - - -/** - * @const - * @type {Array.<string>} - * @private - */ -ol.format.KML.NAMESPACE_URIS_ = [ - null, - 'http://earth.google.com/kml/2.0', - 'http://earth.google.com/kml/2.1', - 'http://earth.google.com/kml/2.2', - 'http://www.opengis.net/kml/2.2' -]; - - -/** - * @const - * @type {string} - * @private - */ -ol.format.KML.SCHEMA_LOCATION_ = 'http://www.opengis.net/kml/2.2 ' + - 'https://developers.google.com/kml/schema/kml22gx.xsd'; - - -/** - * @return {Array.<ol.style.Style>} Default style. - * @private - */ -ol.format.KML.createStyleDefaults_ = function() { - /** - * @const - * @type {ol.Color} - * @private - */ - ol.format.KML.DEFAULT_COLOR_ = [255, 255, 255, 1]; - - /** - * @const - * @type {ol.style.Fill} - * @private - */ - ol.format.KML.DEFAULT_FILL_STYLE_ = new ol.style.Fill({ - color: ol.format.KML.DEFAULT_COLOR_ - }); - - /** - * @const - * @type {ol.Size} - * @private - */ - ol.format.KML.DEFAULT_IMAGE_STYLE_ANCHOR_ = [20, 2]; // FIXME maybe [8, 32] ? - - /** - * @const - * @type {ol.style.IconAnchorUnits} - * @private - */ - ol.format.KML.DEFAULT_IMAGE_STYLE_ANCHOR_X_UNITS_ = - ol.style.IconAnchorUnits.PIXELS; - - /** - * @const - * @type {ol.style.IconAnchorUnits} - * @private - */ - ol.format.KML.DEFAULT_IMAGE_STYLE_ANCHOR_Y_UNITS_ = - ol.style.IconAnchorUnits.PIXELS; - - /** - * @const - * @type {ol.Size} - * @private - */ - ol.format.KML.DEFAULT_IMAGE_STYLE_SIZE_ = [64, 64]; - - /** - * @const - * @type {string} - * @private - */ - ol.format.KML.DEFAULT_IMAGE_STYLE_SRC_ = - 'https://maps.google.com/mapfiles/kml/pushpin/ylw-pushpin.png'; - - /** - * @const - * @type {number} - * @private - */ - ol.format.KML.DEFAULT_IMAGE_SCALE_MULTIPLIER_ = 0.5; - - /** - * @const - * @type {ol.style.Image} - * @private - */ - ol.format.KML.DEFAULT_IMAGE_STYLE_ = new ol.style.Icon({ - anchor: ol.format.KML.DEFAULT_IMAGE_STYLE_ANCHOR_, - anchorOrigin: ol.style.IconOrigin.BOTTOM_LEFT, - anchorXUnits: ol.format.KML.DEFAULT_IMAGE_STYLE_ANCHOR_X_UNITS_, - anchorYUnits: ol.format.KML.DEFAULT_IMAGE_STYLE_ANCHOR_Y_UNITS_, - crossOrigin: 'anonymous', - rotation: 0, - scale: ol.format.KML.DEFAULT_IMAGE_SCALE_MULTIPLIER_, - size: ol.format.KML.DEFAULT_IMAGE_STYLE_SIZE_, - src: ol.format.KML.DEFAULT_IMAGE_STYLE_SRC_ - }); - - /** - * @const - * @type {string} - * @private - */ - ol.format.KML.DEFAULT_NO_IMAGE_STYLE_ = 'NO_IMAGE'; - - /** - * @const - * @type {ol.style.Stroke} - * @private - */ - ol.format.KML.DEFAULT_STROKE_STYLE_ = new ol.style.Stroke({ - color: ol.format.KML.DEFAULT_COLOR_, - width: 1 - }); - - /** - * @const - * @type {ol.style.Stroke} - * @private - */ - ol.format.KML.DEFAULT_TEXT_STROKE_STYLE_ = new ol.style.Stroke({ - color: [51, 51, 51, 1], - width: 2 - }); - - /** - * @const - * @type {ol.style.Text} - * @private - */ - ol.format.KML.DEFAULT_TEXT_STYLE_ = new ol.style.Text({ - font: 'bold 16px Helvetica', - fill: ol.format.KML.DEFAULT_FILL_STYLE_, - stroke: ol.format.KML.DEFAULT_TEXT_STROKE_STYLE_, - scale: 0.8 - }); - - /** - * @const - * @type {ol.style.Style} - * @private - */ - ol.format.KML.DEFAULT_STYLE_ = new ol.style.Style({ - fill: ol.format.KML.DEFAULT_FILL_STYLE_, - image: ol.format.KML.DEFAULT_IMAGE_STYLE_, - text: ol.format.KML.DEFAULT_TEXT_STYLE_, - stroke: ol.format.KML.DEFAULT_STROKE_STYLE_, - zIndex: 0 - }); - - /** - * @const - * @type {Array.<ol.style.Style>} - * @private - */ - ol.format.KML.DEFAULT_STYLE_ARRAY_ = [ol.format.KML.DEFAULT_STYLE_]; - - return ol.format.KML.DEFAULT_STYLE_ARRAY_; -}; - - -/** - * @const - * @type {Object.<string, ol.style.IconAnchorUnits>} - * @private - */ -ol.format.KML.ICON_ANCHOR_UNITS_MAP_ = { - 'fraction': ol.style.IconAnchorUnits.FRACTION, - 'pixels': ol.style.IconAnchorUnits.PIXELS, - 'insetPixels': ol.style.IconAnchorUnits.PIXELS -}; - - -/** - * @param {ol.style.Style|undefined} foundStyle Style. - * @param {string} name Name. - * @return {ol.style.Style} style Style. - * @private - */ -ol.format.KML.createNameStyleFunction_ = function(foundStyle, name) { - var textStyle = null; - var textOffset = [0, 0]; - var textAlign = 'start'; - if (foundStyle.getImage()) { - var imageSize = foundStyle.getImage().getImageSize(); - if (imageSize === null) { - imageSize = ol.format.KML.DEFAULT_IMAGE_STYLE_SIZE_; - } - if (imageSize.length == 2) { - var imageScale = foundStyle.getImage().getScale(); - // Offset the label to be centered to the right of the icon, if there is - // one. - textOffset[0] = imageScale * imageSize[0] / 2; - textOffset[1] = -imageScale * imageSize[1] / 2; - textAlign = 'left'; - } - } - if (foundStyle.getText() !== null) { - // clone the text style, customizing it with name, alignments and offset. - // Note that kml does not support many text options that OpenLayers does (rotation, textBaseline). - var foundText = foundStyle.getText(); - textStyle = foundText.clone(); - textStyle.setFont(foundText.getFont() || ol.format.KML.DEFAULT_TEXT_STYLE_.getFont()); - textStyle.setScale(foundText.getScale() || ol.format.KML.DEFAULT_TEXT_STYLE_.getScale()); - textStyle.setFill(foundText.getFill() || ol.format.KML.DEFAULT_TEXT_STYLE_.getFill()); - textStyle.setStroke(foundText.getStroke() || ol.format.KML.DEFAULT_TEXT_STROKE_STYLE_); - } else { - textStyle = ol.format.KML.DEFAULT_TEXT_STYLE_.clone(); - } - textStyle.setText(name); - textStyle.setOffsetX(textOffset[0]); - textStyle.setOffsetY(textOffset[1]); - textStyle.setTextAlign(textAlign); - - var nameStyle = new ol.style.Style({ - text: textStyle - }); - return nameStyle; -}; - - -/** - * @param {Array.<ol.style.Style>|undefined} style Style. - * @param {string} styleUrl Style URL. - * @param {Array.<ol.style.Style>} defaultStyle Default style. - * @param {Object.<string, (Array.<ol.style.Style>|string)>} sharedStyles Shared - * styles. - * @param {boolean|undefined} showPointNames true to show names for point - * placemarks. - * @return {ol.FeatureStyleFunction} Feature style function. - * @private - */ -ol.format.KML.createFeatureStyleFunction_ = function(style, styleUrl, - defaultStyle, sharedStyles, showPointNames) { - - return ( - /** - * @param {number} resolution Resolution. - * @return {Array.<ol.style.Style>} Style. - * @this {ol.Feature} - */ - function(resolution) { - var drawName = showPointNames; - /** @type {ol.style.Style|undefined} */ - var nameStyle; - var name = ''; - if (drawName) { - if (this.getGeometry()) { - drawName = (this.getGeometry().getType() === - ol.geom.GeometryType.POINT); - } - } - - if (drawName) { - name = /** @type {string} */ (this.get('name')); - drawName = drawName && name; - } - - if (style) { - if (drawName) { - nameStyle = ol.format.KML.createNameStyleFunction_(style[0], - name); - return style.concat(nameStyle); - } - return style; - } - if (styleUrl) { - var foundStyle = ol.format.KML.findStyle_(styleUrl, defaultStyle, - sharedStyles); - if (drawName) { - nameStyle = ol.format.KML.createNameStyleFunction_(foundStyle[0], - name); - return foundStyle.concat(nameStyle); - } - return foundStyle; - } - if (drawName) { - nameStyle = ol.format.KML.createNameStyleFunction_(defaultStyle[0], - name); - return defaultStyle.concat(nameStyle); - } - return defaultStyle; - }); -}; - - -/** - * @param {Array.<ol.style.Style>|string|undefined} styleValue Style value. - * @param {Array.<ol.style.Style>} defaultStyle Default style. - * @param {Object.<string, (Array.<ol.style.Style>|string)>} sharedStyles - * Shared styles. - * @return {Array.<ol.style.Style>} Style. - * @private - */ -ol.format.KML.findStyle_ = function(styleValue, defaultStyle, sharedStyles) { - if (Array.isArray(styleValue)) { - return styleValue; - } else if (typeof styleValue === 'string') { - // KML files in the wild occasionally forget the leading `#` on styleUrls - // defined in the same document. Add a leading `#` if it enables to find - // a style. - if (!(styleValue in sharedStyles) && ('#' + styleValue in sharedStyles)) { - styleValue = '#' + styleValue; - } - return ol.format.KML.findStyle_( - sharedStyles[styleValue], defaultStyle, sharedStyles); - } else { - return defaultStyle; - } -}; - - -/** - * @param {Node} node Node. - * @private - * @return {ol.Color|undefined} Color. - */ -ol.format.KML.readColor_ = function(node) { - var s = ol.xml.getAllTextContent(node, false); - // The KML specification states that colors should not include a leading `#` - // but we tolerate them. - var m = /^\s*#?\s*([0-9A-Fa-f]{8})\s*$/.exec(s); - if (m) { - var hexColor = m[1]; - return [ - parseInt(hexColor.substr(6, 2), 16), - parseInt(hexColor.substr(4, 2), 16), - parseInt(hexColor.substr(2, 2), 16), - parseInt(hexColor.substr(0, 2), 16) / 255 - ]; - - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @private - * @return {Array.<number>|undefined} Flat coordinates. - */ -ol.format.KML.readFlatCoordinates_ = function(node) { - var s = ol.xml.getAllTextContent(node, false); - var flatCoordinates = []; - // The KML specification states that coordinate tuples should not include - // spaces, but we tolerate them. - var re = - /^\s*([+\-]?\d*\.?\d+(?:e[+\-]?\d+)?)\s*,\s*([+\-]?\d*\.?\d+(?:e[+\-]?\d+)?)(?:\s*,\s*([+\-]?\d*\.?\d+(?:e[+\-]?\d+)?))?\s*/i; - var m; - while ((m = re.exec(s))) { - var x = parseFloat(m[1]); - var y = parseFloat(m[2]); - var z = m[3] ? parseFloat(m[3]) : 0; - flatCoordinates.push(x, y, z); - s = s.substr(m[0].length); - } - if (s !== '') { - return undefined; - } - return flatCoordinates; -}; - - -/** - * @param {Node} node Node. - * @private - * @return {string} URI. - */ -ol.format.KML.readURI_ = function(node) { - var s = ol.xml.getAllTextContent(node, false).trim(); - var baseURI = node.baseURI; - if (!baseURI || baseURI == 'about:blank') { - baseURI = window.location.href; - } - if (baseURI) { - var url = new URL(s, baseURI); - return url.href; - } else { - return s; - } -}; - - -/** - * @param {Node} node Node. - * @private - * @return {ol.KMLVec2_} Vec2. - */ -ol.format.KML.readVec2_ = function(node) { - var xunits = node.getAttribute('xunits'); - var yunits = node.getAttribute('yunits'); - var origin; - if (xunits !== 'insetPixels') { - if (yunits !== 'insetPixels') { - origin = ol.style.IconOrigin.BOTTOM_LEFT; - } else { - origin = ol.style.IconOrigin.TOP_LEFT; - } - } else { - if (yunits !== 'insetPixels') { - origin = ol.style.IconOrigin.BOTTOM_RIGHT; - } else { - origin = ol.style.IconOrigin.TOP_RIGHT; - } - } - return { - x: parseFloat(node.getAttribute('x')), - xunits: ol.format.KML.ICON_ANCHOR_UNITS_MAP_[xunits], - y: parseFloat(node.getAttribute('y')), - yunits: ol.format.KML.ICON_ANCHOR_UNITS_MAP_[yunits], - origin: origin - }; -}; - - -/** - * @param {Node} node Node. - * @private - * @return {number|undefined} Scale. - */ -ol.format.KML.readScale_ = function(node) { - return ol.format.XSD.readDecimal(node); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Array.<ol.style.Style>|string|undefined} StyleMap. - */ -ol.format.KML.readStyleMapValue_ = function(node, objectStack) { - return ol.xml.pushParseAndPop(undefined, - ol.format.KML.STYLE_MAP_PARSERS_, node, objectStack); -}; -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.IconStyleParser_ = function(node, objectStack) { - // FIXME refreshMode - // FIXME refreshInterval - // FIXME viewRefreshTime - // FIXME viewBoundScale - // FIXME viewFormat - // FIXME httpQuery - var object = ol.xml.pushParseAndPop( - {}, ol.format.KML.ICON_STYLE_PARSERS_, node, objectStack); - if (!object) { - return; - } - var styleObject = /** @type {Object} */ (objectStack[objectStack.length - 1]); - var IconObject = 'Icon' in object ? object['Icon'] : {}; - var drawIcon = (!('Icon' in object) || Object.keys(IconObject).length > 0); - var src; - var href = /** @type {string|undefined} */ - (IconObject['href']); - if (href) { - src = href; - } else if (drawIcon) { - src = ol.format.KML.DEFAULT_IMAGE_STYLE_SRC_; - } - var anchor, anchorXUnits, anchorYUnits; - var anchorOrigin = ol.style.IconOrigin.BOTTOM_LEFT; - var hotSpot = /** @type {ol.KMLVec2_|undefined} */ - (object['hotSpot']); - if (hotSpot) { - anchor = [hotSpot.x, hotSpot.y]; - anchorXUnits = hotSpot.xunits; - anchorYUnits = hotSpot.yunits; - anchorOrigin = hotSpot.origin; - } else if (src === ol.format.KML.DEFAULT_IMAGE_STYLE_SRC_) { - anchor = ol.format.KML.DEFAULT_IMAGE_STYLE_ANCHOR_; - anchorXUnits = ol.format.KML.DEFAULT_IMAGE_STYLE_ANCHOR_X_UNITS_; - anchorYUnits = ol.format.KML.DEFAULT_IMAGE_STYLE_ANCHOR_Y_UNITS_; - } else if (/^http:\/\/maps\.(?:google|gstatic)\.com\//.test(src)) { - anchor = [0.5, 0]; - anchorXUnits = ol.style.IconAnchorUnits.FRACTION; - anchorYUnits = ol.style.IconAnchorUnits.FRACTION; - } - - var offset; - var x = /** @type {number|undefined} */ - (IconObject['x']); - var y = /** @type {number|undefined} */ - (IconObject['y']); - if (x !== undefined && y !== undefined) { - offset = [x, y]; - } - - var size; - var w = /** @type {number|undefined} */ - (IconObject['w']); - var h = /** @type {number|undefined} */ - (IconObject['h']); - if (w !== undefined && h !== undefined) { - size = [w, h]; - } - - var rotation; - var heading = /** @type {number} */ - (object['heading']); - if (heading !== undefined) { - rotation = ol.math.toRadians(heading); - } - - var scale = /** @type {number|undefined} */ - (object['scale']); - - if (drawIcon) { - if (src == ol.format.KML.DEFAULT_IMAGE_STYLE_SRC_) { - size = ol.format.KML.DEFAULT_IMAGE_STYLE_SIZE_; - if (scale === undefined) { - scale = ol.format.KML.DEFAULT_IMAGE_SCALE_MULTIPLIER_; - } - } - - var imageStyle = new ol.style.Icon({ - anchor: anchor, - anchorOrigin: anchorOrigin, - anchorXUnits: anchorXUnits, - anchorYUnits: anchorYUnits, - crossOrigin: 'anonymous', // FIXME should this be configurable? - offset: offset, - offsetOrigin: ol.style.IconOrigin.BOTTOM_LEFT, - rotation: rotation, - scale: scale, - size: size, - src: src - }); - styleObject['imageStyle'] = imageStyle; - } else { - // handle the case when we explicitly want to draw no icon. - styleObject['imageStyle'] = ol.format.KML.DEFAULT_NO_IMAGE_STYLE_; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.LabelStyleParser_ = function(node, objectStack) { - // FIXME colorMode - var object = ol.xml.pushParseAndPop( - {}, ol.format.KML.LABEL_STYLE_PARSERS_, node, objectStack); - if (!object) { - return; - } - var styleObject = objectStack[objectStack.length - 1]; - var textStyle = new ol.style.Text({ - fill: new ol.style.Fill({ - color: /** @type {ol.Color} */ - ('color' in object ? object['color'] : ol.format.KML.DEFAULT_COLOR_) - }), - scale: /** @type {number|undefined} */ - (object['scale']) - }); - styleObject['textStyle'] = textStyle; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.LineStyleParser_ = function(node, objectStack) { - // FIXME colorMode - // FIXME gx:outerColor - // FIXME gx:outerWidth - // FIXME gx:physicalWidth - // FIXME gx:labelVisibility - var object = ol.xml.pushParseAndPop( - {}, ol.format.KML.LINE_STYLE_PARSERS_, node, objectStack); - if (!object) { - return; - } - var styleObject = objectStack[objectStack.length - 1]; - var strokeStyle = new ol.style.Stroke({ - color: /** @type {ol.Color} */ - ('color' in object ? object['color'] : ol.format.KML.DEFAULT_COLOR_), - width: /** @type {number} */ ('width' in object ? object['width'] : 1) - }); - styleObject['strokeStyle'] = strokeStyle; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.PolyStyleParser_ = function(node, objectStack) { - // FIXME colorMode - var object = ol.xml.pushParseAndPop( - {}, ol.format.KML.POLY_STYLE_PARSERS_, node, objectStack); - if (!object) { - return; - } - var styleObject = objectStack[objectStack.length - 1]; - var fillStyle = new ol.style.Fill({ - color: /** @type {ol.Color} */ - ('color' in object ? object['color'] : ol.format.KML.DEFAULT_COLOR_) - }); - styleObject['fillStyle'] = fillStyle; - var fill = /** @type {boolean|undefined} */ (object['fill']); - if (fill !== undefined) { - styleObject['fill'] = fill; - } - var outline = - /** @type {boolean|undefined} */ (object['outline']); - if (outline !== undefined) { - styleObject['outline'] = outline; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Array.<number>} LinearRing flat coordinates. - */ -ol.format.KML.readFlatLinearRing_ = function(node, objectStack) { - return ol.xml.pushParseAndPop(null, - ol.format.KML.FLAT_LINEAR_RING_PARSERS_, node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.gxCoordParser_ = function(node, objectStack) { - var gxTrackObject = /** @type {ol.KMLGxTrackObject_} */ - (objectStack[objectStack.length - 1]); - var flatCoordinates = gxTrackObject.flatCoordinates; - var s = ol.xml.getAllTextContent(node, false); - var re = - /^\s*([+\-]?\d+(?:\.\d*)?(?:e[+\-]?\d*)?)\s+([+\-]?\d+(?:\.\d*)?(?:e[+\-]?\d*)?)\s+([+\-]?\d+(?:\.\d*)?(?:e[+\-]?\d*)?)\s*$/i; - var m = re.exec(s); - if (m) { - var x = parseFloat(m[1]); - var y = parseFloat(m[2]); - var z = parseFloat(m[3]); - flatCoordinates.push(x, y, z, 0); - } else { - flatCoordinates.push(0, 0, 0, 0); - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {ol.geom.MultiLineString|undefined} MultiLineString. - */ -ol.format.KML.readGxMultiTrack_ = function(node, objectStack) { - var lineStrings = ol.xml.pushParseAndPop([], - ol.format.KML.GX_MULTITRACK_GEOMETRY_PARSERS_, node, objectStack); - if (!lineStrings) { - return undefined; - } - var multiLineString = new ol.geom.MultiLineString(null); - multiLineString.setLineStrings(lineStrings); - return multiLineString; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {ol.geom.LineString|undefined} LineString. - */ -ol.format.KML.readGxTrack_ = function(node, objectStack) { - var gxTrackObject = ol.xml.pushParseAndPop( - /** @type {ol.KMLGxTrackObject_} */ ({ - flatCoordinates: [], - whens: [] - }), ol.format.KML.GX_TRACK_PARSERS_, node, objectStack); - if (!gxTrackObject) { - return undefined; - } - var flatCoordinates = gxTrackObject.flatCoordinates; - var whens = gxTrackObject.whens; - var i, ii; - for (i = 0, ii = Math.min(flatCoordinates.length, whens.length); i < ii; - ++i) { - flatCoordinates[4 * i + 3] = whens[i]; - } - var lineString = new ol.geom.LineString(null); - lineString.setFlatCoordinates(ol.geom.GeometryLayout.XYZM, flatCoordinates); - return lineString; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object} Icon object. - */ -ol.format.KML.readIcon_ = function(node, objectStack) { - var iconObject = ol.xml.pushParseAndPop( - {}, ol.format.KML.ICON_PARSERS_, node, objectStack); - if (iconObject) { - return iconObject; - } else { - return null; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Array.<number>} Flat coordinates. - */ -ol.format.KML.readFlatCoordinatesFromNode_ = function(node, objectStack) { - return ol.xml.pushParseAndPop(null, - ol.format.KML.GEOMETRY_FLAT_COORDINATES_PARSERS_, node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {ol.geom.LineString|undefined} LineString. - */ -ol.format.KML.readLineString_ = function(node, objectStack) { - var properties = ol.xml.pushParseAndPop({}, - ol.format.KML.EXTRUDE_AND_ALTITUDE_MODE_PARSERS_, node, - objectStack); - var flatCoordinates = - ol.format.KML.readFlatCoordinatesFromNode_(node, objectStack); - if (flatCoordinates) { - var lineString = new ol.geom.LineString(null); - lineString.setFlatCoordinates(ol.geom.GeometryLayout.XYZ, flatCoordinates); - lineString.setProperties(properties); - return lineString; - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {ol.geom.Polygon|undefined} Polygon. - */ -ol.format.KML.readLinearRing_ = function(node, objectStack) { - var properties = ol.xml.pushParseAndPop({}, - ol.format.KML.EXTRUDE_AND_ALTITUDE_MODE_PARSERS_, node, - objectStack); - var flatCoordinates = - ol.format.KML.readFlatCoordinatesFromNode_(node, objectStack); - if (flatCoordinates) { - var polygon = new ol.geom.Polygon(null); - polygon.setFlatCoordinates(ol.geom.GeometryLayout.XYZ, flatCoordinates, - [flatCoordinates.length]); - polygon.setProperties(properties); - return polygon; - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {ol.geom.Geometry} Geometry. - */ -ol.format.KML.readMultiGeometry_ = function(node, objectStack) { - var geometries = ol.xml.pushParseAndPop([], - ol.format.KML.MULTI_GEOMETRY_PARSERS_, node, objectStack); - if (!geometries) { - return null; - } - if (geometries.length === 0) { - return new ol.geom.GeometryCollection(geometries); - } - /** @type {ol.geom.Geometry} */ - var multiGeometry; - var homogeneous = true; - var type = geometries[0].getType(); - var geometry, i, ii; - for (i = 1, ii = geometries.length; i < ii; ++i) { - geometry = geometries[i]; - if (geometry.getType() != type) { - homogeneous = false; - break; - } - } - if (homogeneous) { - var layout; - var flatCoordinates; - if (type == ol.geom.GeometryType.POINT) { - var point = geometries[0]; - layout = point.getLayout(); - flatCoordinates = point.getFlatCoordinates(); - for (i = 1, ii = geometries.length; i < ii; ++i) { - geometry = geometries[i]; - ol.array.extend(flatCoordinates, geometry.getFlatCoordinates()); - } - multiGeometry = new ol.geom.MultiPoint(null); - multiGeometry.setFlatCoordinates(layout, flatCoordinates); - ol.format.KML.setCommonGeometryProperties_(multiGeometry, geometries); - } else if (type == ol.geom.GeometryType.LINE_STRING) { - multiGeometry = new ol.geom.MultiLineString(null); - multiGeometry.setLineStrings(geometries); - ol.format.KML.setCommonGeometryProperties_(multiGeometry, geometries); - } else if (type == ol.geom.GeometryType.POLYGON) { - multiGeometry = new ol.geom.MultiPolygon(null); - multiGeometry.setPolygons(geometries); - ol.format.KML.setCommonGeometryProperties_(multiGeometry, geometries); - } else if (type == ol.geom.GeometryType.GEOMETRY_COLLECTION) { - multiGeometry = new ol.geom.GeometryCollection(geometries); - } else { - ol.asserts.assert(false, 37); // Unknown geometry type found - } - } else { - multiGeometry = new ol.geom.GeometryCollection(geometries); - } - return /** @type {ol.geom.Geometry} */ (multiGeometry); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {ol.geom.Point|undefined} Point. - */ -ol.format.KML.readPoint_ = function(node, objectStack) { - var properties = ol.xml.pushParseAndPop({}, - ol.format.KML.EXTRUDE_AND_ALTITUDE_MODE_PARSERS_, node, - objectStack); - var flatCoordinates = - ol.format.KML.readFlatCoordinatesFromNode_(node, objectStack); - if (flatCoordinates) { - var point = new ol.geom.Point(null); - point.setFlatCoordinates(ol.geom.GeometryLayout.XYZ, flatCoordinates); - point.setProperties(properties); - return point; - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {ol.geom.Polygon|undefined} Polygon. - */ -ol.format.KML.readPolygon_ = function(node, objectStack) { - var properties = ol.xml.pushParseAndPop(/** @type {Object<string,*>} */ ({}), - ol.format.KML.EXTRUDE_AND_ALTITUDE_MODE_PARSERS_, node, - objectStack); - var flatLinearRings = ol.xml.pushParseAndPop([null], - ol.format.KML.FLAT_LINEAR_RINGS_PARSERS_, node, objectStack); - if (flatLinearRings && flatLinearRings[0]) { - var polygon = new ol.geom.Polygon(null); - var flatCoordinates = flatLinearRings[0]; - var ends = [flatCoordinates.length]; - var i, ii; - for (i = 1, ii = flatLinearRings.length; i < ii; ++i) { - ol.array.extend(flatCoordinates, flatLinearRings[i]); - ends.push(flatCoordinates.length); - } - polygon.setFlatCoordinates( - ol.geom.GeometryLayout.XYZ, flatCoordinates, ends); - polygon.setProperties(properties); - return polygon; - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Array.<ol.style.Style>} Style. - */ -ol.format.KML.readStyle_ = function(node, objectStack) { - var styleObject = ol.xml.pushParseAndPop( - {}, ol.format.KML.STYLE_PARSERS_, node, objectStack); - if (!styleObject) { - return null; - } - var fillStyle = /** @type {ol.style.Fill} */ - ('fillStyle' in styleObject ? - styleObject['fillStyle'] : ol.format.KML.DEFAULT_FILL_STYLE_); - var fill = /** @type {boolean|undefined} */ (styleObject['fill']); - if (fill !== undefined && !fill) { - fillStyle = null; - } - var imageStyle = /** @type {ol.style.Image} */ - ('imageStyle' in styleObject ? - styleObject['imageStyle'] : ol.format.KML.DEFAULT_IMAGE_STYLE_); - if (imageStyle == ol.format.KML.DEFAULT_NO_IMAGE_STYLE_) { - imageStyle = undefined; - } - var textStyle = /** @type {ol.style.Text} */ - ('textStyle' in styleObject ? - styleObject['textStyle'] : ol.format.KML.DEFAULT_TEXT_STYLE_); - var strokeStyle = /** @type {ol.style.Stroke} */ - ('strokeStyle' in styleObject ? - styleObject['strokeStyle'] : ol.format.KML.DEFAULT_STROKE_STYLE_); - var outline = /** @type {boolean|undefined} */ - (styleObject['outline']); - if (outline !== undefined && !outline) { - strokeStyle = null; - } - return [new ol.style.Style({ - fill: fillStyle, - image: imageStyle, - stroke: strokeStyle, - text: textStyle, - zIndex: undefined // FIXME - })]; -}; - - -/** - * Reads an array of geometries and creates arrays for common geometry - * properties. Then sets them to the multi geometry. - * @param {ol.geom.MultiPoint|ol.geom.MultiLineString|ol.geom.MultiPolygon} - * multiGeometry A multi-geometry. - * @param {Array.<ol.geom.Geometry>} geometries List of geometries. - * @private - */ -ol.format.KML.setCommonGeometryProperties_ = function(multiGeometry, - geometries) { - var ii = geometries.length; - var extrudes = new Array(geometries.length); - var tessellates = new Array(geometries.length); - var altitudeModes = new Array(geometries.length); - var geometry, i, hasExtrude, hasTessellate, hasAltitudeMode; - hasExtrude = hasTessellate = hasAltitudeMode = false; - for (i = 0; i < ii; ++i) { - geometry = geometries[i]; - extrudes[i] = geometry.get('extrude'); - tessellates[i] = geometry.get('tessellate'); - altitudeModes[i] = geometry.get('altitudeMode'); - hasExtrude = hasExtrude || extrudes[i] !== undefined; - hasTessellate = hasTessellate || tessellates[i] !== undefined; - hasAltitudeMode = hasAltitudeMode || altitudeModes[i]; - } - if (hasExtrude) { - multiGeometry.set('extrude', extrudes); - } - if (hasTessellate) { - multiGeometry.set('tessellate', tessellates); - } - if (hasAltitudeMode) { - multiGeometry.set('altitudeMode', altitudeModes); - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.DataParser_ = function(node, objectStack) { - var name = node.getAttribute('name'); - ol.xml.parseNode(ol.format.KML.DATA_PARSERS_, node, objectStack); - var featureObject = /** @type {Object} */ (objectStack[objectStack.length - 1]); - if (name !== null) { - featureObject[name] = featureObject.value; - } else if (featureObject.displayName !== null) { - featureObject[featureObject.displayName] = featureObject.value; - } - delete featureObject['value']; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.ExtendedDataParser_ = function(node, objectStack) { - ol.xml.parseNode(ol.format.KML.EXTENDED_DATA_PARSERS_, node, objectStack); -}; - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.RegionParser_ = function(node, objectStack) { - ol.xml.parseNode(ol.format.KML.REGION_PARSERS_, node, objectStack); -}; - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.PairDataParser_ = function(node, objectStack) { - var pairObject = ol.xml.pushParseAndPop( - {}, ol.format.KML.PAIR_PARSERS_, node, objectStack); - if (!pairObject) { - return; - } - var key = /** @type {string|undefined} */ - (pairObject['key']); - if (key && key == 'normal') { - var styleUrl = /** @type {string|undefined} */ - (pairObject['styleUrl']); - if (styleUrl) { - objectStack[objectStack.length - 1] = styleUrl; - } - var Style = /** @type {ol.style.Style} */ - (pairObject['Style']); - if (Style) { - objectStack[objectStack.length - 1] = Style; - } - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.PlacemarkStyleMapParser_ = function(node, objectStack) { - var styleMapValue = ol.format.KML.readStyleMapValue_(node, objectStack); - if (!styleMapValue) { - return; - } - var placemarkObject = objectStack[objectStack.length - 1]; - if (Array.isArray(styleMapValue)) { - placemarkObject['Style'] = styleMapValue; - } else if (typeof styleMapValue === 'string') { - placemarkObject['styleUrl'] = styleMapValue; - } else { - ol.asserts.assert(false, 38); // `styleMapValue` has an unknown type - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.SchemaDataParser_ = function(node, objectStack) { - ol.xml.parseNode(ol.format.KML.SCHEMA_DATA_PARSERS_, node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.SimpleDataParser_ = function(node, objectStack) { - var name = node.getAttribute('name'); - if (name !== null) { - var data = ol.format.XSD.readString(node); - var featureObject = - /** @type {Object} */ (objectStack[objectStack.length - 1]); - featureObject[name] = data; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.LatLonAltBoxParser_ = function(node, objectStack) { - var object = ol.xml.pushParseAndPop({}, ol.format.KML.LAT_LON_ALT_BOX_PARSERS_, node, objectStack); - if (!object) { - return; - } - var regionObject = /** @type {Object} */ (objectStack[objectStack.length - 1]); - var extent = [ - parseFloat(object['west']), - parseFloat(object['south']), - parseFloat(object['east']), - parseFloat(object['north']) - ]; - regionObject['extent'] = extent; - regionObject['altitudeMode'] = object['altitudeMode']; - regionObject['minAltitude'] = parseFloat(object['minAltitude']); - regionObject['maxAltitude'] = parseFloat(object['maxAltitude']); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.LodParser_ = function(node, objectStack) { - var object = ol.xml.pushParseAndPop({}, ol.format.KML.LOD_PARSERS_, node, objectStack); - if (!object) { - return; - } - var lodObject = /** @type {Object} */ (objectStack[objectStack.length - 1]); - lodObject['minLodPixels'] = parseFloat(object['minLodPixels']); - lodObject['maxLodPixels'] = parseFloat(object['maxLodPixels']); - lodObject['minFadeExtent'] = parseFloat(object['minFadeExtent']); - lodObject['maxFadeExtent'] = parseFloat(object['maxFadeExtent']); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.innerBoundaryIsParser_ = function(node, objectStack) { - /** @type {Array.<number>|undefined} */ - var flatLinearRing = ol.xml.pushParseAndPop(undefined, - ol.format.KML.INNER_BOUNDARY_IS_PARSERS_, node, objectStack); - if (flatLinearRing) { - var flatLinearRings = /** @type {Array.<Array.<number>>} */ - (objectStack[objectStack.length - 1]); - flatLinearRings.push(flatLinearRing); - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.outerBoundaryIsParser_ = function(node, objectStack) { - /** @type {Array.<number>|undefined} */ - var flatLinearRing = ol.xml.pushParseAndPop(undefined, - ol.format.KML.OUTER_BOUNDARY_IS_PARSERS_, node, objectStack); - if (flatLinearRing) { - var flatLinearRings = /** @type {Array.<Array.<number>>} */ - (objectStack[objectStack.length - 1]); - flatLinearRings[0] = flatLinearRing; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.LinkParser_ = function(node, objectStack) { - ol.xml.parseNode(ol.format.KML.LINK_PARSERS_, node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.whenParser_ = function(node, objectStack) { - var gxTrackObject = /** @type {ol.KMLGxTrackObject_} */ - (objectStack[objectStack.length - 1]); - var whens = gxTrackObject.whens; - var s = ol.xml.getAllTextContent(node, false); - var when = Date.parse(s); - whens.push(isNaN(when) ? 0 : when); -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.DATA_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'displayName': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'value': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.EXTENDED_DATA_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'Data': ol.format.KML.DataParser_, - 'SchemaData': ol.format.KML.SchemaDataParser_ - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.REGION_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'LatLonAltBox': ol.format.KML.LatLonAltBoxParser_, - 'Lod': ol.format.KML.LodParser_ - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.LAT_LON_ALT_BOX_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'altitudeMode': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'minAltitude': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'maxAltitude': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'north': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'south': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'east': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'west': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.LOD_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'minLodPixels': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'maxLodPixels': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'minFadeExtent': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'maxFadeExtent': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.EXTRUDE_AND_ALTITUDE_MODE_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'extrude': ol.xml.makeObjectPropertySetter(ol.format.XSD.readBoolean), - 'tessellate': ol.xml.makeObjectPropertySetter(ol.format.XSD.readBoolean), - 'altitudeMode': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.FLAT_LINEAR_RING_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'coordinates': ol.xml.makeReplacer(ol.format.KML.readFlatCoordinates_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.FLAT_LINEAR_RINGS_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'innerBoundaryIs': ol.format.KML.innerBoundaryIsParser_, - 'outerBoundaryIs': ol.format.KML.outerBoundaryIsParser_ - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.GX_TRACK_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'when': ol.format.KML.whenParser_ - }, ol.xml.makeStructureNS( - ol.format.KML.GX_NAMESPACE_URIS_, { - 'coord': ol.format.KML.gxCoordParser_ - })); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.GEOMETRY_FLAT_COORDINATES_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'coordinates': ol.xml.makeReplacer(ol.format.KML.readFlatCoordinates_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.ICON_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'href': ol.xml.makeObjectPropertySetter(ol.format.KML.readURI_) - }, ol.xml.makeStructureNS( - ol.format.KML.GX_NAMESPACE_URIS_, { - 'x': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'y': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'w': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'h': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal) - })); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.ICON_STYLE_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'Icon': ol.xml.makeObjectPropertySetter(ol.format.KML.readIcon_), - 'heading': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal), - 'hotSpot': ol.xml.makeObjectPropertySetter(ol.format.KML.readVec2_), - 'scale': ol.xml.makeObjectPropertySetter(ol.format.KML.readScale_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.INNER_BOUNDARY_IS_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'LinearRing': ol.xml.makeReplacer(ol.format.KML.readFlatLinearRing_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.LABEL_STYLE_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'color': ol.xml.makeObjectPropertySetter(ol.format.KML.readColor_), - 'scale': ol.xml.makeObjectPropertySetter(ol.format.KML.readScale_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.LINE_STYLE_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'color': ol.xml.makeObjectPropertySetter(ol.format.KML.readColor_), - 'width': ol.xml.makeObjectPropertySetter(ol.format.XSD.readDecimal) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.MULTI_GEOMETRY_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'LineString': ol.xml.makeArrayPusher(ol.format.KML.readLineString_), - 'LinearRing': ol.xml.makeArrayPusher(ol.format.KML.readLinearRing_), - 'MultiGeometry': ol.xml.makeArrayPusher(ol.format.KML.readMultiGeometry_), - 'Point': ol.xml.makeArrayPusher(ol.format.KML.readPoint_), - 'Polygon': ol.xml.makeArrayPusher(ol.format.KML.readPolygon_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.GX_MULTITRACK_GEOMETRY_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.GX_NAMESPACE_URIS_, { - 'Track': ol.xml.makeArrayPusher(ol.format.KML.readGxTrack_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.NETWORK_LINK_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'ExtendedData': ol.format.KML.ExtendedDataParser_, - 'Region': ol.format.KML.RegionParser_, - 'Link': ol.format.KML.LinkParser_, - 'address': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'description': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'name': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'open': ol.xml.makeObjectPropertySetter(ol.format.XSD.readBoolean), - 'phoneNumber': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'visibility': ol.xml.makeObjectPropertySetter(ol.format.XSD.readBoolean) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.LINK_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'href': ol.xml.makeObjectPropertySetter(ol.format.KML.readURI_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.OUTER_BOUNDARY_IS_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'LinearRing': ol.xml.makeReplacer(ol.format.KML.readFlatLinearRing_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.PAIR_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'Style': ol.xml.makeObjectPropertySetter(ol.format.KML.readStyle_), - 'key': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'styleUrl': ol.xml.makeObjectPropertySetter(ol.format.KML.readURI_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.PLACEMARK_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'ExtendedData': ol.format.KML.ExtendedDataParser_, - 'Region': ol.format.KML.RegionParser_, - 'MultiGeometry': ol.xml.makeObjectPropertySetter( - ol.format.KML.readMultiGeometry_, 'geometry'), - 'LineString': ol.xml.makeObjectPropertySetter( - ol.format.KML.readLineString_, 'geometry'), - 'LinearRing': ol.xml.makeObjectPropertySetter( - ol.format.KML.readLinearRing_, 'geometry'), - 'Point': ol.xml.makeObjectPropertySetter( - ol.format.KML.readPoint_, 'geometry'), - 'Polygon': ol.xml.makeObjectPropertySetter( - ol.format.KML.readPolygon_, 'geometry'), - 'Style': ol.xml.makeObjectPropertySetter(ol.format.KML.readStyle_), - 'StyleMap': ol.format.KML.PlacemarkStyleMapParser_, - 'address': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'description': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'name': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'open': ol.xml.makeObjectPropertySetter(ol.format.XSD.readBoolean), - 'phoneNumber': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'styleUrl': ol.xml.makeObjectPropertySetter(ol.format.KML.readURI_), - 'visibility': ol.xml.makeObjectPropertySetter(ol.format.XSD.readBoolean) - }, ol.xml.makeStructureNS( - ol.format.KML.GX_NAMESPACE_URIS_, { - 'MultiTrack': ol.xml.makeObjectPropertySetter( - ol.format.KML.readGxMultiTrack_, 'geometry'), - 'Track': ol.xml.makeObjectPropertySetter( - ol.format.KML.readGxTrack_, 'geometry') - } - )); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.POLY_STYLE_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'color': ol.xml.makeObjectPropertySetter(ol.format.KML.readColor_), - 'fill': ol.xml.makeObjectPropertySetter(ol.format.XSD.readBoolean), - 'outline': ol.xml.makeObjectPropertySetter(ol.format.XSD.readBoolean) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.SCHEMA_DATA_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'SimpleData': ol.format.KML.SimpleDataParser_ - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.STYLE_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'IconStyle': ol.format.KML.IconStyleParser_, - 'LabelStyle': ol.format.KML.LabelStyleParser_, - 'LineStyle': ol.format.KML.LineStyleParser_, - 'PolyStyle': ol.format.KML.PolyStyleParser_ - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.KML.STYLE_MAP_PARSERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'Pair': ol.format.KML.PairDataParser_ - }); - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Array.<ol.Feature>|undefined} Features. - */ -ol.format.KML.prototype.readDocumentOrFolder_ = function(node, objectStack) { - // FIXME use scope somehow - var parsersNS = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'Document': ol.xml.makeArrayExtender(this.readDocumentOrFolder_, this), - 'Folder': ol.xml.makeArrayExtender(this.readDocumentOrFolder_, this), - 'Placemark': ol.xml.makeArrayPusher(this.readPlacemark_, this), - 'Style': this.readSharedStyle_.bind(this), - 'StyleMap': this.readSharedStyleMap_.bind(this) - }); - /** @type {Array.<ol.Feature>} */ - var features = ol.xml.pushParseAndPop([], parsersNS, node, objectStack, this); - if (features) { - return features; - } else { - return undefined; - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {ol.Feature|undefined} Feature. - */ -ol.format.KML.prototype.readPlacemark_ = function(node, objectStack) { - var object = ol.xml.pushParseAndPop({'geometry': null}, - ol.format.KML.PLACEMARK_PARSERS_, node, objectStack); - if (!object) { - return undefined; - } - var feature = new ol.Feature(); - var id = node.getAttribute('id'); - if (id !== null) { - feature.setId(id); - } - var options = /** @type {olx.format.ReadOptions} */ (objectStack[0]); - - var geometry = object['geometry']; - if (geometry) { - ol.format.Feature.transformWithOptions(geometry, false, options); - } - feature.setGeometry(geometry); - delete object['geometry']; - - if (this.extractStyles_) { - var style = object['Style']; - var styleUrl = object['styleUrl']; - var styleFunction = ol.format.KML.createFeatureStyleFunction_( - style, styleUrl, this.defaultStyle_, this.sharedStyles_, - this.showPointNames_); - feature.setStyle(styleFunction); - } - delete object['Style']; - // we do not remove the styleUrl property from the object, so it - // gets stored on feature when setProperties is called - - feature.setProperties(object); - - return feature; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.prototype.readSharedStyle_ = function(node, objectStack) { - var id = node.getAttribute('id'); - if (id !== null) { - var style = ol.format.KML.readStyle_(node, objectStack); - if (style) { - var styleUri; - var baseURI = node.baseURI; - if (!baseURI || baseURI == 'about:blank') { - baseURI = window.location.href; - } - if (baseURI) { - var url = new URL('#' + id, baseURI); - styleUri = url.href; - } else { - styleUri = '#' + id; - } - this.sharedStyles_[styleUri] = style; - } - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.prototype.readSharedStyleMap_ = function(node, objectStack) { - var id = node.getAttribute('id'); - if (id === null) { - return; - } - var styleMapValue = ol.format.KML.readStyleMapValue_(node, objectStack); - if (!styleMapValue) { - return; - } - var styleUri; - var baseURI = node.baseURI; - if (!baseURI || baseURI == 'about:blank') { - baseURI = window.location.href; - } - if (baseURI) { - var url = new URL('#' + id, baseURI); - styleUri = url.href; - } else { - styleUri = '#' + id; - } - this.sharedStyles_[styleUri] = styleMapValue; -}; - - -/** - * Read the first feature from a KML source. MultiGeometries are converted into - * GeometryCollections if they are a mix of geometry types, and into MultiPoint/ - * MultiLineString/MultiPolygon if they are all of the same type. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {ol.Feature} Feature. - * @api - */ -ol.format.KML.prototype.readFeature; - - -/** - * @inheritDoc - */ -ol.format.KML.prototype.readFeatureFromNode = function(node, opt_options) { - if (!ol.array.includes(ol.format.KML.NAMESPACE_URIS_, node.namespaceURI)) { - return null; - } - var feature = this.readPlacemark_( - node, [this.getReadOptions(node, opt_options)]); - if (feature) { - return feature; - } else { - return null; - } -}; - - -/** - * Read all features from a KML source. MultiGeometries are converted into - * GeometryCollections if they are a mix of geometry types, and into MultiPoint/ - * MultiLineString/MultiPolygon if they are all of the same type. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {Array.<ol.Feature>} Features. - * @api - */ -ol.format.KML.prototype.readFeatures; - - -/** - * @inheritDoc - */ -ol.format.KML.prototype.readFeaturesFromNode = function(node, opt_options) { - if (!ol.array.includes(ol.format.KML.NAMESPACE_URIS_, node.namespaceURI)) { - return []; - } - var features; - var localName = node.localName; - if (localName == 'Document' || localName == 'Folder') { - features = this.readDocumentOrFolder_( - node, [this.getReadOptions(node, opt_options)]); - if (features) { - return features; - } else { - return []; - } - } else if (localName == 'Placemark') { - var feature = this.readPlacemark_( - node, [this.getReadOptions(node, opt_options)]); - if (feature) { - return [feature]; - } else { - return []; - } - } else if (localName == 'kml') { - features = []; - var n; - for (n = node.firstElementChild; n; n = n.nextElementSibling) { - var fs = this.readFeaturesFromNode(n, opt_options); - if (fs) { - ol.array.extend(features, fs); - } - } - return features; - } else { - return []; - } -}; - - -/** - * Read the name of the KML. - * - * @param {Document|Node|string} source Souce. - * @return {string|undefined} Name. - * @api - */ -ol.format.KML.prototype.readName = function(source) { - if (ol.xml.isDocument(source)) { - return this.readNameFromDocument(/** @type {Document} */ (source)); - } else if (ol.xml.isNode(source)) { - return this.readNameFromNode(/** @type {Node} */ (source)); - } else if (typeof source === 'string') { - var doc = ol.xml.parse(source); - return this.readNameFromDocument(doc); - } else { - return undefined; - } -}; - - -/** - * @param {Document} doc Document. - * @return {string|undefined} Name. - */ -ol.format.KML.prototype.readNameFromDocument = function(doc) { - var n; - for (n = doc.firstChild; n; n = n.nextSibling) { - if (n.nodeType == Node.ELEMENT_NODE) { - var name = this.readNameFromNode(n); - if (name) { - return name; - } - } - } - return undefined; -}; - - -/** - * @param {Node} node Node. - * @return {string|undefined} Name. - */ -ol.format.KML.prototype.readNameFromNode = function(node) { - var n; - for (n = node.firstElementChild; n; n = n.nextElementSibling) { - if (ol.array.includes(ol.format.KML.NAMESPACE_URIS_, n.namespaceURI) && - n.localName == 'name') { - return ol.format.XSD.readString(n); - } - } - for (n = node.firstElementChild; n; n = n.nextElementSibling) { - var localName = n.localName; - if (ol.array.includes(ol.format.KML.NAMESPACE_URIS_, n.namespaceURI) && - (localName == 'Document' || - localName == 'Folder' || - localName == 'Placemark' || - localName == 'kml')) { - var name = this.readNameFromNode(n); - if (name) { - return name; - } - } - } - return undefined; -}; - - -/** - * Read the network links of the KML. - * - * @param {Document|Node|string} source Source. - * @return {Array.<Object>} Network links. - * @api - */ -ol.format.KML.prototype.readNetworkLinks = function(source) { - var networkLinks = []; - if (ol.xml.isDocument(source)) { - ol.array.extend(networkLinks, this.readNetworkLinksFromDocument( - /** @type {Document} */ (source))); - } else if (ol.xml.isNode(source)) { - ol.array.extend(networkLinks, this.readNetworkLinksFromNode( - /** @type {Node} */ (source))); - } else if (typeof source === 'string') { - var doc = ol.xml.parse(source); - ol.array.extend(networkLinks, this.readNetworkLinksFromDocument(doc)); - } - return networkLinks; -}; - - -/** - * @param {Document} doc Document. - * @return {Array.<Object>} Network links. - */ -ol.format.KML.prototype.readNetworkLinksFromDocument = function(doc) { - var n, networkLinks = []; - for (n = doc.firstChild; n; n = n.nextSibling) { - if (n.nodeType == Node.ELEMENT_NODE) { - ol.array.extend(networkLinks, this.readNetworkLinksFromNode(n)); - } - } - return networkLinks; -}; - - -/** - * @param {Node} node Node. - * @return {Array.<Object>} Network links. - */ -ol.format.KML.prototype.readNetworkLinksFromNode = function(node) { - var n, networkLinks = []; - for (n = node.firstElementChild; n; n = n.nextElementSibling) { - if (ol.array.includes(ol.format.KML.NAMESPACE_URIS_, n.namespaceURI) && - n.localName == 'NetworkLink') { - var obj = ol.xml.pushParseAndPop({}, ol.format.KML.NETWORK_LINK_PARSERS_, - n, []); - networkLinks.push(obj); - } - } - for (n = node.firstElementChild; n; n = n.nextElementSibling) { - var localName = n.localName; - if (ol.array.includes(ol.format.KML.NAMESPACE_URIS_, n.namespaceURI) && - (localName == 'Document' || - localName == 'Folder' || - localName == 'kml')) { - ol.array.extend(networkLinks, this.readNetworkLinksFromNode(n)); - } - } - return networkLinks; -}; - - -/** - * Read the regions of the KML. - * - * @param {Document|Node|string} source Source. - * @return {Array.<Object>} Regions. - * @api - */ -ol.format.KML.prototype.readRegion = function(source) { - var regions = []; - if (ol.xml.isDocument(source)) { - ol.array.extend(regions, this.readRegionFromDocument( - /** @type {Document} */ (source))); - } else if (ol.xml.isNode(source)) { - ol.array.extend(regions, this.readRegionFromNode( - /** @type {Node} */ (source))); - } else if (typeof source === 'string') { - var doc = ol.xml.parse(source); - ol.array.extend(regions, this.readRegionFromDocument(doc)); - } - return regions; -}; - - -/** - * @param {Document} doc Document. - * @return {Array.<Object>} Region. - */ -ol.format.KML.prototype.readRegionFromDocument = function(doc) { - var n, regions = []; - for (n = doc.firstChild; n; n = n.nextSibling) { - if (n.nodeType == Node.ELEMENT_NODE) { - ol.array.extend(regions, this.readRegionFromNode(n)); - } - } - return regions; -}; - - -/** - * @param {Node} node Node. - * @return {Array.<Object>} Region. - * @api - */ -ol.format.KML.prototype.readRegionFromNode = function(node) { - var n, regions = []; - for (n = node.firstElementChild; n; n = n.nextElementSibling) { - if (ol.array.includes(ol.format.KML.NAMESPACE_URIS_, n.namespaceURI) && - n.localName == 'Region') { - var obj = ol.xml.pushParseAndPop({}, ol.format.KML.REGION_PARSERS_, - n, []); - regions.push(obj); - } - } - for (n = node.firstElementChild; n; n = n.nextElementSibling) { - var localName = n.localName; - if (ol.array.includes(ol.format.KML.NAMESPACE_URIS_, n.namespaceURI) && - (localName == 'Document' || - localName == 'Folder' || - localName == 'kml')) { - ol.array.extend(regions, this.readRegionFromNode(n)); - } - } - return regions; -}; - - -/** - * Read the projection from a KML source. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @return {ol.proj.Projection} Projection. - * @api - */ -ol.format.KML.prototype.readProjection; - - -/** - * @param {Node} node Node to append a TextNode with the color to. - * @param {ol.Color|string} color Color. - * @private - */ -ol.format.KML.writeColorTextNode_ = function(node, color) { - var rgba = ol.color.asArray(color); - var opacity = (rgba.length == 4) ? rgba[3] : 1; - var abgr = [opacity * 255, rgba[2], rgba[1], rgba[0]]; - var i; - for (i = 0; i < 4; ++i) { - var hex = parseInt(abgr[i], 10).toString(16); - abgr[i] = (hex.length == 1) ? '0' + hex : hex; - } - ol.format.XSD.writeStringTextNode(node, abgr.join('')); -}; - - -/** - * @param {Node} node Node to append a TextNode with the coordinates to. - * @param {Array.<number>} coordinates Coordinates. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.writeCoordinatesTextNode_ = function(node, coordinates, objectStack) { - var context = objectStack[objectStack.length - 1]; - - var layout = context['layout']; - var stride = context['stride']; - - var dimension; - if (layout == ol.geom.GeometryLayout.XY || - layout == ol.geom.GeometryLayout.XYM) { - dimension = 2; - } else if (layout == ol.geom.GeometryLayout.XYZ || - layout == ol.geom.GeometryLayout.XYZM) { - dimension = 3; - } else { - ol.asserts.assert(false, 34); // Invalid geometry layout - } - - var d, i; - var ii = coordinates.length; - var text = ''; - if (ii > 0) { - text += coordinates[0]; - for (d = 1; d < dimension; ++d) { - text += ',' + coordinates[d]; - } - for (i = stride; i < ii; i += stride) { - text += ' ' + coordinates[i]; - for (d = 1; d < dimension; ++d) { - text += ',' + coordinates[i + d]; - } - } - } - ol.format.XSD.writeStringTextNode(node, text); -}; - - -/** - * @param {Node} node Node. - * @param {{name: *, value: *}} pair Name value pair. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.writeDataNode_ = function(node, pair, objectStack) { - node.setAttribute('name', pair.name); - var /** @type {ol.XmlNodeStackItem} */ context = {node: node}; - var value = pair.value; - - if (typeof value == 'object') { - if (value !== null && value.displayName) { - ol.xml.pushSerializeAndPop(context, ol.format.KML.EXTENDEDDATA_NODE_SERIALIZERS_, - ol.xml.OBJECT_PROPERTY_NODE_FACTORY, [value.displayName], objectStack, ['displayName']); - } - - if (value !== null && value.value) { - ol.xml.pushSerializeAndPop(context, ol.format.KML.EXTENDEDDATA_NODE_SERIALIZERS_, - ol.xml.OBJECT_PROPERTY_NODE_FACTORY, [value.value], objectStack, ['value']); - } - } else { - ol.xml.pushSerializeAndPop(context, ol.format.KML.EXTENDEDDATA_NODE_SERIALIZERS_, - ol.xml.OBJECT_PROPERTY_NODE_FACTORY, [value], objectStack, ['value']); - } -}; - - -/** - * @param {Node} node Node to append a TextNode with the name to. - * @param {string} name DisplayName. - * @private - */ -ol.format.KML.writeDataNodeName_ = function(node, name) { - ol.format.XSD.writeCDATASection(node, name); -}; - - -/** - * @param {Node} node Node to append a CDATA Section with the value to. - * @param {string} value Value. - * @private - */ -ol.format.KML.writeDataNodeValue_ = function(node, value) { - ol.format.XSD.writeStringTextNode(node, value); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<ol.Feature>} features Features. - * @param {Array.<*>} objectStack Object stack. - * @this {ol.format.KML} - * @private - */ -ol.format.KML.writeDocument_ = function(node, features, objectStack) { - var /** @type {ol.XmlNodeStackItem} */ context = {node: node}; - ol.xml.pushSerializeAndPop(context, ol.format.KML.DOCUMENT_SERIALIZERS_, - ol.format.KML.DOCUMENT_NODE_FACTORY_, features, objectStack, undefined, - this); -}; - - -/** - * @param {Node} node Node. - * @param {{names: Array<string>, values: (Array<*>)}} namesAndValues Names and values. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.writeExtendedData_ = function(node, namesAndValues, objectStack) { - var /** @type {ol.XmlNodeStackItem} */ context = {node: node}; - var names = namesAndValues.names, values = namesAndValues.values; - var length = names.length; - - for (var i = 0; i < length; i++) { - ol.xml.pushSerializeAndPop(context, ol.format.KML.EXTENDEDDATA_NODE_SERIALIZERS_, - ol.format.KML.DATA_NODE_FACTORY_, [{name: names[i], value: values[i]}], objectStack); - } -}; - - -/** - * @param {Node} node Node. - * @param {Object} icon Icon object. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.writeIcon_ = function(node, icon, objectStack) { - var /** @type {ol.XmlNodeStackItem} */ context = {node: node}; - var parentNode = objectStack[objectStack.length - 1].node; - var orderedKeys = ol.format.KML.ICON_SEQUENCE_[parentNode.namespaceURI]; - var values = ol.xml.makeSequence(icon, orderedKeys); - ol.xml.pushSerializeAndPop(context, - ol.format.KML.ICON_SERIALIZERS_, ol.xml.OBJECT_PROPERTY_NODE_FACTORY, - values, objectStack, orderedKeys); - orderedKeys = - ol.format.KML.ICON_SEQUENCE_[ol.format.KML.GX_NAMESPACE_URIS_[0]]; - values = ol.xml.makeSequence(icon, orderedKeys); - ol.xml.pushSerializeAndPop(context, ol.format.KML.ICON_SERIALIZERS_, - ol.format.KML.GX_NODE_FACTORY_, values, objectStack, orderedKeys); -}; - - -/** - * @param {Node} node Node. - * @param {ol.style.Icon} style Icon style. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.writeIconStyle_ = function(node, style, objectStack) { - var /** @type {ol.XmlNodeStackItem} */ context = {node: node}; - var properties = {}; - var src = style.getSrc(); - var size = style.getSize(); - var iconImageSize = style.getImageSize(); - var iconProperties = { - 'href': src - }; - - if (size) { - iconProperties['w'] = size[0]; - iconProperties['h'] = size[1]; - var anchor = style.getAnchor(); // top-left - var origin = style.getOrigin(); // top-left - - if (origin && iconImageSize && origin[0] !== 0 && origin[1] !== size[1]) { - iconProperties['x'] = origin[0]; - iconProperties['y'] = iconImageSize[1] - (origin[1] + size[1]); - } - - if (anchor && (anchor[0] !== size[0] / 2 || anchor[1] !== size[1] / 2)) { - var /** @type {ol.KMLVec2_} */ hotSpot = { - x: anchor[0], - xunits: ol.style.IconAnchorUnits.PIXELS, - y: size[1] - anchor[1], - yunits: ol.style.IconAnchorUnits.PIXELS - }; - properties['hotSpot'] = hotSpot; - } - } - - properties['Icon'] = iconProperties; - - var scale = style.getScale(); - if (scale !== 1) { - properties['scale'] = scale; - } - - var rotation = style.getRotation(); - if (rotation !== 0) { - properties['heading'] = rotation; // 0-360 - } - - var parentNode = objectStack[objectStack.length - 1].node; - var orderedKeys = ol.format.KML.ICON_STYLE_SEQUENCE_[parentNode.namespaceURI]; - var values = ol.xml.makeSequence(properties, orderedKeys); - ol.xml.pushSerializeAndPop(context, ol.format.KML.ICON_STYLE_SERIALIZERS_, - ol.xml.OBJECT_PROPERTY_NODE_FACTORY, values, objectStack, orderedKeys); -}; - - -/** - * @param {Node} node Node. - * @param {ol.style.Text} style style. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.writeLabelStyle_ = function(node, style, objectStack) { - var /** @type {ol.XmlNodeStackItem} */ context = {node: node}; - var properties = {}; - var fill = style.getFill(); - if (fill) { - properties['color'] = fill.getColor(); - } - var scale = style.getScale(); - if (scale && scale !== 1) { - properties['scale'] = scale; - } - var parentNode = objectStack[objectStack.length - 1].node; - var orderedKeys = - ol.format.KML.LABEL_STYLE_SEQUENCE_[parentNode.namespaceURI]; - var values = ol.xml.makeSequence(properties, orderedKeys); - ol.xml.pushSerializeAndPop(context, ol.format.KML.LABEL_STYLE_SERIALIZERS_, - ol.xml.OBJECT_PROPERTY_NODE_FACTORY, values, objectStack, orderedKeys); -}; - - -/** - * @param {Node} node Node. - * @param {ol.style.Stroke} style style. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.writeLineStyle_ = function(node, style, objectStack) { - var /** @type {ol.XmlNodeStackItem} */ context = {node: node}; - var properties = { - 'color': style.getColor(), - 'width': style.getWidth() - }; - var parentNode = objectStack[objectStack.length - 1].node; - var orderedKeys = ol.format.KML.LINE_STYLE_SEQUENCE_[parentNode.namespaceURI]; - var values = ol.xml.makeSequence(properties, orderedKeys); - ol.xml.pushSerializeAndPop(context, ol.format.KML.LINE_STYLE_SERIALIZERS_, - ol.xml.OBJECT_PROPERTY_NODE_FACTORY, values, objectStack, orderedKeys); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.Geometry} geometry Geometry. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.writeMultiGeometry_ = function(node, geometry, objectStack) { - /** @type {ol.XmlNodeStackItem} */ - var context = {node: node}; - var type = geometry.getType(); - /** @type {Array.<ol.geom.Geometry>} */ - var geometries; - /** @type {function(*, Array.<*>, string=): (Node|undefined)} */ - var factory; - if (type == ol.geom.GeometryType.GEOMETRY_COLLECTION) { - geometries = /** @type {ol.geom.GeometryCollection} */ (geometry).getGeometries(); - factory = ol.format.KML.GEOMETRY_NODE_FACTORY_; - } else if (type == ol.geom.GeometryType.MULTI_POINT) { - geometries = /** @type {ol.geom.MultiPoint} */ (geometry).getPoints(); - factory = ol.format.KML.POINT_NODE_FACTORY_; - } else if (type == ol.geom.GeometryType.MULTI_LINE_STRING) { - geometries = - (/** @type {ol.geom.MultiLineString} */ (geometry)).getLineStrings(); - factory = ol.format.KML.LINE_STRING_NODE_FACTORY_; - } else if (type == ol.geom.GeometryType.MULTI_POLYGON) { - geometries = - (/** @type {ol.geom.MultiPolygon} */ (geometry)).getPolygons(); - factory = ol.format.KML.POLYGON_NODE_FACTORY_; - } else { - ol.asserts.assert(false, 39); // Unknown geometry type - } - ol.xml.pushSerializeAndPop(context, - ol.format.KML.MULTI_GEOMETRY_SERIALIZERS_, factory, - geometries, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.LinearRing} linearRing Linear ring. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.writeBoundaryIs_ = function(node, linearRing, objectStack) { - var /** @type {ol.XmlNodeStackItem} */ context = {node: node}; - ol.xml.pushSerializeAndPop(context, - ol.format.KML.BOUNDARY_IS_SERIALIZERS_, - ol.format.KML.LINEAR_RING_NODE_FACTORY_, [linearRing], objectStack); -}; - - -/** - * FIXME currently we do serialize arbitrary/custom feature properties - * (ExtendedData). - * @param {Node} node Node. - * @param {ol.Feature} feature Feature. - * @param {Array.<*>} objectStack Object stack. - * @this {ol.format.KML} - * @private - */ -ol.format.KML.writePlacemark_ = function(node, feature, objectStack) { - var /** @type {ol.XmlNodeStackItem} */ context = {node: node}; - - // set id - if (feature.getId()) { - node.setAttribute('id', feature.getId()); - } - - // serialize properties (properties unknown to KML are not serialized) - var properties = feature.getProperties(); - - // don't export these to ExtendedData - var filter = {'address': 1, 'description': 1, 'name': 1, 'open': 1, - 'phoneNumber': 1, 'styleUrl': 1, 'visibility': 1}; - filter[feature.getGeometryName()] = 1; - var keys = Object.keys(properties || {}).sort().filter(function(v) { - return !filter[v]; - }); - - if (keys.length > 0) { - var sequence = ol.xml.makeSequence(properties, keys); - var namesAndValues = {names: keys, values: sequence}; - ol.xml.pushSerializeAndPop(context, ol.format.KML.PLACEMARK_SERIALIZERS_, - ol.format.KML.EXTENDEDDATA_NODE_FACTORY_, [namesAndValues], objectStack); - } - - var styleFunction = feature.getStyleFunction(); - if (styleFunction) { - // FIXME the styles returned by the style function are supposed to be - // resolution-independent here - var styles = styleFunction.call(feature, 0); - if (styles) { - var style = Array.isArray(styles) ? styles[0] : styles; - if (this.writeStyles_) { - properties['Style'] = style; - } - var textStyle = style.getText(); - if (textStyle) { - properties['name'] = textStyle.getText(); - } - } - } - var parentNode = objectStack[objectStack.length - 1].node; - var orderedKeys = ol.format.KML.PLACEMARK_SEQUENCE_[parentNode.namespaceURI]; - var values = ol.xml.makeSequence(properties, orderedKeys); - ol.xml.pushSerializeAndPop(context, ol.format.KML.PLACEMARK_SERIALIZERS_, - ol.xml.OBJECT_PROPERTY_NODE_FACTORY, values, objectStack, orderedKeys); - - // serialize geometry - var options = /** @type {olx.format.WriteOptions} */ (objectStack[0]); - var geometry = feature.getGeometry(); - if (geometry) { - geometry = - ol.format.Feature.transformWithOptions(geometry, true, options); - } - ol.xml.pushSerializeAndPop(context, ol.format.KML.PLACEMARK_SERIALIZERS_, - ol.format.KML.GEOMETRY_NODE_FACTORY_, [geometry], objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.SimpleGeometry} geometry Geometry. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.writePrimitiveGeometry_ = function(node, geometry, objectStack) { - var flatCoordinates = geometry.getFlatCoordinates(); - var /** @type {ol.XmlNodeStackItem} */ context = {node: node}; - context['layout'] = geometry.getLayout(); - context['stride'] = geometry.getStride(); - - // serialize properties (properties unknown to KML are not serialized) - var properties = geometry.getProperties(); - properties.coordinates = flatCoordinates; - - var parentNode = objectStack[objectStack.length - 1].node; - var orderedKeys = ol.format.KML.PRIMITIVE_GEOMETRY_SEQUENCE_[parentNode.namespaceURI]; - var values = ol.xml.makeSequence(properties, orderedKeys); - ol.xml.pushSerializeAndPop(context, ol.format.KML.PRIMITIVE_GEOMETRY_SERIALIZERS_, - ol.xml.OBJECT_PROPERTY_NODE_FACTORY, values, objectStack, orderedKeys); -}; - - -/** - * @param {Node} node Node. - * @param {ol.geom.Polygon} polygon Polygon. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.writePolygon_ = function(node, polygon, objectStack) { - var linearRings = polygon.getLinearRings(); - var outerRing = linearRings.shift(); - var /** @type {ol.XmlNodeStackItem} */ context = {node: node}; - // inner rings - ol.xml.pushSerializeAndPop(context, - ol.format.KML.POLYGON_SERIALIZERS_, - ol.format.KML.INNER_BOUNDARY_NODE_FACTORY_, - linearRings, objectStack); - // outer ring - ol.xml.pushSerializeAndPop(context, - ol.format.KML.POLYGON_SERIALIZERS_, - ol.format.KML.OUTER_BOUNDARY_NODE_FACTORY_, - [outerRing], objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {ol.style.Fill} style Style. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.writePolyStyle_ = function(node, style, objectStack) { - var /** @type {ol.XmlNodeStackItem} */ context = {node: node}; - ol.xml.pushSerializeAndPop(context, ol.format.KML.POLY_STYLE_SERIALIZERS_, - ol.format.KML.COLOR_NODE_FACTORY_, [style.getColor()], objectStack); -}; - - -/** - * @param {Node} node Node to append a TextNode with the scale to. - * @param {number|undefined} scale Scale. - * @private - */ -ol.format.KML.writeScaleTextNode_ = function(node, scale) { - // the Math is to remove any excess decimals created by float arithmetic - ol.format.XSD.writeDecimalTextNode(node, - Math.round(scale * 1e6) / 1e6); -}; - - -/** - * @param {Node} node Node. - * @param {ol.style.Style} style Style. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.KML.writeStyle_ = function(node, style, objectStack) { - var /** @type {ol.XmlNodeStackItem} */ context = {node: node}; - var properties = {}; - var fillStyle = style.getFill(); - var strokeStyle = style.getStroke(); - var imageStyle = style.getImage(); - var textStyle = style.getText(); - if (imageStyle instanceof ol.style.Icon) { - properties['IconStyle'] = imageStyle; - } - if (textStyle) { - properties['LabelStyle'] = textStyle; - } - if (strokeStyle) { - properties['LineStyle'] = strokeStyle; - } - if (fillStyle) { - properties['PolyStyle'] = fillStyle; - } - var parentNode = objectStack[objectStack.length - 1].node; - var orderedKeys = ol.format.KML.STYLE_SEQUENCE_[parentNode.namespaceURI]; - var values = ol.xml.makeSequence(properties, orderedKeys); - ol.xml.pushSerializeAndPop(context, ol.format.KML.STYLE_SERIALIZERS_, - ol.xml.OBJECT_PROPERTY_NODE_FACTORY, values, objectStack, orderedKeys); -}; - - -/** - * @param {Node} node Node to append a TextNode with the Vec2 to. - * @param {ol.KMLVec2_} vec2 Vec2. - * @private - */ -ol.format.KML.writeVec2_ = function(node, vec2) { - node.setAttribute('x', vec2.x); - node.setAttribute('y', vec2.y); - node.setAttribute('xunits', vec2.xunits); - node.setAttribute('yunits', vec2.yunits); -}; - - -/** - * @const - * @type {Object.<string, Array.<string>>} - * @private - */ -ol.format.KML.KML_SEQUENCE_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, [ - 'Document', 'Placemark' - ]); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.KML.KML_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'Document': ol.xml.makeChildAppender(ol.format.KML.writeDocument_), - 'Placemark': ol.xml.makeChildAppender(ol.format.KML.writePlacemark_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.KML.DOCUMENT_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'Placemark': ol.xml.makeChildAppender(ol.format.KML.writePlacemark_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.KML.EXTENDEDDATA_NODE_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'Data': ol.xml.makeChildAppender(ol.format.KML.writeDataNode_), - 'value': ol.xml.makeChildAppender(ol.format.KML.writeDataNodeValue_), - 'displayName': ol.xml.makeChildAppender(ol.format.KML.writeDataNodeName_) - }); - - -/** - * @const - * @type {Object.<string, string>} - * @private - */ -ol.format.KML.GEOMETRY_TYPE_TO_NODENAME_ = { - 'Point': 'Point', - 'LineString': 'LineString', - 'LinearRing': 'LinearRing', - 'Polygon': 'Polygon', - 'MultiPoint': 'MultiGeometry', - 'MultiLineString': 'MultiGeometry', - 'MultiPolygon': 'MultiGeometry', - 'GeometryCollection': 'MultiGeometry' -}; - -/** - * @const - * @type {Object.<string, Array.<string>>} - * @private - */ -ol.format.KML.ICON_SEQUENCE_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, [ - 'href' - ], - ol.xml.makeStructureNS(ol.format.KML.GX_NAMESPACE_URIS_, [ - 'x', 'y', 'w', 'h' - ])); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.KML.ICON_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'href': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode) - }, ol.xml.makeStructureNS( - ol.format.KML.GX_NAMESPACE_URIS_, { - 'x': ol.xml.makeChildAppender(ol.format.XSD.writeDecimalTextNode), - 'y': ol.xml.makeChildAppender(ol.format.XSD.writeDecimalTextNode), - 'w': ol.xml.makeChildAppender(ol.format.XSD.writeDecimalTextNode), - 'h': ol.xml.makeChildAppender(ol.format.XSD.writeDecimalTextNode) - })); - - -/** - * @const - * @type {Object.<string, Array.<string>>} - * @private - */ -ol.format.KML.ICON_STYLE_SEQUENCE_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, [ - 'scale', 'heading', 'Icon', 'hotSpot' - ]); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.KML.ICON_STYLE_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'Icon': ol.xml.makeChildAppender(ol.format.KML.writeIcon_), - 'heading': ol.xml.makeChildAppender(ol.format.XSD.writeDecimalTextNode), - 'hotSpot': ol.xml.makeChildAppender(ol.format.KML.writeVec2_), - 'scale': ol.xml.makeChildAppender(ol.format.KML.writeScaleTextNode_) - }); - - -/** - * @const - * @type {Object.<string, Array.<string>>} - * @private - */ -ol.format.KML.LABEL_STYLE_SEQUENCE_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, [ - 'color', 'scale' - ]); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.KML.LABEL_STYLE_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'color': ol.xml.makeChildAppender(ol.format.KML.writeColorTextNode_), - 'scale': ol.xml.makeChildAppender(ol.format.KML.writeScaleTextNode_) - }); - - -/** - * @const - * @type {Object.<string, Array.<string>>} - * @private - */ -ol.format.KML.LINE_STYLE_SEQUENCE_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, [ - 'color', 'width' - ]); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.KML.LINE_STYLE_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'color': ol.xml.makeChildAppender(ol.format.KML.writeColorTextNode_), - 'width': ol.xml.makeChildAppender(ol.format.XSD.writeDecimalTextNode) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.KML.BOUNDARY_IS_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'LinearRing': ol.xml.makeChildAppender( - ol.format.KML.writePrimitiveGeometry_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.KML.MULTI_GEOMETRY_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'LineString': ol.xml.makeChildAppender( - ol.format.KML.writePrimitiveGeometry_), - 'Point': ol.xml.makeChildAppender( - ol.format.KML.writePrimitiveGeometry_), - 'Polygon': ol.xml.makeChildAppender(ol.format.KML.writePolygon_), - 'GeometryCollection': ol.xml.makeChildAppender( - ol.format.KML.writeMultiGeometry_) - }); - - -/** - * @const - * @type {Object.<string, Array.<string>>} - * @private - */ -ol.format.KML.PLACEMARK_SEQUENCE_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, [ - 'name', 'open', 'visibility', 'address', 'phoneNumber', 'description', - 'styleUrl', 'Style' - ]); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.KML.PLACEMARK_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'ExtendedData': ol.xml.makeChildAppender( - ol.format.KML.writeExtendedData_), - 'MultiGeometry': ol.xml.makeChildAppender( - ol.format.KML.writeMultiGeometry_), - 'LineString': ol.xml.makeChildAppender( - ol.format.KML.writePrimitiveGeometry_), - 'LinearRing': ol.xml.makeChildAppender( - ol.format.KML.writePrimitiveGeometry_), - 'Point': ol.xml.makeChildAppender( - ol.format.KML.writePrimitiveGeometry_), - 'Polygon': ol.xml.makeChildAppender(ol.format.KML.writePolygon_), - 'Style': ol.xml.makeChildAppender(ol.format.KML.writeStyle_), - 'address': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'description': ol.xml.makeChildAppender( - ol.format.XSD.writeStringTextNode), - 'name': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'open': ol.xml.makeChildAppender(ol.format.XSD.writeBooleanTextNode), - 'phoneNumber': ol.xml.makeChildAppender( - ol.format.XSD.writeStringTextNode), - 'styleUrl': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'visibility': ol.xml.makeChildAppender( - ol.format.XSD.writeBooleanTextNode) - }); - - -/** - * @const - * @type {Object.<string, Array.<string>>} - * @private - */ -ol.format.KML.PRIMITIVE_GEOMETRY_SEQUENCE_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, [ - 'extrude', 'tessellate', 'altitudeMode', 'coordinates' - ]); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.KML.PRIMITIVE_GEOMETRY_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'extrude': ol.xml.makeChildAppender(ol.format.XSD.writeBooleanTextNode), - 'tessellate': ol.xml.makeChildAppender(ol.format.XSD.writeBooleanTextNode), - 'altitudeMode': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode), - 'coordinates': ol.xml.makeChildAppender( - ol.format.KML.writeCoordinatesTextNode_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.KML.POLYGON_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'outerBoundaryIs': ol.xml.makeChildAppender( - ol.format.KML.writeBoundaryIs_), - 'innerBoundaryIs': ol.xml.makeChildAppender( - ol.format.KML.writeBoundaryIs_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.KML.POLY_STYLE_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'color': ol.xml.makeChildAppender(ol.format.KML.writeColorTextNode_) - }); - - -/** - * @const - * @type {Object.<string, Array.<string>>} - * @private - */ -ol.format.KML.STYLE_SEQUENCE_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, [ - 'IconStyle', 'LabelStyle', 'LineStyle', 'PolyStyle' - ]); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.KML.STYLE_SERIALIZERS_ = ol.xml.makeStructureNS( - ol.format.KML.NAMESPACE_URIS_, { - 'IconStyle': ol.xml.makeChildAppender(ol.format.KML.writeIconStyle_), - 'LabelStyle': ol.xml.makeChildAppender(ol.format.KML.writeLabelStyle_), - 'LineStyle': ol.xml.makeChildAppender(ol.format.KML.writeLineStyle_), - 'PolyStyle': ol.xml.makeChildAppender(ol.format.KML.writePolyStyle_) - }); - - -/** - * @const - * @param {*} value Value. - * @param {Array.<*>} objectStack Object stack. - * @param {string=} opt_nodeName Node name. - * @return {Node|undefined} Node. - * @private - */ -ol.format.KML.GX_NODE_FACTORY_ = function(value, objectStack, opt_nodeName) { - return ol.xml.createElementNS(ol.format.KML.GX_NAMESPACE_URIS_[0], - 'gx:' + opt_nodeName); -}; - - -/** - * @const - * @param {*} value Value. - * @param {Array.<*>} objectStack Object stack. - * @param {string=} opt_nodeName Node name. - * @return {Node|undefined} Node. - * @private - */ -ol.format.KML.DOCUMENT_NODE_FACTORY_ = function(value, objectStack, - opt_nodeName) { - var parentNode = objectStack[objectStack.length - 1].node; - return ol.xml.createElementNS(parentNode.namespaceURI, 'Placemark'); -}; - - -/** - * @const - * @param {*} value Value. - * @param {Array.<*>} objectStack Object stack. - * @param {string=} opt_nodeName Node name. - * @return {Node|undefined} Node. - * @private - */ -ol.format.KML.GEOMETRY_NODE_FACTORY_ = function(value, objectStack, - opt_nodeName) { - if (value) { - var parentNode = objectStack[objectStack.length - 1].node; - return ol.xml.createElementNS(parentNode.namespaceURI, - ol.format.KML.GEOMETRY_TYPE_TO_NODENAME_[/** @type {ol.geom.Geometry} */ (value).getType()]); - } -}; - - -/** - * A factory for creating coordinates nodes. - * @const - * @type {function(*, Array.<*>, string=): (Node|undefined)} - * @private - */ -ol.format.KML.COLOR_NODE_FACTORY_ = ol.xml.makeSimpleNodeFactory('color'); - - -/** - * A factory for creating Data nodes. - * @const - * @type {function(*, Array.<*>): (Node|undefined)} - * @private - */ -ol.format.KML.DATA_NODE_FACTORY_ = - ol.xml.makeSimpleNodeFactory('Data'); - - -/** - * A factory for creating ExtendedData nodes. - * @const - * @type {function(*, Array.<*>): (Node|undefined)} - * @private - */ -ol.format.KML.EXTENDEDDATA_NODE_FACTORY_ = - ol.xml.makeSimpleNodeFactory('ExtendedData'); - - -/** - * A factory for creating innerBoundaryIs nodes. - * @const - * @type {function(*, Array.<*>, string=): (Node|undefined)} - * @private - */ -ol.format.KML.INNER_BOUNDARY_NODE_FACTORY_ = - ol.xml.makeSimpleNodeFactory('innerBoundaryIs'); - - -/** - * A factory for creating Point nodes. - * @const - * @type {function(*, Array.<*>, string=): (Node|undefined)} - * @private - */ -ol.format.KML.POINT_NODE_FACTORY_ = - ol.xml.makeSimpleNodeFactory('Point'); - - -/** - * A factory for creating LineString nodes. - * @const - * @type {function(*, Array.<*>, string=): (Node|undefined)} - * @private - */ -ol.format.KML.LINE_STRING_NODE_FACTORY_ = - ol.xml.makeSimpleNodeFactory('LineString'); - - -/** - * A factory for creating LinearRing nodes. - * @const - * @type {function(*, Array.<*>, string=): (Node|undefined)} - * @private - */ -ol.format.KML.LINEAR_RING_NODE_FACTORY_ = - ol.xml.makeSimpleNodeFactory('LinearRing'); - - -/** - * A factory for creating Polygon nodes. - * @const - * @type {function(*, Array.<*>, string=): (Node|undefined)} - * @private - */ -ol.format.KML.POLYGON_NODE_FACTORY_ = - ol.xml.makeSimpleNodeFactory('Polygon'); - - -/** - * A factory for creating outerBoundaryIs nodes. - * @const - * @type {function(*, Array.<*>, string=): (Node|undefined)} - * @private - */ -ol.format.KML.OUTER_BOUNDARY_NODE_FACTORY_ = - ol.xml.makeSimpleNodeFactory('outerBoundaryIs'); - - -/** - * Encode an array of features in the KML format. GeometryCollections, MultiPoints, - * MultiLineStrings, and MultiPolygons are output as MultiGeometries. - * - * @function - * @param {Array.<ol.Feature>} features Features. - * @param {olx.format.WriteOptions=} opt_options Options. - * @return {string} Result. - * @api - */ -ol.format.KML.prototype.writeFeatures; - - -/** - * Encode an array of features in the KML format as an XML node. GeometryCollections, - * MultiPoints, MultiLineStrings, and MultiPolygons are output as MultiGeometries. - * - * @param {Array.<ol.Feature>} features Features. - * @param {olx.format.WriteOptions=} opt_options Options. - * @return {Node} Node. - * @override - * @api - */ -ol.format.KML.prototype.writeFeaturesNode = function(features, opt_options) { - opt_options = this.adaptOptions(opt_options); - var kml = ol.xml.createElementNS(ol.format.KML.NAMESPACE_URIS_[4], 'kml'); - var xmlnsUri = 'http://www.w3.org/2000/xmlns/'; - var xmlSchemaInstanceUri = 'http://www.w3.org/2001/XMLSchema-instance'; - ol.xml.setAttributeNS(kml, xmlnsUri, 'xmlns:gx', - ol.format.KML.GX_NAMESPACE_URIS_[0]); - ol.xml.setAttributeNS(kml, xmlnsUri, 'xmlns:xsi', xmlSchemaInstanceUri); - ol.xml.setAttributeNS(kml, xmlSchemaInstanceUri, 'xsi:schemaLocation', - ol.format.KML.SCHEMA_LOCATION_); - - var /** @type {ol.XmlNodeStackItem} */ context = {node: kml}; - var properties = {}; - if (features.length > 1) { - properties['Document'] = features; - } else if (features.length == 1) { - properties['Placemark'] = features[0]; - } - var orderedKeys = ol.format.KML.KML_SEQUENCE_[kml.namespaceURI]; - var values = ol.xml.makeSequence(properties, orderedKeys); - ol.xml.pushSerializeAndPop(context, ol.format.KML.KML_SERIALIZERS_, - ol.xml.OBJECT_PROPERTY_NODE_FACTORY, values, [opt_options], orderedKeys, - this); - return kml; -}; - - -/** - * @fileoverview - * @suppress {accessControls, ambiguousFunctionDecl, checkDebuggerStatement, checkRegExp, checkTypes, checkVars, const, constantProperty, deprecated, duplicate, es5Strict, fileoverviewTags, missingProperties, nonStandardJsDocs, strictModuleDepCheck, suspiciousCode, undefinedNames, undefinedVars, unknownDefines, unusedLocalVariables, uselessCode, visibility} - */ -goog.provide('ol.ext.PBF'); - -/** @typedef {function(*)} */ -ol.ext.PBF = function() {}; - -(function() {(function (exports) { -'use strict'; - -var read = function (buffer, offset, isLE, mLen, nBytes) { - var e, m; - var eLen = nBytes * 8 - mLen - 1; - var eMax = (1 << eLen) - 1; - var eBias = eMax >> 1; - var nBits = -7; - var i = isLE ? (nBytes - 1) : 0; - var d = isLE ? -1 : 1; - var s = buffer[offset + i]; - i += d; - e = s & ((1 << (-nBits)) - 1); - s >>= (-nBits); - nBits += eLen; - for (; nBits > 0; e = e * 256 + buffer[offset + i], i += d, nBits -= 8) {} - m = e & ((1 << (-nBits)) - 1); - e >>= (-nBits); - nBits += mLen; - for (; nBits > 0; m = m * 256 + buffer[offset + i], i += d, nBits -= 8) {} - if (e === 0) { - e = 1 - eBias; - } else if (e === eMax) { - return m ? NaN : ((s ? -1 : 1) * Infinity) - } else { - m = m + Math.pow(2, mLen); - e = e - eBias; - } - return (s ? -1 : 1) * m * Math.pow(2, e - mLen) -}; -var write = function (buffer, value, offset, isLE, mLen, nBytes) { - var e, m, c; - var eLen = nBytes * 8 - mLen - 1; - var eMax = (1 << eLen) - 1; - var eBias = eMax >> 1; - var rt = (mLen === 23 ? Math.pow(2, -24) - Math.pow(2, -77) : 0); - var i = isLE ? 0 : (nBytes - 1); - var d = isLE ? 1 : -1; - var s = value < 0 || (value === 0 && 1 / value < 0) ? 1 : 0; - value = Math.abs(value); - if (isNaN(value) || value === Infinity) { - m = isNaN(value) ? 1 : 0; - e = eMax; - } else { - e = Math.floor(Math.log(value) / Math.LN2); - if (value * (c = Math.pow(2, -e)) < 1) { - e--; - c *= 2; - } - if (e + eBias >= 1) { - value += rt / c; - } else { - value += rt * Math.pow(2, 1 - eBias); - } - if (value * c >= 2) { - e++; - c /= 2; - } - if (e + eBias >= eMax) { - m = 0; - e = eMax; - } else if (e + eBias >= 1) { - m = (value * c - 1) * Math.pow(2, mLen); - e = e + eBias; - } else { - m = value * Math.pow(2, eBias - 1) * Math.pow(2, mLen); - e = 0; - } - } - for (; mLen >= 8; buffer[offset + i] = m & 0xff, i += d, m /= 256, mLen -= 8) {} - e = (e << mLen) | m; - eLen += mLen; - for (; eLen > 0; buffer[offset + i] = e & 0xff, i += d, e /= 256, eLen -= 8) {} - buffer[offset + i - d] |= s * 128; -}; -var ieee754 = { - read: read, - write: write -}; - -'use strict'; -var pbf = Pbf; -function Pbf(buf) { - this.buf = ArrayBuffer.isView && ArrayBuffer.isView(buf) ? buf : new Uint8Array(buf || 0); - this.pos = 0; - this.type = 0; - this.length = this.buf.length; -} -Pbf.Varint = 0; -Pbf.Fixed64 = 1; -Pbf.Bytes = 2; -Pbf.Fixed32 = 5; -var SHIFT_LEFT_32 = (1 << 16) * (1 << 16); -var SHIFT_RIGHT_32 = 1 / SHIFT_LEFT_32; -Pbf.prototype = { - destroy: function() { - this.buf = null; - }, - readFields: function(readField, result, end) { - end = end || this.length; - while (this.pos < end) { - var val = this.readVarint(), - tag = val >> 3, - startPos = this.pos; - this.type = val & 0x7; - readField(tag, result, this); - if (this.pos === startPos) this.skip(val); - } - return result; - }, - readMessage: function(readField, result) { - return this.readFields(readField, result, this.readVarint() + this.pos); - }, - readFixed32: function() { - var val = readUInt32(this.buf, this.pos); - this.pos += 4; - return val; - }, - readSFixed32: function() { - var val = readInt32(this.buf, this.pos); - this.pos += 4; - return val; - }, - readFixed64: function() { - var val = readUInt32(this.buf, this.pos) + readUInt32(this.buf, this.pos + 4) * SHIFT_LEFT_32; - this.pos += 8; - return val; - }, - readSFixed64: function() { - var val = readUInt32(this.buf, this.pos) + readInt32(this.buf, this.pos + 4) * SHIFT_LEFT_32; - this.pos += 8; - return val; - }, - readFloat: function() { - var val = ieee754.read(this.buf, this.pos, true, 23, 4); - this.pos += 4; - return val; - }, - readDouble: function() { - var val = ieee754.read(this.buf, this.pos, true, 52, 8); - this.pos += 8; - return val; - }, - readVarint: function(isSigned) { - var buf = this.buf, - val, b; - b = buf[this.pos++]; val = b & 0x7f; if (b < 0x80) return val; - b = buf[this.pos++]; val |= (b & 0x7f) << 7; if (b < 0x80) return val; - b = buf[this.pos++]; val |= (b & 0x7f) << 14; if (b < 0x80) return val; - b = buf[this.pos++]; val |= (b & 0x7f) << 21; if (b < 0x80) return val; - b = buf[this.pos]; val |= (b & 0x0f) << 28; - return readVarintRemainder(val, isSigned, this); - }, - readVarint64: function() { - return this.readVarint(true); - }, - readSVarint: function() { - var num = this.readVarint(); - return num % 2 === 1 ? (num + 1) / -2 : num / 2; - }, - readBoolean: function() { - return Boolean(this.readVarint()); - }, - readString: function() { - var end = this.readVarint() + this.pos, - str = readUtf8(this.buf, this.pos, end); - this.pos = end; - return str; - }, - readBytes: function() { - var end = this.readVarint() + this.pos, - buffer = this.buf.subarray(this.pos, end); - this.pos = end; - return buffer; - }, - readPackedVarint: function(arr, isSigned) { - var end = readPackedEnd(this); - arr = arr || []; - while (this.pos < end) arr.push(this.readVarint(isSigned)); - return arr; - }, - readPackedSVarint: function(arr) { - var end = readPackedEnd(this); - arr = arr || []; - while (this.pos < end) arr.push(this.readSVarint()); - return arr; - }, - readPackedBoolean: function(arr) { - var end = readPackedEnd(this); - arr = arr || []; - while (this.pos < end) arr.push(this.readBoolean()); - return arr; - }, - readPackedFloat: function(arr) { - var end = readPackedEnd(this); - arr = arr || []; - while (this.pos < end) arr.push(this.readFloat()); - return arr; - }, - readPackedDouble: function(arr) { - var end = readPackedEnd(this); - arr = arr || []; - while (this.pos < end) arr.push(this.readDouble()); - return arr; - }, - readPackedFixed32: function(arr) { - var end = readPackedEnd(this); - arr = arr || []; - while (this.pos < end) arr.push(this.readFixed32()); - return arr; - }, - readPackedSFixed32: function(arr) { - var end = readPackedEnd(this); - arr = arr || []; - while (this.pos < end) arr.push(this.readSFixed32()); - return arr; - }, - readPackedFixed64: function(arr) { - var end = readPackedEnd(this); - arr = arr || []; - while (this.pos < end) arr.push(this.readFixed64()); - return arr; - }, - readPackedSFixed64: function(arr) { - var end = readPackedEnd(this); - arr = arr || []; - while (this.pos < end) arr.push(this.readSFixed64()); - return arr; - }, - skip: function(val) { - var type = val & 0x7; - if (type === Pbf.Varint) while (this.buf[this.pos++] > 0x7f) {} - else if (type === Pbf.Bytes) this.pos = this.readVarint() + this.pos; - else if (type === Pbf.Fixed32) this.pos += 4; - else if (type === Pbf.Fixed64) this.pos += 8; - else throw new Error('Unimplemented type: ' + type); - }, - writeTag: function(tag, type) { - this.writeVarint((tag << 3) | type); - }, - realloc: function(min) { - var length = this.length || 16; - while (length < this.pos + min) length *= 2; - if (length !== this.length) { - var buf = new Uint8Array(length); - buf.set(this.buf); - this.buf = buf; - this.length = length; - } - }, - finish: function() { - this.length = this.pos; - this.pos = 0; - return this.buf.subarray(0, this.length); - }, - writeFixed32: function(val) { - this.realloc(4); - writeInt32(this.buf, val, this.pos); - this.pos += 4; - }, - writeSFixed32: function(val) { - this.realloc(4); - writeInt32(this.buf, val, this.pos); - this.pos += 4; - }, - writeFixed64: function(val) { - this.realloc(8); - writeInt32(this.buf, val & -1, this.pos); - writeInt32(this.buf, Math.floor(val * SHIFT_RIGHT_32), this.pos + 4); - this.pos += 8; - }, - writeSFixed64: function(val) { - this.realloc(8); - writeInt32(this.buf, val & -1, this.pos); - writeInt32(this.buf, Math.floor(val * SHIFT_RIGHT_32), this.pos + 4); - this.pos += 8; - }, - writeVarint: function(val) { - val = +val || 0; - if (val > 0xfffffff || val < 0) { - writeBigVarint(val, this); - return; - } - this.realloc(4); - this.buf[this.pos++] = val & 0x7f | (val > 0x7f ? 0x80 : 0); if (val <= 0x7f) return; - this.buf[this.pos++] = ((val >>>= 7) & 0x7f) | (val > 0x7f ? 0x80 : 0); if (val <= 0x7f) return; - this.buf[this.pos++] = ((val >>>= 7) & 0x7f) | (val > 0x7f ? 0x80 : 0); if (val <= 0x7f) return; - this.buf[this.pos++] = (val >>> 7) & 0x7f; - }, - writeSVarint: function(val) { - this.writeVarint(val < 0 ? -val * 2 - 1 : val * 2); - }, - writeBoolean: function(val) { - this.writeVarint(Boolean(val)); - }, - writeString: function(str) { - str = String(str); - this.realloc(str.length * 4); - this.pos++; - var startPos = this.pos; - this.pos = writeUtf8(this.buf, str, this.pos); - var len = this.pos - startPos; - if (len >= 0x80) makeRoomForExtraLength(startPos, len, this); - this.pos = startPos - 1; - this.writeVarint(len); - this.pos += len; - }, - writeFloat: function(val) { - this.realloc(4); - ieee754.write(this.buf, val, this.pos, true, 23, 4); - this.pos += 4; - }, - writeDouble: function(val) { - this.realloc(8); - ieee754.write(this.buf, val, this.pos, true, 52, 8); - this.pos += 8; - }, - writeBytes: function(buffer) { - var len = buffer.length; - this.writeVarint(len); - this.realloc(len); - for (var i = 0; i < len; i++) this.buf[this.pos++] = buffer[i]; - }, - writeRawMessage: function(fn, obj) { - this.pos++; - var startPos = this.pos; - fn(obj, this); - var len = this.pos - startPos; - if (len >= 0x80) makeRoomForExtraLength(startPos, len, this); - this.pos = startPos - 1; - this.writeVarint(len); - this.pos += len; - }, - writeMessage: function(tag, fn, obj) { - this.writeTag(tag, Pbf.Bytes); - this.writeRawMessage(fn, obj); - }, - writePackedVarint: function(tag, arr) { this.writeMessage(tag, writePackedVarint, arr); }, - writePackedSVarint: function(tag, arr) { this.writeMessage(tag, writePackedSVarint, arr); }, - writePackedBoolean: function(tag, arr) { this.writeMessage(tag, writePackedBoolean, arr); }, - writePackedFloat: function(tag, arr) { this.writeMessage(tag, writePackedFloat, arr); }, - writePackedDouble: function(tag, arr) { this.writeMessage(tag, writePackedDouble, arr); }, - writePackedFixed32: function(tag, arr) { this.writeMessage(tag, writePackedFixed32, arr); }, - writePackedSFixed32: function(tag, arr) { this.writeMessage(tag, writePackedSFixed32, arr); }, - writePackedFixed64: function(tag, arr) { this.writeMessage(tag, writePackedFixed64, arr); }, - writePackedSFixed64: function(tag, arr) { this.writeMessage(tag, writePackedSFixed64, arr); }, - writeBytesField: function(tag, buffer) { - this.writeTag(tag, Pbf.Bytes); - this.writeBytes(buffer); - }, - writeFixed32Field: function(tag, val) { - this.writeTag(tag, Pbf.Fixed32); - this.writeFixed32(val); - }, - writeSFixed32Field: function(tag, val) { - this.writeTag(tag, Pbf.Fixed32); - this.writeSFixed32(val); - }, - writeFixed64Field: function(tag, val) { - this.writeTag(tag, Pbf.Fixed64); - this.writeFixed64(val); - }, - writeSFixed64Field: function(tag, val) { - this.writeTag(tag, Pbf.Fixed64); - this.writeSFixed64(val); - }, - writeVarintField: function(tag, val) { - this.writeTag(tag, Pbf.Varint); - this.writeVarint(val); - }, - writeSVarintField: function(tag, val) { - this.writeTag(tag, Pbf.Varint); - this.writeSVarint(val); - }, - writeStringField: function(tag, str) { - this.writeTag(tag, Pbf.Bytes); - this.writeString(str); - }, - writeFloatField: function(tag, val) { - this.writeTag(tag, Pbf.Fixed32); - this.writeFloat(val); - }, - writeDoubleField: function(tag, val) { - this.writeTag(tag, Pbf.Fixed64); - this.writeDouble(val); - }, - writeBooleanField: function(tag, val) { - this.writeVarintField(tag, Boolean(val)); - } -}; -function readVarintRemainder(l, s, p) { - var buf = p.buf, - h, b; - b = buf[p.pos++]; h = (b & 0x70) >> 4; if (b < 0x80) return toNum(l, h, s); - b = buf[p.pos++]; h |= (b & 0x7f) << 3; if (b < 0x80) return toNum(l, h, s); - b = buf[p.pos++]; h |= (b & 0x7f) << 10; if (b < 0x80) return toNum(l, h, s); - b = buf[p.pos++]; h |= (b & 0x7f) << 17; if (b < 0x80) return toNum(l, h, s); - b = buf[p.pos++]; h |= (b & 0x7f) << 24; if (b < 0x80) return toNum(l, h, s); - b = buf[p.pos++]; h |= (b & 0x01) << 31; if (b < 0x80) return toNum(l, h, s); - throw new Error('Expected varint not more than 10 bytes'); -} -function readPackedEnd(pbf) { - return pbf.type === Pbf.Bytes ? - pbf.readVarint() + pbf.pos : pbf.pos + 1; -} -function toNum(low, high, isSigned) { - if (isSigned) { - return high * 0x100000000 + (low >>> 0); - } - return ((high >>> 0) * 0x100000000) + (low >>> 0); -} -function writeBigVarint(val, pbf) { - var low, high; - if (val >= 0) { - low = (val % 0x100000000) | 0; - high = (val / 0x100000000) | 0; - } else { - low = ~(-val % 0x100000000); - high = ~(-val / 0x100000000); - if (low ^ 0xffffffff) { - low = (low + 1) | 0; - } else { - low = 0; - high = (high + 1) | 0; - } - } - if (val >= 0x10000000000000000 || val < -0x10000000000000000) { - throw new Error('Given varint doesn\'t fit into 10 bytes'); - } - pbf.realloc(10); - writeBigVarintLow(low, high, pbf); - writeBigVarintHigh(high, pbf); -} -function writeBigVarintLow(low, high, pbf) { - pbf.buf[pbf.pos++] = low & 0x7f | 0x80; low >>>= 7; - pbf.buf[pbf.pos++] = low & 0x7f | 0x80; low >>>= 7; - pbf.buf[pbf.pos++] = low & 0x7f | 0x80; low >>>= 7; - pbf.buf[pbf.pos++] = low & 0x7f | 0x80; low >>>= 7; - pbf.buf[pbf.pos] = low & 0x7f; -} -function writeBigVarintHigh(high, pbf) { - var lsb = (high & 0x07) << 4; - pbf.buf[pbf.pos++] |= lsb | ((high >>>= 3) ? 0x80 : 0); if (!high) return; - pbf.buf[pbf.pos++] = high & 0x7f | ((high >>>= 7) ? 0x80 : 0); if (!high) return; - pbf.buf[pbf.pos++] = high & 0x7f | ((high >>>= 7) ? 0x80 : 0); if (!high) return; - pbf.buf[pbf.pos++] = high & 0x7f | ((high >>>= 7) ? 0x80 : 0); if (!high) return; - pbf.buf[pbf.pos++] = high & 0x7f | ((high >>>= 7) ? 0x80 : 0); if (!high) return; - pbf.buf[pbf.pos++] = high & 0x7f; -} -function makeRoomForExtraLength(startPos, len, pbf) { - var extraLen = - len <= 0x3fff ? 1 : - len <= 0x1fffff ? 2 : - len <= 0xfffffff ? 3 : Math.ceil(Math.log(len) / (Math.LN2 * 7)); - pbf.realloc(extraLen); - for (var i = pbf.pos - 1; i >= startPos; i--) pbf.buf[i + extraLen] = pbf.buf[i]; -} -function writePackedVarint(arr, pbf) { for (var i = 0; i < arr.length; i++) pbf.writeVarint(arr[i]); } -function writePackedSVarint(arr, pbf) { for (var i = 0; i < arr.length; i++) pbf.writeSVarint(arr[i]); } -function writePackedFloat(arr, pbf) { for (var i = 0; i < arr.length; i++) pbf.writeFloat(arr[i]); } -function writePackedDouble(arr, pbf) { for (var i = 0; i < arr.length; i++) pbf.writeDouble(arr[i]); } -function writePackedBoolean(arr, pbf) { for (var i = 0; i < arr.length; i++) pbf.writeBoolean(arr[i]); } -function writePackedFixed32(arr, pbf) { for (var i = 0; i < arr.length; i++) pbf.writeFixed32(arr[i]); } -function writePackedSFixed32(arr, pbf) { for (var i = 0; i < arr.length; i++) pbf.writeSFixed32(arr[i]); } -function writePackedFixed64(arr, pbf) { for (var i = 0; i < arr.length; i++) pbf.writeFixed64(arr[i]); } -function writePackedSFixed64(arr, pbf) { for (var i = 0; i < arr.length; i++) pbf.writeSFixed64(arr[i]); } -function readUInt32(buf, pos) { - return ((buf[pos]) | - (buf[pos + 1] << 8) | - (buf[pos + 2] << 16)) + - (buf[pos + 3] * 0x1000000); -} -function writeInt32(buf, val, pos) { - buf[pos] = val; - buf[pos + 1] = (val >>> 8); - buf[pos + 2] = (val >>> 16); - buf[pos + 3] = (val >>> 24); -} -function readInt32(buf, pos) { - return ((buf[pos]) | - (buf[pos + 1] << 8) | - (buf[pos + 2] << 16)) + - (buf[pos + 3] << 24); -} -function readUtf8(buf, pos, end) { - var str = ''; - var i = pos; - while (i < end) { - var b0 = buf[i]; - var c = null; - var bytesPerSequence = - b0 > 0xEF ? 4 : - b0 > 0xDF ? 3 : - b0 > 0xBF ? 2 : 1; - if (i + bytesPerSequence > end) break; - var b1, b2, b3; - if (bytesPerSequence === 1) { - if (b0 < 0x80) { - c = b0; - } - } else if (bytesPerSequence === 2) { - b1 = buf[i + 1]; - if ((b1 & 0xC0) === 0x80) { - c = (b0 & 0x1F) << 0x6 | (b1 & 0x3F); - if (c <= 0x7F) { - c = null; - } - } - } else if (bytesPerSequence === 3) { - b1 = buf[i + 1]; - b2 = buf[i + 2]; - if ((b1 & 0xC0) === 0x80 && (b2 & 0xC0) === 0x80) { - c = (b0 & 0xF) << 0xC | (b1 & 0x3F) << 0x6 | (b2 & 0x3F); - if (c <= 0x7FF || (c >= 0xD800 && c <= 0xDFFF)) { - c = null; - } - } - } else if (bytesPerSequence === 4) { - b1 = buf[i + 1]; - b2 = buf[i + 2]; - b3 = buf[i + 3]; - if ((b1 & 0xC0) === 0x80 && (b2 & 0xC0) === 0x80 && (b3 & 0xC0) === 0x80) { - c = (b0 & 0xF) << 0x12 | (b1 & 0x3F) << 0xC | (b2 & 0x3F) << 0x6 | (b3 & 0x3F); - if (c <= 0xFFFF || c >= 0x110000) { - c = null; - } - } - } - if (c === null) { - c = 0xFFFD; - bytesPerSequence = 1; - } else if (c > 0xFFFF) { - c -= 0x10000; - str += String.fromCharCode(c >>> 10 & 0x3FF | 0xD800); - c = 0xDC00 | c & 0x3FF; - } - str += String.fromCharCode(c); - i += bytesPerSequence; - } - return str; -} -function writeUtf8(buf, str, pos) { - for (var i = 0, c, lead; i < str.length; i++) { - c = str.charCodeAt(i); - if (c > 0xD7FF && c < 0xE000) { - if (lead) { - if (c < 0xDC00) { - buf[pos++] = 0xEF; - buf[pos++] = 0xBF; - buf[pos++] = 0xBD; - lead = c; - continue; - } else { - c = lead - 0xD800 << 10 | c - 0xDC00 | 0x10000; - lead = null; - } - } else { - if (c > 0xDBFF || (i + 1 === str.length)) { - buf[pos++] = 0xEF; - buf[pos++] = 0xBF; - buf[pos++] = 0xBD; - } else { - lead = c; - } - continue; - } - } else if (lead) { - buf[pos++] = 0xEF; - buf[pos++] = 0xBF; - buf[pos++] = 0xBD; - lead = null; - } - if (c < 0x80) { - buf[pos++] = c; - } else { - if (c < 0x800) { - buf[pos++] = c >> 0x6 | 0xC0; - } else { - if (c < 0x10000) { - buf[pos++] = c >> 0xC | 0xE0; - } else { - buf[pos++] = c >> 0x12 | 0xF0; - buf[pos++] = c >> 0xC & 0x3F | 0x80; - } - buf[pos++] = c >> 0x6 & 0x3F | 0x80; - } - buf[pos++] = c & 0x3F | 0x80; - } - } - return pos; -} - -exports['default'] = pbf; - -}((this.PBF = this.PBF || {})));}).call(ol.ext); -ol.ext.PBF = ol.ext.PBF.default; - -goog.provide('ol.render.Feature'); - -goog.require('ol'); -goog.require('ol.extent'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.flat.transform'); -goog.require('ol.transform'); - - -/** - * Lightweight, read-only, {@link ol.Feature} and {@link ol.geom.Geometry} like - * structure, optimized for vector tile rendering and styling. Geometry access - * through the API is limited to getting the type and extent of the geometry. - * - * @constructor - * @param {ol.geom.GeometryType} type Geometry type. - * @param {Array.<number>} flatCoordinates Flat coordinates. These always need - * to be right-handed for polygons. - * @param {Array.<number>|Array.<Array.<number>>} ends Ends or Endss. - * @param {Object.<string, *>} properties Properties. - * @param {number|string|undefined} id Feature id. - */ -ol.render.Feature = function(type, flatCoordinates, ends, properties, id) { - /** - * @private - * @type {ol.Extent|undefined} - */ - this.extent_; - - /** - * @private - * @type {number|string|undefined} - */ - this.id_ = id; - - /** - * @private - * @type {ol.geom.GeometryType} - */ - this.type_ = type; - - /** - * @private - * @type {Array.<number>} - */ - this.flatCoordinates_ = flatCoordinates; - - /** - * @private - * @type {Array.<number>|Array.<Array.<number>>} - */ - this.ends_ = ends; - - /** - * @private - * @type {Object.<string, *>} - */ - this.properties_ = properties; - - - /** - * @private - * @type {ol.Transform} - */ - this.tmpTransform_ = ol.transform.create(); -}; - - -/** - * Get a feature property by its key. - * @param {string} key Key - * @return {*} Value for the requested key. - * @api - */ -ol.render.Feature.prototype.get = function(key) { - return this.properties_[key]; -}; - - -/** - * @return {Array.<number>|Array.<Array.<number>>} Ends or endss. - */ -ol.render.Feature.prototype.getEnds = -ol.render.Feature.prototype.getEndss = function() { - return this.ends_; -}; - - -/** - * Get the extent of this feature's geometry. - * @return {ol.Extent} Extent. - * @api - */ -ol.render.Feature.prototype.getExtent = function() { - if (!this.extent_) { - this.extent_ = this.type_ === ol.geom.GeometryType.POINT ? - ol.extent.createOrUpdateFromCoordinate(this.flatCoordinates_) : - ol.extent.createOrUpdateFromFlatCoordinates( - this.flatCoordinates_, 0, this.flatCoordinates_.length, 2); - - } - return this.extent_; -}; - -/** - * Get the feature identifier. This is a stable identifier for the feature and - * is set when reading data from a remote source. - * @return {number|string|undefined} Id. - * @api - */ -ol.render.Feature.prototype.getId = function() { - return this.id_; -}; - - -/** - * @return {Array.<number>} Flat coordinates. - */ -ol.render.Feature.prototype.getOrientedFlatCoordinates = function() { - return this.flatCoordinates_; -}; - - -/** - * @return {Array.<number>} Flat coordinates. - */ -ol.render.Feature.prototype.getFlatCoordinates = - ol.render.Feature.prototype.getOrientedFlatCoordinates; - - -/** - * For API compatibility with {@link ol.Feature}, this method is useful when - * determining the geometry type in style function (see {@link #getType}). - * @return {ol.render.Feature} Feature. - * @api - */ -ol.render.Feature.prototype.getGeometry = function() { - return this; -}; - - -/** - * Get the feature properties. - * @return {Object.<string, *>} Feature properties. - * @api - */ -ol.render.Feature.prototype.getProperties = function() { - return this.properties_; -}; - - -/** - * Get the feature for working with its geometry. - * @return {ol.render.Feature} Feature. - */ -ol.render.Feature.prototype.getSimplifiedGeometry = - ol.render.Feature.prototype.getGeometry; - - -/** - * @return {number} Stride. - */ -ol.render.Feature.prototype.getStride = function() { - return 2; -}; - - -/** - * @return {undefined} - */ -ol.render.Feature.prototype.getStyleFunction = ol.nullFunction; - - -/** - * Get the type of this feature's geometry. - * @return {ol.geom.GeometryType} Geometry type. - * @api - */ -ol.render.Feature.prototype.getType = function() { - return this.type_; -}; - -/** - * Transform geometry coordinates from tile pixel space to projected. - * The SRS of the source and destination are expected to be the same. - * - * @param {ol.ProjectionLike} source The current projection - * @param {ol.ProjectionLike} destination The desired projection. - */ -ol.render.Feature.prototype.transform = function(source, destination) { - var pixelExtent = source.getExtent(); - var projectedExtent = source.getWorldExtent(); - var scale = ol.extent.getHeight(projectedExtent) / ol.extent.getHeight(pixelExtent); - var transform = this.tmpTransform_; - ol.transform.compose(transform, - projectedExtent[0], projectedExtent[3], - scale, -scale, 0, - 0, 0); - ol.geom.flat.transform.transform2D(this.flatCoordinates_, 0, this.flatCoordinates_.length, 2, - transform, this.flatCoordinates_); -}; - -//FIXME Implement projection handling - -goog.provide('ol.format.MVT'); - -goog.require('ol'); -goog.require('ol.asserts'); -goog.require('ol.ext.PBF'); -goog.require('ol.format.Feature'); -goog.require('ol.format.FormatType'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.LineString'); -goog.require('ol.geom.MultiLineString'); -goog.require('ol.geom.MultiPoint'); -goog.require('ol.geom.MultiPolygon'); -goog.require('ol.geom.Point'); -goog.require('ol.geom.Polygon'); -goog.require('ol.geom.flat.orient'); -goog.require('ol.proj.Projection'); -goog.require('ol.proj.Units'); -goog.require('ol.render.Feature'); - - -/** - * @classdesc - * Feature format for reading data in the Mapbox MVT format. - * - * @constructor - * @extends {ol.format.Feature} - * @param {olx.format.MVTOptions=} opt_options Options. - * @api - */ -ol.format.MVT = function(opt_options) { - - ol.format.Feature.call(this); - - var options = opt_options ? opt_options : {}; - - /** - * @type {ol.proj.Projection} - */ - this.defaultDataProjection = new ol.proj.Projection({ - code: 'EPSG:3857', - units: ol.proj.Units.TILE_PIXELS - }); - - /** - * @private - * @type {function((ol.geom.Geometry|Object.<string,*>)=)| - * function(ol.geom.GeometryType,Array.<number>, - * (Array.<number>|Array.<Array.<number>>),Object.<string,*>,number)} - */ - this.featureClass_ = options.featureClass ? - options.featureClass : ol.render.Feature; - - /** - * @private - * @type {string|undefined} - */ - this.geometryName_ = options.geometryName; - - /** - * @private - * @type {string} - */ - this.layerName_ = options.layerName ? options.layerName : 'layer'; - - /** - * @private - * @type {Array.<string>} - */ - this.layers_ = options.layers ? options.layers : null; - - /** - * @private - * @type {ol.Extent} - */ - this.extent_ = null; - -}; -ol.inherits(ol.format.MVT, ol.format.Feature); - - -/** - * Reader callbacks for parsing the PBF. - * @type {Object.<string, function(number, Object, ol.ext.PBF)>} - */ -ol.format.MVT.pbfReaders_ = { - layers: function(tag, layers, pbf) { - if (tag === 3) { - var layer = { - keys: [], - values: [], - features: [] - }; - var end = pbf.readVarint() + pbf.pos; - pbf.readFields(ol.format.MVT.pbfReaders_.layer, layer, end); - layer.length = layer.features.length; - if (layer.length) { - layers[layer.name] = layer; - } - } - }, - layer: function(tag, layer, pbf) { - if (tag === 15) { - layer.version = pbf.readVarint(); - } else if (tag === 1) { - layer.name = pbf.readString(); - } else if (tag === 5) { - layer.extent = pbf.readVarint(); - } else if (tag === 2) { - layer.features.push(pbf.pos); - } else if (tag === 3) { - layer.keys.push(pbf.readString()); - } else if (tag === 4) { - var value = null; - var end = pbf.readVarint() + pbf.pos; - while (pbf.pos < end) { - tag = pbf.readVarint() >> 3; - value = tag === 1 ? pbf.readString() : - tag === 2 ? pbf.readFloat() : - tag === 3 ? pbf.readDouble() : - tag === 4 ? pbf.readVarint64() : - tag === 5 ? pbf.readVarint() : - tag === 6 ? pbf.readSVarint() : - tag === 7 ? pbf.readBoolean() : null; - } - layer.values.push(value); - } - }, - feature: function(tag, feature, pbf) { - if (tag == 1) { - feature.id = pbf.readVarint(); - } else if (tag == 2) { - var end = pbf.readVarint() + pbf.pos; - while (pbf.pos < end) { - var key = feature.layer.keys[pbf.readVarint()]; - var value = feature.layer.values[pbf.readVarint()]; - feature.properties[key] = value; - } - } else if (tag == 3) { - feature.type = pbf.readVarint(); - } else if (tag == 4) { - feature.geometry = pbf.pos; - } - } -}; - - -/** - * Read a raw feature from the pbf offset stored at index `i` in the raw layer. - * @suppress {missingProperties} - * @private - * @param {ol.ext.PBF} pbf PBF. - * @param {Object} layer Raw layer. - * @param {number} i Index of the feature in the raw layer's `features` array. - * @return {Object} Raw feature. - */ -ol.format.MVT.readRawFeature_ = function(pbf, layer, i) { - pbf.pos = layer.features[i]; - var end = pbf.readVarint() + pbf.pos; - - var feature = { - layer: layer, - type: 0, - properties: {} - }; - pbf.readFields(ol.format.MVT.pbfReaders_.feature, feature, end); - return feature; -}; - - -/** - * Read the raw geometry from the pbf offset stored in a raw feature's geometry - * proeprty. - * @suppress {missingProperties} - * @private - * @param {ol.ext.PBF} pbf PBF. - * @param {Object} feature Raw feature. - * @param {Array.<number>} flatCoordinates Array to store flat coordinates in. - * @param {Array.<number>} ends Array to store ends in. - */ -ol.format.MVT.readRawGeometry_ = function(pbf, feature, flatCoordinates, ends) { - pbf.pos = feature.geometry; - - var end = pbf.readVarint() + pbf.pos; - var cmd = 1; - var length = 0; - var x = 0; - var y = 0; - var coordsLen = 0; - var currentEnd = 0; - - while (pbf.pos < end) { - if (!length) { - var cmdLen = pbf.readVarint(); - cmd = cmdLen & 0x7; - length = cmdLen >> 3; - } - - length--; - - if (cmd === 1 || cmd === 2) { - x += pbf.readSVarint(); - y += pbf.readSVarint(); - - if (cmd === 1) { // moveTo - if (coordsLen > currentEnd) { - ends.push(coordsLen); - currentEnd = coordsLen; - } - } - - flatCoordinates.push(x, y); - coordsLen += 2; - - } else if (cmd === 7) { - - if (coordsLen > currentEnd) { - // close polygon - flatCoordinates.push( - flatCoordinates[currentEnd], flatCoordinates[currentEnd + 1]); - coordsLen += 2; - } - - } else { - ol.asserts.assert(false, 59); // Invalid command found in the PBF - } - } - - if (coordsLen > currentEnd) { - ends.push(coordsLen); - currentEnd = coordsLen; - } - -}; - - -/** - * @suppress {missingProperties} - * @private - * @param {number} type The raw feature's geometry type - * @param {number} numEnds Number of ends of the flat coordinates of the - * geometry. - * @return {ol.geom.GeometryType} The geometry type. - */ -ol.format.MVT.getGeometryType_ = function(type, numEnds) { - /** @type {ol.geom.GeometryType} */ - var geometryType; - if (type === 1) { - geometryType = numEnds === 1 ? - ol.geom.GeometryType.POINT : ol.geom.GeometryType.MULTI_POINT; - } else if (type === 2) { - geometryType = numEnds === 1 ? - ol.geom.GeometryType.LINE_STRING : - ol.geom.GeometryType.MULTI_LINE_STRING; - } else if (type === 3) { - geometryType = ol.geom.GeometryType.POLYGON; - // MultiPolygon not relevant for rendering - winding order determines - // outer rings of polygons. - } - return geometryType; -}; - -/** - * @private - * @param {ol.ext.PBF} pbf PBF - * @param {Object} rawFeature Raw Mapbox feature. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {ol.Feature|ol.render.Feature} Feature. - */ -ol.format.MVT.prototype.createFeature_ = function(pbf, rawFeature, opt_options) { - var type = rawFeature.type; - if (type === 0) { - return null; - } - - var feature; - var id = rawFeature.id; - var values = rawFeature.properties; - values[this.layerName_] = rawFeature.layer.name; - - var flatCoordinates = []; - var ends = []; - ol.format.MVT.readRawGeometry_(pbf, rawFeature, flatCoordinates, ends); - - var geometryType = ol.format.MVT.getGeometryType_(type, ends.length); - - if (this.featureClass_ === ol.render.Feature) { - feature = new this.featureClass_(geometryType, flatCoordinates, ends, values, id); - } else { - var geom; - if (geometryType == ol.geom.GeometryType.POLYGON) { - var endss = []; - var offset = 0; - var prevEndIndex = 0; - for (var i = 0, ii = ends.length; i < ii; ++i) { - var end = ends[i]; - if (!ol.geom.flat.orient.linearRingIsClockwise(flatCoordinates, offset, end, 2)) { - endss.push(ends.slice(prevEndIndex, i)); - prevEndIndex = i; - } - offset = end; - } - if (endss.length > 1) { - ends = endss; - geom = new ol.geom.MultiPolygon(null); - } else { - geom = new ol.geom.Polygon(null); - } - } else { - geom = geometryType === ol.geom.GeometryType.POINT ? new ol.geom.Point(null) : - geometryType === ol.geom.GeometryType.LINE_STRING ? new ol.geom.LineString(null) : - geometryType === ol.geom.GeometryType.POLYGON ? new ol.geom.Polygon(null) : - geometryType === ol.geom.GeometryType.MULTI_POINT ? new ol.geom.MultiPoint (null) : - geometryType === ol.geom.GeometryType.MULTI_LINE_STRING ? new ol.geom.MultiLineString(null) : - null; - } - geom.setFlatCoordinates(ol.geom.GeometryLayout.XY, flatCoordinates, ends); - feature = new this.featureClass_(); - if (this.geometryName_) { - feature.setGeometryName(this.geometryName_); - } - var geometry = ol.format.Feature.transformWithOptions(geom, false, this.adaptOptions(opt_options)); - feature.setGeometry(geometry); - feature.setId(id); - feature.setProperties(values); - } - - return feature; -}; - - -/** - * @inheritDoc - * @api - */ -ol.format.MVT.prototype.getLastExtent = function() { - return this.extent_; -}; - - -/** - * @inheritDoc - */ -ol.format.MVT.prototype.getType = function() { - return ol.format.FormatType.ARRAY_BUFFER; -}; - - -/** - * @inheritDoc - * @api - */ -ol.format.MVT.prototype.readFeatures = function(source, opt_options) { - var layers = this.layers_; - - var pbf = new ol.ext.PBF(/** @type {ArrayBuffer} */ (source)); - var pbfLayers = pbf.readFields(ol.format.MVT.pbfReaders_.layers, {}); - /** @type {Array.<ol.Feature|ol.render.Feature>} */ - var features = []; - var pbfLayer; - for (var name in pbfLayers) { - if (layers && layers.indexOf(name) == -1) { - continue; - } - pbfLayer = pbfLayers[name]; - - var rawFeature; - for (var i = 0, ii = pbfLayer.length; i < ii; ++i) { - rawFeature = ol.format.MVT.readRawFeature_(pbf, pbfLayer, i); - features.push(this.createFeature_(pbf, rawFeature)); - } - this.extent_ = pbfLayer ? [0, 0, pbfLayer.extent, pbfLayer.extent] : null; - } - - return features; -}; - - -/** - * @inheritDoc - * @api - */ -ol.format.MVT.prototype.readProjection = function(source) { - return this.defaultDataProjection; -}; - - -/** - * Sets the layers that features will be read from. - * @param {Array.<string>} layers Layers. - * @api - */ -ol.format.MVT.prototype.setLayers = function(layers) { - this.layers_ = layers; -}; - - -/** - * Not implemented. - * @override - */ -ol.format.MVT.prototype.readFeature = function() {}; - - -/** - * Not implemented. - * @override - */ -ol.format.MVT.prototype.readGeometry = function() {}; - - -/** - * Not implemented. - * @override - */ -ol.format.MVT.prototype.writeFeature = function() {}; - - -/** - * Not implemented. - * @override - */ -ol.format.MVT.prototype.writeGeometry = function() {}; - - -/** - * Not implemented. - * @override - */ -ol.format.MVT.prototype.writeFeatures = function() {}; - -// FIXME add typedef for stack state objects -goog.provide('ol.format.OSMXML'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.Feature'); -goog.require('ol.format.Feature'); -goog.require('ol.format.XMLFeature'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.LineString'); -goog.require('ol.geom.Point'); -goog.require('ol.geom.Polygon'); -goog.require('ol.obj'); -goog.require('ol.proj'); -goog.require('ol.xml'); - - -/** - * @classdesc - * Feature format for reading data in the - * [OSMXML format](http://wiki.openstreetmap.org/wiki/OSM_XML). - * - * @constructor - * @extends {ol.format.XMLFeature} - * @api - */ -ol.format.OSMXML = function() { - ol.format.XMLFeature.call(this); - - /** - * @inheritDoc - */ - this.defaultDataProjection = ol.proj.get('EPSG:4326'); -}; -ol.inherits(ol.format.OSMXML, ol.format.XMLFeature); - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.OSMXML.readNode_ = function(node, objectStack) { - var options = /** @type {olx.format.ReadOptions} */ (objectStack[0]); - var state = /** @type {Object} */ (objectStack[objectStack.length - 1]); - var id = node.getAttribute('id'); - /** @type {ol.Coordinate} */ - var coordinates = [ - parseFloat(node.getAttribute('lon')), - parseFloat(node.getAttribute('lat')) - ]; - state.nodes[id] = coordinates; - - var values = ol.xml.pushParseAndPop({ - tags: {} - }, ol.format.OSMXML.NODE_PARSERS_, node, objectStack); - if (!ol.obj.isEmpty(values.tags)) { - var geometry = new ol.geom.Point(coordinates); - ol.format.Feature.transformWithOptions(geometry, false, options); - var feature = new ol.Feature(geometry); - feature.setId(id); - feature.setProperties(values.tags); - state.features.push(feature); - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.OSMXML.readWay_ = function(node, objectStack) { - var id = node.getAttribute('id'); - var values = ol.xml.pushParseAndPop({ - id: id, - ndrefs: [], - tags: {} - }, ol.format.OSMXML.WAY_PARSERS_, node, objectStack); - var state = /** @type {Object} */ (objectStack[objectStack.length - 1]); - state.ways.push(values); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.OSMXML.readNd_ = function(node, objectStack) { - var values = /** @type {Object} */ (objectStack[objectStack.length - 1]); - values.ndrefs.push(node.getAttribute('ref')); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.OSMXML.readTag_ = function(node, objectStack) { - var values = /** @type {Object} */ (objectStack[objectStack.length - 1]); - values.tags[node.getAttribute('k')] = node.getAttribute('v'); -}; - - -/** - * @const - * @private - * @type {Array.<string>} - */ -ol.format.OSMXML.NAMESPACE_URIS_ = [ - null -]; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.OSMXML.WAY_PARSERS_ = ol.xml.makeStructureNS( - ol.format.OSMXML.NAMESPACE_URIS_, { - 'nd': ol.format.OSMXML.readNd_, - 'tag': ol.format.OSMXML.readTag_ - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.OSMXML.PARSERS_ = ol.xml.makeStructureNS( - ol.format.OSMXML.NAMESPACE_URIS_, { - 'node': ol.format.OSMXML.readNode_, - 'way': ol.format.OSMXML.readWay_ - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.OSMXML.NODE_PARSERS_ = ol.xml.makeStructureNS( - ol.format.OSMXML.NAMESPACE_URIS_, { - 'tag': ol.format.OSMXML.readTag_ - }); - - -/** - * Read all features from an OSM source. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {Array.<ol.Feature>} Features. - * @api - */ -ol.format.OSMXML.prototype.readFeatures; - - -/** - * @inheritDoc - */ -ol.format.OSMXML.prototype.readFeaturesFromNode = function(node, opt_options) { - var options = this.getReadOptions(node, opt_options); - if (node.localName == 'osm') { - var state = ol.xml.pushParseAndPop({ - nodes: {}, - ways: [], - features: [] - }, ol.format.OSMXML.PARSERS_, node, [options]); - // parse nodes in ways - for (var j = 0; j < state.ways.length; j++) { - var values = /** @type {Object} */ (state.ways[j]); - /** @type {Array.<number>} */ - var flatCoordinates = []; - for (var i = 0, ii = values.ndrefs.length; i < ii; i++) { - var point = state.nodes[values.ndrefs[i]]; - ol.array.extend(flatCoordinates, point); - } - var geometry; - if (values.ndrefs[0] == values.ndrefs[values.ndrefs.length - 1]) { - // closed way - geometry = new ol.geom.Polygon(null); - geometry.setFlatCoordinates(ol.geom.GeometryLayout.XY, flatCoordinates, - [flatCoordinates.length]); - } else { - geometry = new ol.geom.LineString(null); - geometry.setFlatCoordinates(ol.geom.GeometryLayout.XY, flatCoordinates); - } - ol.format.Feature.transformWithOptions(geometry, false, options); - var feature = new ol.Feature(geometry); - feature.setId(values.id); - feature.setProperties(values.tags); - state.features.push(feature); - } - if (state.features) { - return state.features; - } - } - return []; -}; - - -/** - * Read the projection from an OSM source. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @return {ol.proj.Projection} Projection. - * @api - */ -ol.format.OSMXML.prototype.readProjection; - - -/** - * Not implemented. - * @inheritDoc - */ -ol.format.OSMXML.prototype.writeFeatureNode = function(feature, opt_options) {}; - - -/** - * Not implemented. - * @inheritDoc - */ -ol.format.OSMXML.prototype.writeFeaturesNode = function(features, opt_options) {}; - - -/** - * Not implemented. - * @inheritDoc - */ -ol.format.OSMXML.prototype.writeGeometryNode = function(geometry, opt_options) {}; - -goog.provide('ol.format.XLink'); - - -/** - * @const - * @type {string} - */ -ol.format.XLink.NAMESPACE_URI = 'http://www.w3.org/1999/xlink'; - - -/** - * @param {Node} node Node. - * @return {boolean|undefined} Boolean. - */ -ol.format.XLink.readHref = function(node) { - return node.getAttributeNS(ol.format.XLink.NAMESPACE_URI, 'href'); -}; - -goog.provide('ol.format.XML'); - -goog.require('ol.xml'); - - -/** - * @classdesc - * Generic format for reading non-feature XML data - * - * @constructor - * @abstract - * @struct - */ -ol.format.XML = function() { -}; - - -/** - * @param {Document|Node|string} source Source. - * @return {Object} The parsed result. - */ -ol.format.XML.prototype.read = function(source) { - if (ol.xml.isDocument(source)) { - return this.readFromDocument(/** @type {Document} */ (source)); - } else if (ol.xml.isNode(source)) { - return this.readFromNode(/** @type {Node} */ (source)); - } else if (typeof source === 'string') { - var doc = ol.xml.parse(source); - return this.readFromDocument(doc); - } else { - return null; - } -}; - - -/** - * @abstract - * @param {Document} doc Document. - * @return {Object} Object - */ -ol.format.XML.prototype.readFromDocument = function(doc) {}; - - -/** - * @abstract - * @param {Node} node Node. - * @return {Object} Object - */ -ol.format.XML.prototype.readFromNode = function(node) {}; - -goog.provide('ol.format.OWS'); - -goog.require('ol'); -goog.require('ol.format.XLink'); -goog.require('ol.format.XML'); -goog.require('ol.format.XSD'); -goog.require('ol.xml'); - - -/** - * @constructor - * @extends {ol.format.XML} - */ -ol.format.OWS = function() { - ol.format.XML.call(this); -}; -ol.inherits(ol.format.OWS, ol.format.XML); - - -/** - * @inheritDoc - */ -ol.format.OWS.prototype.readFromDocument = function(doc) { - for (var n = doc.firstChild; n; n = n.nextSibling) { - if (n.nodeType == Node.ELEMENT_NODE) { - return this.readFromNode(n); - } - } - return null; -}; - - -/** - * @inheritDoc - */ -ol.format.OWS.prototype.readFromNode = function(node) { - var owsObject = ol.xml.pushParseAndPop({}, - ol.format.OWS.PARSERS_, node, []); - return owsObject ? owsObject : null; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} The address. - */ -ol.format.OWS.readAddress_ = function(node, objectStack) { - return ol.xml.pushParseAndPop({}, - ol.format.OWS.ADDRESS_PARSERS_, node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} The values. - */ -ol.format.OWS.readAllowedValues_ = function(node, objectStack) { - return ol.xml.pushParseAndPop({}, - ol.format.OWS.ALLOWED_VALUES_PARSERS_, node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} The constraint. - */ -ol.format.OWS.readConstraint_ = function(node, objectStack) { - var name = node.getAttribute('name'); - if (!name) { - return undefined; - } - return ol.xml.pushParseAndPop({'name': name}, - ol.format.OWS.CONSTRAINT_PARSERS_, node, - objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} The contact info. - */ -ol.format.OWS.readContactInfo_ = function(node, objectStack) { - return ol.xml.pushParseAndPop({}, - ol.format.OWS.CONTACT_INFO_PARSERS_, node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} The DCP. - */ -ol.format.OWS.readDcp_ = function(node, objectStack) { - return ol.xml.pushParseAndPop({}, - ol.format.OWS.DCP_PARSERS_, node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} The GET object. - */ -ol.format.OWS.readGet_ = function(node, objectStack) { - var href = ol.format.XLink.readHref(node); - if (!href) { - return undefined; - } - return ol.xml.pushParseAndPop({'href': href}, - ol.format.OWS.REQUEST_METHOD_PARSERS_, node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} The HTTP object. - */ -ol.format.OWS.readHttp_ = function(node, objectStack) { - return ol.xml.pushParseAndPop({}, ol.format.OWS.HTTP_PARSERS_, - node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} The operation. - */ -ol.format.OWS.readOperation_ = function(node, objectStack) { - var name = node.getAttribute('name'); - var value = ol.xml.pushParseAndPop({}, - ol.format.OWS.OPERATION_PARSERS_, node, objectStack); - if (!value) { - return undefined; - } - var object = /** @type {Object} */ - (objectStack[objectStack.length - 1]); - object[name] = value; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} The operations metadata. - */ -ol.format.OWS.readOperationsMetadata_ = function(node, - objectStack) { - return ol.xml.pushParseAndPop({}, - ol.format.OWS.OPERATIONS_METADATA_PARSERS_, node, - objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} The phone. - */ -ol.format.OWS.readPhone_ = function(node, objectStack) { - return ol.xml.pushParseAndPop({}, - ol.format.OWS.PHONE_PARSERS_, node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} The service identification. - */ -ol.format.OWS.readServiceIdentification_ = function(node, - objectStack) { - return ol.xml.pushParseAndPop( - {}, ol.format.OWS.SERVICE_IDENTIFICATION_PARSERS_, node, - objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} The service contact. - */ -ol.format.OWS.readServiceContact_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - {}, ol.format.OWS.SERVICE_CONTACT_PARSERS_, node, - objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} The service provider. - */ -ol.format.OWS.readServiceProvider_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - {}, ol.format.OWS.SERVICE_PROVIDER_PARSERS_, node, - objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {string|undefined} The value. - */ -ol.format.OWS.readValue_ = function(node, objectStack) { - return ol.format.XSD.readString(node); -}; - - -/** - * @const - * @type {Array.<string>} - * @private - */ -ol.format.OWS.NAMESPACE_URIS_ = [ - null, - 'http://www.opengis.net/ows/1.1' -]; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.OWS.PARSERS_ = ol.xml.makeStructureNS( - ol.format.OWS.NAMESPACE_URIS_, { - 'ServiceIdentification': ol.xml.makeObjectPropertySetter( - ol.format.OWS.readServiceIdentification_), - 'ServiceProvider': ol.xml.makeObjectPropertySetter( - ol.format.OWS.readServiceProvider_), - 'OperationsMetadata': ol.xml.makeObjectPropertySetter( - ol.format.OWS.readOperationsMetadata_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.OWS.ADDRESS_PARSERS_ = ol.xml.makeStructureNS( - ol.format.OWS.NAMESPACE_URIS_, { - 'DeliveryPoint': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'City': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'AdministrativeArea': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'PostalCode': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'Country': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'ElectronicMailAddress': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.OWS.ALLOWED_VALUES_PARSERS_ = ol.xml.makeStructureNS( - ol.format.OWS.NAMESPACE_URIS_, { - 'Value': ol.xml.makeObjectPropertyPusher(ol.format.OWS.readValue_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.OWS.CONSTRAINT_PARSERS_ = ol.xml.makeStructureNS( - ol.format.OWS.NAMESPACE_URIS_, { - 'AllowedValues': ol.xml.makeObjectPropertySetter( - ol.format.OWS.readAllowedValues_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.OWS.CONTACT_INFO_PARSERS_ = ol.xml.makeStructureNS( - ol.format.OWS.NAMESPACE_URIS_, { - 'Phone': ol.xml.makeObjectPropertySetter(ol.format.OWS.readPhone_), - 'Address': ol.xml.makeObjectPropertySetter(ol.format.OWS.readAddress_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.OWS.DCP_PARSERS_ = ol.xml.makeStructureNS( - ol.format.OWS.NAMESPACE_URIS_, { - 'HTTP': ol.xml.makeObjectPropertySetter(ol.format.OWS.readHttp_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.OWS.HTTP_PARSERS_ = ol.xml.makeStructureNS( - ol.format.OWS.NAMESPACE_URIS_, { - 'Get': ol.xml.makeObjectPropertyPusher(ol.format.OWS.readGet_), - 'Post': undefined // TODO - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.OWS.OPERATION_PARSERS_ = ol.xml.makeStructureNS( - ol.format.OWS.NAMESPACE_URIS_, { - 'DCP': ol.xml.makeObjectPropertySetter(ol.format.OWS.readDcp_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.OWS.OPERATIONS_METADATA_PARSERS_ = ol.xml.makeStructureNS( - ol.format.OWS.NAMESPACE_URIS_, { - 'Operation': ol.format.OWS.readOperation_ - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.OWS.PHONE_PARSERS_ = ol.xml.makeStructureNS( - ol.format.OWS.NAMESPACE_URIS_, { - 'Voice': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'Facsimile': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.OWS.REQUEST_METHOD_PARSERS_ = ol.xml.makeStructureNS( - ol.format.OWS.NAMESPACE_URIS_, { - 'Constraint': ol.xml.makeObjectPropertyPusher( - ol.format.OWS.readConstraint_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.OWS.SERVICE_CONTACT_PARSERS_ = - ol.xml.makeStructureNS( - ol.format.OWS.NAMESPACE_URIS_, { - 'IndividualName': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'PositionName': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'ContactInfo': ol.xml.makeObjectPropertySetter( - ol.format.OWS.readContactInfo_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.OWS.SERVICE_IDENTIFICATION_PARSERS_ = - ol.xml.makeStructureNS( - ol.format.OWS.NAMESPACE_URIS_, { - 'Title': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'ServiceTypeVersion': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'ServiceType': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.OWS.SERVICE_PROVIDER_PARSERS_ = - ol.xml.makeStructureNS( - ol.format.OWS.NAMESPACE_URIS_, { - 'ProviderName': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'ProviderSite': ol.xml.makeObjectPropertySetter(ol.format.XLink.readHref), - 'ServiceContact': ol.xml.makeObjectPropertySetter( - ol.format.OWS.readServiceContact_) - }); - -goog.provide('ol.geom.flat.flip'); - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @param {Array.<number>=} opt_dest Destination. - * @param {number=} opt_destOffset Destination offset. - * @return {Array.<number>} Flat coordinates. - */ -ol.geom.flat.flip.flipXY = function(flatCoordinates, offset, end, stride, opt_dest, opt_destOffset) { - var dest, destOffset; - if (opt_dest !== undefined) { - dest = opt_dest; - destOffset = opt_destOffset !== undefined ? opt_destOffset : 0; - } else { - dest = []; - destOffset = 0; - } - var j = offset; - while (j < end) { - var x = flatCoordinates[j++]; - dest[destOffset++] = flatCoordinates[j++]; - dest[destOffset++] = x; - for (var k = 2; k < stride; ++k) { - dest[destOffset++] = flatCoordinates[j++]; - } - } - dest.length = destOffset; - return dest; -}; - -goog.provide('ol.format.Polyline'); - -goog.require('ol'); -goog.require('ol.asserts'); -goog.require('ol.Feature'); -goog.require('ol.format.Feature'); -goog.require('ol.format.TextFeature'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.LineString'); -goog.require('ol.geom.SimpleGeometry'); -goog.require('ol.geom.flat.flip'); -goog.require('ol.geom.flat.inflate'); -goog.require('ol.proj'); - - -/** - * @classdesc - * Feature format for reading and writing data in the Encoded - * Polyline Algorithm Format. - * - * @constructor - * @extends {ol.format.TextFeature} - * @param {olx.format.PolylineOptions=} opt_options - * Optional configuration object. - * @api - */ -ol.format.Polyline = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - ol.format.TextFeature.call(this); - - /** - * @inheritDoc - */ - this.defaultDataProjection = ol.proj.get('EPSG:4326'); - - /** - * @private - * @type {number} - */ - this.factor_ = options.factor ? options.factor : 1e5; - - /** - * @private - * @type {ol.geom.GeometryLayout} - */ - this.geometryLayout_ = options.geometryLayout ? - options.geometryLayout : ol.geom.GeometryLayout.XY; -}; -ol.inherits(ol.format.Polyline, ol.format.TextFeature); - - -/** - * Encode a list of n-dimensional points and return an encoded string - * - * Attention: This function will modify the passed array! - * - * @param {Array.<number>} numbers A list of n-dimensional points. - * @param {number} stride The number of dimension of the points in the list. - * @param {number=} opt_factor The factor by which the numbers will be - * multiplied. The remaining decimal places will get rounded away. - * Default is `1e5`. - * @return {string} The encoded string. - * @api - */ -ol.format.Polyline.encodeDeltas = function(numbers, stride, opt_factor) { - var factor = opt_factor ? opt_factor : 1e5; - var d; - - var lastNumbers = new Array(stride); - for (d = 0; d < stride; ++d) { - lastNumbers[d] = 0; - } - - var i, ii; - for (i = 0, ii = numbers.length; i < ii;) { - for (d = 0; d < stride; ++d, ++i) { - var num = numbers[i]; - var delta = num - lastNumbers[d]; - lastNumbers[d] = num; - - numbers[i] = delta; - } - } - - return ol.format.Polyline.encodeFloats(numbers, factor); -}; - - -/** - * Decode a list of n-dimensional points from an encoded string - * - * @param {string} encoded An encoded string. - * @param {number} stride The number of dimension of the points in the - * encoded string. - * @param {number=} opt_factor The factor by which the resulting numbers will - * be divided. Default is `1e5`. - * @return {Array.<number>} A list of n-dimensional points. - * @api - */ -ol.format.Polyline.decodeDeltas = function(encoded, stride, opt_factor) { - var factor = opt_factor ? opt_factor : 1e5; - var d; - - /** @type {Array.<number>} */ - var lastNumbers = new Array(stride); - for (d = 0; d < stride; ++d) { - lastNumbers[d] = 0; - } - - var numbers = ol.format.Polyline.decodeFloats(encoded, factor); - - var i, ii; - for (i = 0, ii = numbers.length; i < ii;) { - for (d = 0; d < stride; ++d, ++i) { - lastNumbers[d] += numbers[i]; - - numbers[i] = lastNumbers[d]; - } - } - - return numbers; -}; - - -/** - * Encode a list of floating point numbers and return an encoded string - * - * Attention: This function will modify the passed array! - * - * @param {Array.<number>} numbers A list of floating point numbers. - * @param {number=} opt_factor The factor by which the numbers will be - * multiplied. The remaining decimal places will get rounded away. - * Default is `1e5`. - * @return {string} The encoded string. - * @api - */ -ol.format.Polyline.encodeFloats = function(numbers, opt_factor) { - var factor = opt_factor ? opt_factor : 1e5; - var i, ii; - for (i = 0, ii = numbers.length; i < ii; ++i) { - numbers[i] = Math.round(numbers[i] * factor); - } - - return ol.format.Polyline.encodeSignedIntegers(numbers); -}; - - -/** - * Decode a list of floating point numbers from an encoded string - * - * @param {string} encoded An encoded string. - * @param {number=} opt_factor The factor by which the result will be divided. - * Default is `1e5`. - * @return {Array.<number>} A list of floating point numbers. - * @api - */ -ol.format.Polyline.decodeFloats = function(encoded, opt_factor) { - var factor = opt_factor ? opt_factor : 1e5; - var numbers = ol.format.Polyline.decodeSignedIntegers(encoded); - var i, ii; - for (i = 0, ii = numbers.length; i < ii; ++i) { - numbers[i] /= factor; - } - return numbers; -}; - - -/** - * Encode a list of signed integers and return an encoded string - * - * Attention: This function will modify the passed array! - * - * @param {Array.<number>} numbers A list of signed integers. - * @return {string} The encoded string. - */ -ol.format.Polyline.encodeSignedIntegers = function(numbers) { - var i, ii; - for (i = 0, ii = numbers.length; i < ii; ++i) { - var num = numbers[i]; - numbers[i] = (num < 0) ? ~(num << 1) : (num << 1); - } - return ol.format.Polyline.encodeUnsignedIntegers(numbers); -}; - - -/** - * Decode a list of signed integers from an encoded string - * - * @param {string} encoded An encoded string. - * @return {Array.<number>} A list of signed integers. - */ -ol.format.Polyline.decodeSignedIntegers = function(encoded) { - var numbers = ol.format.Polyline.decodeUnsignedIntegers(encoded); - var i, ii; - for (i = 0, ii = numbers.length; i < ii; ++i) { - var num = numbers[i]; - numbers[i] = (num & 1) ? ~(num >> 1) : (num >> 1); - } - return numbers; -}; - - -/** - * Encode a list of unsigned integers and return an encoded string - * - * @param {Array.<number>} numbers A list of unsigned integers. - * @return {string} The encoded string. - */ -ol.format.Polyline.encodeUnsignedIntegers = function(numbers) { - var encoded = ''; - var i, ii; - for (i = 0, ii = numbers.length; i < ii; ++i) { - encoded += ol.format.Polyline.encodeUnsignedInteger(numbers[i]); - } - return encoded; -}; - - -/** - * Decode a list of unsigned integers from an encoded string - * - * @param {string} encoded An encoded string. - * @return {Array.<number>} A list of unsigned integers. - */ -ol.format.Polyline.decodeUnsignedIntegers = function(encoded) { - var numbers = []; - var current = 0; - var shift = 0; - var i, ii; - for (i = 0, ii = encoded.length; i < ii; ++i) { - var b = encoded.charCodeAt(i) - 63; - current |= (b & 0x1f) << shift; - if (b < 0x20) { - numbers.push(current); - current = 0; - shift = 0; - } else { - shift += 5; - } - } - return numbers; -}; - - -/** - * Encode one single unsigned integer and return an encoded string - * - * @param {number} num Unsigned integer that should be encoded. - * @return {string} The encoded string. - */ -ol.format.Polyline.encodeUnsignedInteger = function(num) { - var value, encoded = ''; - while (num >= 0x20) { - value = (0x20 | (num & 0x1f)) + 63; - encoded += String.fromCharCode(value); - num >>= 5; - } - value = num + 63; - encoded += String.fromCharCode(value); - return encoded; -}; - - -/** - * Read the feature from the Polyline source. The coordinates are assumed to be - * in two dimensions and in latitude, longitude order. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {ol.Feature} Feature. - * @api - */ -ol.format.Polyline.prototype.readFeature; - - -/** - * @inheritDoc - */ -ol.format.Polyline.prototype.readFeatureFromText = function(text, opt_options) { - var geometry = this.readGeometryFromText(text, opt_options); - return new ol.Feature(geometry); -}; - - -/** - * Read the feature from the source. As Polyline sources contain a single - * feature, this will return the feature in an array. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {Array.<ol.Feature>} Features. - * @api - */ -ol.format.Polyline.prototype.readFeatures; - - -/** - * @inheritDoc - */ -ol.format.Polyline.prototype.readFeaturesFromText = function(text, opt_options) { - var feature = this.readFeatureFromText(text, opt_options); - return [feature]; -}; - - -/** - * Read the geometry from the source. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {ol.geom.Geometry} Geometry. - * @api - */ -ol.format.Polyline.prototype.readGeometry; - - -/** - * @inheritDoc - */ -ol.format.Polyline.prototype.readGeometryFromText = function(text, opt_options) { - var stride = ol.geom.SimpleGeometry.getStrideForLayout(this.geometryLayout_); - var flatCoordinates = ol.format.Polyline.decodeDeltas( - text, stride, this.factor_); - ol.geom.flat.flip.flipXY( - flatCoordinates, 0, flatCoordinates.length, stride, flatCoordinates); - var coordinates = ol.geom.flat.inflate.coordinates( - flatCoordinates, 0, flatCoordinates.length, stride); - - return /** @type {ol.geom.Geometry} */ ( - ol.format.Feature.transformWithOptions( - new ol.geom.LineString(coordinates, this.geometryLayout_), false, - this.adaptOptions(opt_options))); -}; - - -/** - * Read the projection from a Polyline source. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @return {ol.proj.Projection} Projection. - * @api - */ -ol.format.Polyline.prototype.readProjection; - - -/** - * @inheritDoc - */ -ol.format.Polyline.prototype.writeFeatureText = function(feature, opt_options) { - var geometry = feature.getGeometry(); - if (geometry) { - return this.writeGeometryText(geometry, opt_options); - } else { - ol.asserts.assert(false, 40); // Expected `feature` to have a geometry - return ''; - } -}; - - -/** - * @inheritDoc - */ -ol.format.Polyline.prototype.writeFeaturesText = function(features, opt_options) { - return this.writeFeatureText(features[0], opt_options); -}; - - -/** - * Write a single geometry in Polyline format. - * - * @function - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {string} Geometry. - * @api - */ -ol.format.Polyline.prototype.writeGeometry; - - -/** - * @inheritDoc - */ -ol.format.Polyline.prototype.writeGeometryText = function(geometry, opt_options) { - geometry = /** @type {ol.geom.LineString} */ - (ol.format.Feature.transformWithOptions( - geometry, true, this.adaptOptions(opt_options))); - var flatCoordinates = geometry.getFlatCoordinates(); - var stride = geometry.getStride(); - ol.geom.flat.flip.flipXY( - flatCoordinates, 0, flatCoordinates.length, stride, flatCoordinates); - return ol.format.Polyline.encodeDeltas(flatCoordinates, stride, this.factor_); -}; - -goog.provide('ol.format.TopoJSON'); - -goog.require('ol'); -goog.require('ol.Feature'); -goog.require('ol.format.Feature'); -goog.require('ol.format.JSONFeature'); -goog.require('ol.geom.LineString'); -goog.require('ol.geom.MultiLineString'); -goog.require('ol.geom.MultiPoint'); -goog.require('ol.geom.MultiPolygon'); -goog.require('ol.geom.Point'); -goog.require('ol.geom.Polygon'); -goog.require('ol.proj'); - - -/** - * @classdesc - * Feature format for reading data in the TopoJSON format. - * - * @constructor - * @extends {ol.format.JSONFeature} - * @param {olx.format.TopoJSONOptions=} opt_options Options. - * @api - */ -ol.format.TopoJSON = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - ol.format.JSONFeature.call(this); - - /** - * @private - * @type {string|undefined} - */ - this.layerName_ = options.layerName; - - /** - * @private - * @type {Array.<string>} - */ - this.layers_ = options.layers ? options.layers : null; - - /** - * @inheritDoc - */ - this.defaultDataProjection = ol.proj.get( - options.defaultDataProjection ? - options.defaultDataProjection : 'EPSG:4326'); - -}; -ol.inherits(ol.format.TopoJSON, ol.format.JSONFeature); - - -/** - * Concatenate arcs into a coordinate array. - * @param {Array.<number>} indices Indices of arcs to concatenate. Negative - * values indicate arcs need to be reversed. - * @param {Array.<Array.<ol.Coordinate>>} arcs Array of arcs (already - * transformed). - * @return {Array.<ol.Coordinate>} Coordinates array. - * @private - */ -ol.format.TopoJSON.concatenateArcs_ = function(indices, arcs) { - /** @type {Array.<ol.Coordinate>} */ - var coordinates = []; - var index, arc; - var i, ii; - var j, jj; - for (i = 0, ii = indices.length; i < ii; ++i) { - index = indices[i]; - if (i > 0) { - // splicing together arcs, discard last point - coordinates.pop(); - } - if (index >= 0) { - // forward arc - arc = arcs[index]; - } else { - // reverse arc - arc = arcs[~index].slice().reverse(); - } - coordinates.push.apply(coordinates, arc); - } - // provide fresh copies of coordinate arrays - for (j = 0, jj = coordinates.length; j < jj; ++j) { - coordinates[j] = coordinates[j].slice(); - } - return coordinates; -}; - - -/** - * Create a point from a TopoJSON geometry object. - * - * @param {TopoJSONGeometry} object TopoJSON object. - * @param {Array.<number>} scale Scale for each dimension. - * @param {Array.<number>} translate Translation for each dimension. - * @return {ol.geom.Point} Geometry. - * @private - */ -ol.format.TopoJSON.readPointGeometry_ = function(object, scale, translate) { - var coordinates = object.coordinates; - if (scale && translate) { - ol.format.TopoJSON.transformVertex_(coordinates, scale, translate); - } - return new ol.geom.Point(coordinates); -}; - - -/** - * Create a multi-point from a TopoJSON geometry object. - * - * @param {TopoJSONGeometry} object TopoJSON object. - * @param {Array.<number>} scale Scale for each dimension. - * @param {Array.<number>} translate Translation for each dimension. - * @return {ol.geom.MultiPoint} Geometry. - * @private - */ -ol.format.TopoJSON.readMultiPointGeometry_ = function(object, scale, - translate) { - var coordinates = object.coordinates; - var i, ii; - if (scale && translate) { - for (i = 0, ii = coordinates.length; i < ii; ++i) { - ol.format.TopoJSON.transformVertex_(coordinates[i], scale, translate); - } - } - return new ol.geom.MultiPoint(coordinates); -}; - - -/** - * Create a linestring from a TopoJSON geometry object. - * - * @param {TopoJSONGeometry} object TopoJSON object. - * @param {Array.<Array.<ol.Coordinate>>} arcs Array of arcs. - * @return {ol.geom.LineString} Geometry. - * @private - */ -ol.format.TopoJSON.readLineStringGeometry_ = function(object, arcs) { - var coordinates = ol.format.TopoJSON.concatenateArcs_(object.arcs, arcs); - return new ol.geom.LineString(coordinates); -}; - - -/** - * Create a multi-linestring from a TopoJSON geometry object. - * - * @param {TopoJSONGeometry} object TopoJSON object. - * @param {Array.<Array.<ol.Coordinate>>} arcs Array of arcs. - * @return {ol.geom.MultiLineString} Geometry. - * @private - */ -ol.format.TopoJSON.readMultiLineStringGeometry_ = function(object, arcs) { - var coordinates = []; - var i, ii; - for (i = 0, ii = object.arcs.length; i < ii; ++i) { - coordinates[i] = ol.format.TopoJSON.concatenateArcs_(object.arcs[i], arcs); - } - return new ol.geom.MultiLineString(coordinates); -}; - - -/** - * Create a polygon from a TopoJSON geometry object. - * - * @param {TopoJSONGeometry} object TopoJSON object. - * @param {Array.<Array.<ol.Coordinate>>} arcs Array of arcs. - * @return {ol.geom.Polygon} Geometry. - * @private - */ -ol.format.TopoJSON.readPolygonGeometry_ = function(object, arcs) { - var coordinates = []; - var i, ii; - for (i = 0, ii = object.arcs.length; i < ii; ++i) { - coordinates[i] = ol.format.TopoJSON.concatenateArcs_(object.arcs[i], arcs); - } - return new ol.geom.Polygon(coordinates); -}; - - -/** - * Create a multi-polygon from a TopoJSON geometry object. - * - * @param {TopoJSONGeometry} object TopoJSON object. - * @param {Array.<Array.<ol.Coordinate>>} arcs Array of arcs. - * @return {ol.geom.MultiPolygon} Geometry. - * @private - */ -ol.format.TopoJSON.readMultiPolygonGeometry_ = function(object, arcs) { - var coordinates = []; - var polyArray, ringCoords, j, jj; - var i, ii; - for (i = 0, ii = object.arcs.length; i < ii; ++i) { - // for each polygon - polyArray = object.arcs[i]; - ringCoords = []; - for (j = 0, jj = polyArray.length; j < jj; ++j) { - // for each ring - ringCoords[j] = ol.format.TopoJSON.concatenateArcs_(polyArray[j], arcs); - } - coordinates[i] = ringCoords; - } - return new ol.geom.MultiPolygon(coordinates); -}; - - -/** - * Create features from a TopoJSON GeometryCollection object. - * - * @param {TopoJSONGeometryCollection} collection TopoJSON Geometry - * object. - * @param {Array.<Array.<ol.Coordinate>>} arcs Array of arcs. - * @param {Array.<number>} scale Scale for each dimension. - * @param {Array.<number>} translate Translation for each dimension. - * @param {string|undefined} property Property to set the `GeometryCollection`'s parent - * object to. - * @param {string} name Name of the `Topology`'s child object. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {Array.<ol.Feature>} Array of features. - * @private - */ -ol.format.TopoJSON.readFeaturesFromGeometryCollection_ = function( - collection, arcs, scale, translate, property, name, opt_options) { - var geometries = collection.geometries; - var features = []; - var i, ii; - for (i = 0, ii = geometries.length; i < ii; ++i) { - features[i] = ol.format.TopoJSON.readFeatureFromGeometry_( - geometries[i], arcs, scale, translate, property, name, opt_options); - } - return features; -}; - - -/** - * Create a feature from a TopoJSON geometry object. - * - * @param {TopoJSONGeometry} object TopoJSON geometry object. - * @param {Array.<Array.<ol.Coordinate>>} arcs Array of arcs. - * @param {Array.<number>} scale Scale for each dimension. - * @param {Array.<number>} translate Translation for each dimension. - * @param {string|undefined} property Property to set the `GeometryCollection`'s parent - * object to. - * @param {string} name Name of the `Topology`'s child object. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {ol.Feature} Feature. - * @private - */ -ol.format.TopoJSON.readFeatureFromGeometry_ = function(object, arcs, - scale, translate, property, name, opt_options) { - var geometry; - var type = object.type; - var geometryReader = ol.format.TopoJSON.GEOMETRY_READERS_[type]; - if ((type === 'Point') || (type === 'MultiPoint')) { - geometry = geometryReader(object, scale, translate); - } else { - geometry = geometryReader(object, arcs); - } - var feature = new ol.Feature(); - feature.setGeometry(/** @type {ol.geom.Geometry} */ ( - ol.format.Feature.transformWithOptions(geometry, false, opt_options))); - if (object.id !== undefined) { - feature.setId(object.id); - } - var properties = object.properties; - if (property) { - if (!properties) { - properties = {}; - } - properties[property] = name; - } - if (properties) { - feature.setProperties(properties); - } - return feature; -}; - - -/** - * Read all features from a TopoJSON source. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @return {Array.<ol.Feature>} Features. - * @api - */ -ol.format.TopoJSON.prototype.readFeatures; - - -/** - * @inheritDoc - */ -ol.format.TopoJSON.prototype.readFeaturesFromObject = function( - object, opt_options) { - if (object.type == 'Topology') { - var topoJSONTopology = /** @type {TopoJSONTopology} */ (object); - var transform, scale = null, translate = null; - if (topoJSONTopology.transform) { - transform = topoJSONTopology.transform; - scale = transform.scale; - translate = transform.translate; - } - var arcs = topoJSONTopology.arcs; - if (transform) { - ol.format.TopoJSON.transformArcs_(arcs, scale, translate); - } - /** @type {Array.<ol.Feature>} */ - var features = []; - var topoJSONFeatures = topoJSONTopology.objects; - var property = this.layerName_; - var objectName, feature; - for (objectName in topoJSONFeatures) { - if (this.layers_ && this.layers_.indexOf(objectName) == -1) { - continue; - } - if (topoJSONFeatures[objectName].type === 'GeometryCollection') { - feature = /** @type {TopoJSONGeometryCollection} */ - (topoJSONFeatures[objectName]); - features.push.apply(features, - ol.format.TopoJSON.readFeaturesFromGeometryCollection_( - feature, arcs, scale, translate, property, objectName, opt_options)); - } else { - feature = /** @type {TopoJSONGeometry} */ - (topoJSONFeatures[objectName]); - features.push(ol.format.TopoJSON.readFeatureFromGeometry_( - feature, arcs, scale, translate, property, objectName, opt_options)); - } - } - return features; - } else { - return []; - } -}; - - -/** - * Apply a linear transform to array of arcs. The provided array of arcs is - * modified in place. - * - * @param {Array.<Array.<ol.Coordinate>>} arcs Array of arcs. - * @param {Array.<number>} scale Scale for each dimension. - * @param {Array.<number>} translate Translation for each dimension. - * @private - */ -ol.format.TopoJSON.transformArcs_ = function(arcs, scale, translate) { - var i, ii; - for (i = 0, ii = arcs.length; i < ii; ++i) { - ol.format.TopoJSON.transformArc_(arcs[i], scale, translate); - } -}; - - -/** - * Apply a linear transform to an arc. The provided arc is modified in place. - * - * @param {Array.<ol.Coordinate>} arc Arc. - * @param {Array.<number>} scale Scale for each dimension. - * @param {Array.<number>} translate Translation for each dimension. - * @private - */ -ol.format.TopoJSON.transformArc_ = function(arc, scale, translate) { - var x = 0; - var y = 0; - var vertex; - var i, ii; - for (i = 0, ii = arc.length; i < ii; ++i) { - vertex = arc[i]; - x += vertex[0]; - y += vertex[1]; - vertex[0] = x; - vertex[1] = y; - ol.format.TopoJSON.transformVertex_(vertex, scale, translate); - } -}; - - -/** - * Apply a linear transform to a vertex. The provided vertex is modified in - * place. - * - * @param {ol.Coordinate} vertex Vertex. - * @param {Array.<number>} scale Scale for each dimension. - * @param {Array.<number>} translate Translation for each dimension. - * @private - */ -ol.format.TopoJSON.transformVertex_ = function(vertex, scale, translate) { - vertex[0] = vertex[0] * scale[0] + translate[0]; - vertex[1] = vertex[1] * scale[1] + translate[1]; -}; - - -/** - * Read the projection from a TopoJSON source. - * - * @param {Document|Node|Object|string} object Source. - * @return {ol.proj.Projection} Projection. - * @override - * @api - */ -ol.format.TopoJSON.prototype.readProjection; - - -/** - * @inheritDoc - */ -ol.format.TopoJSON.prototype.readProjectionFromObject = function(object) { - return this.defaultDataProjection; -}; - - -/** - * @const - * @private - * @type {Object.<string, function(TopoJSONGeometry, Array, ...Array): ol.geom.Geometry>} - */ -ol.format.TopoJSON.GEOMETRY_READERS_ = { - 'Point': ol.format.TopoJSON.readPointGeometry_, - 'LineString': ol.format.TopoJSON.readLineStringGeometry_, - 'Polygon': ol.format.TopoJSON.readPolygonGeometry_, - 'MultiPoint': ol.format.TopoJSON.readMultiPointGeometry_, - 'MultiLineString': ol.format.TopoJSON.readMultiLineStringGeometry_, - 'MultiPolygon': ol.format.TopoJSON.readMultiPolygonGeometry_ -}; - - -/** - * Not implemented. - * @inheritDoc - */ -ol.format.TopoJSON.prototype.writeFeatureObject = function(feature, opt_options) {}; - - -/** - * Not implemented. - * @inheritDoc - */ -ol.format.TopoJSON.prototype.writeFeaturesObject = function(features, opt_options) {}; - - -/** - * Not implemented. - * @inheritDoc - */ -ol.format.TopoJSON.prototype.writeGeometryObject = function(geometry, opt_options) {}; - - -/** - * Not implemented. - * @override - */ -ol.format.TopoJSON.prototype.readGeometryFromObject = function() {}; - - -/** - * Not implemented. - * @override - */ -ol.format.TopoJSON.prototype.readFeatureFromObject = function() {}; - -goog.provide('ol.format.WFS'); - -goog.require('ol'); -goog.require('ol.asserts'); -goog.require('ol.format.GML2'); -goog.require('ol.format.GML3'); -goog.require('ol.format.GMLBase'); -goog.require('ol.format.filter'); -goog.require('ol.format.XMLFeature'); -goog.require('ol.format.XSD'); -goog.require('ol.geom.Geometry'); -goog.require('ol.obj'); -goog.require('ol.proj'); -goog.require('ol.xml'); - - -/** - * @classdesc - * Feature format for reading and writing data in the WFS format. - * By default, supports WFS version 1.1.0. You can pass a GML format - * as option if you want to read a WFS that contains GML2 (WFS 1.0.0). - * Also see {@link ol.format.GMLBase} which is used by this format. - * - * @constructor - * @param {olx.format.WFSOptions=} opt_options - * Optional configuration object. - * @extends {ol.format.XMLFeature} - * @api - */ -ol.format.WFS = function(opt_options) { - var options = opt_options ? opt_options : {}; - - /** - * @private - * @type {Array.<string>|string|undefined} - */ - this.featureType_ = options.featureType; - - /** - * @private - * @type {Object.<string, string>|string|undefined} - */ - this.featureNS_ = options.featureNS; - - /** - * @private - * @type {ol.format.GMLBase} - */ - this.gmlFormat_ = options.gmlFormat ? - options.gmlFormat : new ol.format.GML3(); - - /** - * @private - * @type {string} - */ - this.schemaLocation_ = options.schemaLocation ? - options.schemaLocation : - ol.format.WFS.SCHEMA_LOCATIONS[ol.format.WFS.DEFAULT_VERSION]; - - ol.format.XMLFeature.call(this); -}; -ol.inherits(ol.format.WFS, ol.format.XMLFeature); - - -/** - * @const - * @type {string} - */ -ol.format.WFS.FEATURE_PREFIX = 'feature'; - - -/** - * @const - * @type {string} - */ -ol.format.WFS.XMLNS = 'http://www.w3.org/2000/xmlns/'; - - -/** - * @const - * @type {string} - */ -ol.format.WFS.OGCNS = 'http://www.opengis.net/ogc'; - - -/** - * @const - * @type {string} - */ -ol.format.WFS.WFSNS = 'http://www.opengis.net/wfs'; - - -/** - * @const - * @type {string} - */ -ol.format.WFS.FESNS = 'http://www.opengis.net/fes'; - - -/** - * @const - * @type {Object.<string, string>} - */ -ol.format.WFS.SCHEMA_LOCATIONS = { - '1.1.0': 'http://www.opengis.net/wfs ' + - 'http://schemas.opengis.net/wfs/1.1.0/wfs.xsd', - '1.0.0': 'http://www.opengis.net/wfs ' + - 'http://schemas.opengis.net/wfs/1.0.0/wfs.xsd' -}; - - -/** - * @const - * @type {string} - */ -ol.format.WFS.DEFAULT_VERSION = '1.1.0'; - - -/** - * Read all features from a WFS FeatureCollection. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {Array.<ol.Feature>} Features. - * @api - */ -ol.format.WFS.prototype.readFeatures; - - -/** - * @inheritDoc - */ -ol.format.WFS.prototype.readFeaturesFromNode = function(node, opt_options) { - var context = /** @type {ol.XmlNodeStackItem} */ ({ - 'featureType': this.featureType_, - 'featureNS': this.featureNS_ - }); - ol.obj.assign(context, this.getReadOptions(node, - opt_options ? opt_options : {})); - var objectStack = [context]; - this.gmlFormat_.FEATURE_COLLECTION_PARSERS[ol.format.GMLBase.GMLNS][ - 'featureMember'] = - ol.xml.makeArrayPusher(ol.format.GMLBase.prototype.readFeaturesInternal); - var features = ol.xml.pushParseAndPop([], - this.gmlFormat_.FEATURE_COLLECTION_PARSERS, node, - objectStack, this.gmlFormat_); - if (!features) { - features = []; - } - return features; -}; - - -/** - * Read transaction response of the source. - * - * @param {Document|Node|Object|string} source Source. - * @return {ol.WFSTransactionResponse|undefined} Transaction response. - * @api - */ -ol.format.WFS.prototype.readTransactionResponse = function(source) { - if (ol.xml.isDocument(source)) { - return this.readTransactionResponseFromDocument( - /** @type {Document} */ (source)); - } else if (ol.xml.isNode(source)) { - return this.readTransactionResponseFromNode(/** @type {Node} */ (source)); - } else if (typeof source === 'string') { - var doc = ol.xml.parse(source); - return this.readTransactionResponseFromDocument(doc); - } else { - return undefined; - } -}; - - -/** - * Read feature collection metadata of the source. - * - * @param {Document|Node|Object|string} source Source. - * @return {ol.WFSFeatureCollectionMetadata|undefined} - * FeatureCollection metadata. - * @api - */ -ol.format.WFS.prototype.readFeatureCollectionMetadata = function(source) { - if (ol.xml.isDocument(source)) { - return this.readFeatureCollectionMetadataFromDocument( - /** @type {Document} */ (source)); - } else if (ol.xml.isNode(source)) { - return this.readFeatureCollectionMetadataFromNode( - /** @type {Node} */ (source)); - } else if (typeof source === 'string') { - var doc = ol.xml.parse(source); - return this.readFeatureCollectionMetadataFromDocument(doc); - } else { - return undefined; - } -}; - - -/** - * @param {Document} doc Document. - * @return {ol.WFSFeatureCollectionMetadata|undefined} - * FeatureCollection metadata. - */ -ol.format.WFS.prototype.readFeatureCollectionMetadataFromDocument = function(doc) { - for (var n = doc.firstChild; n; n = n.nextSibling) { - if (n.nodeType == Node.ELEMENT_NODE) { - return this.readFeatureCollectionMetadataFromNode(n); - } - } - return undefined; -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WFS.FEATURE_COLLECTION_PARSERS_ = { - 'http://www.opengis.net/gml': { - 'boundedBy': ol.xml.makeObjectPropertySetter( - ol.format.GMLBase.prototype.readGeometryElement, 'bounds') - } -}; - - -/** - * @param {Node} node Node. - * @return {ol.WFSFeatureCollectionMetadata|undefined} - * FeatureCollection metadata. - */ -ol.format.WFS.prototype.readFeatureCollectionMetadataFromNode = function(node) { - var result = {}; - var value = ol.format.XSD.readNonNegativeIntegerString( - node.getAttribute('numberOfFeatures')); - result['numberOfFeatures'] = value; - return ol.xml.pushParseAndPop( - /** @type {ol.WFSFeatureCollectionMetadata} */ (result), - ol.format.WFS.FEATURE_COLLECTION_PARSERS_, node, [], this.gmlFormat_); -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WFS.TRANSACTION_SUMMARY_PARSERS_ = { - 'http://www.opengis.net/wfs': { - 'totalInserted': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readNonNegativeInteger), - 'totalUpdated': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readNonNegativeInteger), - 'totalDeleted': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readNonNegativeInteger) - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Transaction Summary. - * @private - */ -ol.format.WFS.readTransactionSummary_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - {}, ol.format.WFS.TRANSACTION_SUMMARY_PARSERS_, node, objectStack); -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WFS.OGC_FID_PARSERS_ = { - 'http://www.opengis.net/ogc': { - 'FeatureId': ol.xml.makeArrayPusher(function(node, objectStack) { - return node.getAttribute('fid'); - }) - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - */ -ol.format.WFS.fidParser_ = function(node, objectStack) { - ol.xml.parseNode(ol.format.WFS.OGC_FID_PARSERS_, node, objectStack); -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WFS.INSERT_RESULTS_PARSERS_ = { - 'http://www.opengis.net/wfs': { - 'Feature': ol.format.WFS.fidParser_ - } -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Array.<string>|undefined} Insert results. - * @private - */ -ol.format.WFS.readInsertResults_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - [], ol.format.WFS.INSERT_RESULTS_PARSERS_, node, objectStack); -}; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WFS.TRANSACTION_RESPONSE_PARSERS_ = { - 'http://www.opengis.net/wfs': { - 'TransactionSummary': ol.xml.makeObjectPropertySetter( - ol.format.WFS.readTransactionSummary_, 'transactionSummary'), - 'InsertResults': ol.xml.makeObjectPropertySetter( - ol.format.WFS.readInsertResults_, 'insertIds') - } -}; - - -/** - * @param {Document} doc Document. - * @return {ol.WFSTransactionResponse|undefined} Transaction response. - */ -ol.format.WFS.prototype.readTransactionResponseFromDocument = function(doc) { - for (var n = doc.firstChild; n; n = n.nextSibling) { - if (n.nodeType == Node.ELEMENT_NODE) { - return this.readTransactionResponseFromNode(n); - } - } - return undefined; -}; - - -/** - * @param {Node} node Node. - * @return {ol.WFSTransactionResponse|undefined} Transaction response. - */ -ol.format.WFS.prototype.readTransactionResponseFromNode = function(node) { - return ol.xml.pushParseAndPop( - /** @type {ol.WFSTransactionResponse} */({}), - ol.format.WFS.TRANSACTION_RESPONSE_PARSERS_, node, []); -}; - - -/** - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.WFS.QUERY_SERIALIZERS_ = { - 'http://www.opengis.net/wfs': { - 'PropertyName': ol.xml.makeChildAppender(ol.format.XSD.writeStringTextNode) - } -}; - - -/** - * @param {Node} node Node. - * @param {ol.Feature} feature Feature. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeFeature_ = function(node, feature, objectStack) { - var context = objectStack[objectStack.length - 1]; - var featureType = context['featureType']; - var featureNS = context['featureNS']; - var gmlVersion = context['gmlVersion']; - var child = ol.xml.createElementNS(featureNS, featureType); - node.appendChild(child); - if (gmlVersion === 2) { - ol.format.GML2.prototype.writeFeatureElement(child, feature, objectStack); - } else { - ol.format.GML3.prototype.writeFeatureElement(child, feature, objectStack); - } -}; - - -/** - * @param {Node} node Node. - * @param {number|string} fid Feature identifier. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeOgcFidFilter_ = function(node, fid, objectStack) { - var filter = ol.xml.createElementNS(ol.format.WFS.OGCNS, 'Filter'); - var child = ol.xml.createElementNS(ol.format.WFS.OGCNS, 'FeatureId'); - filter.appendChild(child); - child.setAttribute('fid', fid); - node.appendChild(filter); -}; - - -/** - * @param {string|undefined} featurePrefix The prefix of the feature. - * @param {string} featureType The type of the feature. - * @returns {string} The value of the typeName property. - * @private - */ -ol.format.WFS.getTypeName_ = function(featurePrefix, featureType) { - featurePrefix = featurePrefix ? featurePrefix : - ol.format.WFS.FEATURE_PREFIX; - var prefix = featurePrefix + ':'; - // The featureType already contains the prefix. - if (featureType.indexOf(prefix) === 0) { - return featureType; - } else { - return prefix + featureType; - } -}; - - -/** - * @param {Node} node Node. - * @param {ol.Feature} feature Feature. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeDelete_ = function(node, feature, objectStack) { - var context = objectStack[objectStack.length - 1]; - ol.asserts.assert(feature.getId() !== undefined, 26); // Features must have an id set - var featureType = context['featureType']; - var featurePrefix = context['featurePrefix']; - var featureNS = context['featureNS']; - var typeName = ol.format.WFS.getTypeName_(featurePrefix, featureType); - node.setAttribute('typeName', typeName); - ol.xml.setAttributeNS(node, ol.format.WFS.XMLNS, 'xmlns:' + featurePrefix, - featureNS); - var fid = feature.getId(); - if (fid !== undefined) { - ol.format.WFS.writeOgcFidFilter_(node, fid, objectStack); - } -}; - - -/** - * @param {Node} node Node. - * @param {ol.Feature} feature Feature. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeUpdate_ = function(node, feature, objectStack) { - var context = objectStack[objectStack.length - 1]; - ol.asserts.assert(feature.getId() !== undefined, 27); // Features must have an id set - var featureType = context['featureType']; - var featurePrefix = context['featurePrefix']; - var featureNS = context['featureNS']; - var typeName = ol.format.WFS.getTypeName_(featurePrefix, featureType); - var geometryName = feature.getGeometryName(); - node.setAttribute('typeName', typeName); - ol.xml.setAttributeNS(node, ol.format.WFS.XMLNS, 'xmlns:' + featurePrefix, - featureNS); - var fid = feature.getId(); - if (fid !== undefined) { - var keys = feature.getKeys(); - var values = []; - for (var i = 0, ii = keys.length; i < ii; i++) { - var value = feature.get(keys[i]); - if (value !== undefined) { - var name = keys[i]; - if (value instanceof ol.geom.Geometry) { - name = geometryName; - } - values.push({name: name, value: value}); - } - } - ol.xml.pushSerializeAndPop(/** @type {ol.XmlNodeStackItem} */ ( - {'gmlVersion': context['gmlVersion'], node: node, - 'hasZ': context['hasZ'], 'srsName': context['srsName']}), - ol.format.WFS.TRANSACTION_SERIALIZERS_, - ol.xml.makeSimpleNodeFactory('Property'), values, - objectStack); - ol.format.WFS.writeOgcFidFilter_(node, fid, objectStack); - } -}; - - -/** - * @param {Node} node Node. - * @param {Object} pair Property name and value. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeProperty_ = function(node, pair, objectStack) { - var name = ol.xml.createElementNS(ol.format.WFS.WFSNS, 'Name'); - var context = objectStack[objectStack.length - 1]; - var gmlVersion = context['gmlVersion']; - node.appendChild(name); - ol.format.XSD.writeStringTextNode(name, pair.name); - if (pair.value !== undefined && pair.value !== null) { - var value = ol.xml.createElementNS(ol.format.WFS.WFSNS, 'Value'); - node.appendChild(value); - if (pair.value instanceof ol.geom.Geometry) { - if (gmlVersion === 2) { - ol.format.GML2.prototype.writeGeometryElement(value, - pair.value, objectStack); - } else { - ol.format.GML3.prototype.writeGeometryElement(value, - pair.value, objectStack); - } - } else { - ol.format.XSD.writeStringTextNode(value, pair.value); - } - } -}; - - -/** - * @param {Node} node Node. - * @param {{vendorId: string, safeToIgnore: boolean, value: string}} - * nativeElement The native element. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeNative_ = function(node, nativeElement, objectStack) { - if (nativeElement.vendorId) { - node.setAttribute('vendorId', nativeElement.vendorId); - } - if (nativeElement.safeToIgnore !== undefined) { - node.setAttribute('safeToIgnore', nativeElement.safeToIgnore); - } - if (nativeElement.value !== undefined) { - ol.format.XSD.writeStringTextNode(node, nativeElement.value); - } -}; - - -/** - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.WFS.TRANSACTION_SERIALIZERS_ = { - 'http://www.opengis.net/wfs': { - 'Insert': ol.xml.makeChildAppender(ol.format.WFS.writeFeature_), - 'Update': ol.xml.makeChildAppender(ol.format.WFS.writeUpdate_), - 'Delete': ol.xml.makeChildAppender(ol.format.WFS.writeDelete_), - 'Property': ol.xml.makeChildAppender(ol.format.WFS.writeProperty_), - 'Native': ol.xml.makeChildAppender(ol.format.WFS.writeNative_) - } -}; - - -/** - * @param {Node} node Node. - * @param {string} featureType Feature type. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeQuery_ = function(node, featureType, objectStack) { - var context = /** @type {Object} */ (objectStack[objectStack.length - 1]); - var featurePrefix = context['featurePrefix']; - var featureNS = context['featureNS']; - var propertyNames = context['propertyNames']; - var srsName = context['srsName']; - var typeName; - // If feature prefix is not defined, we must not use the default prefix. - if (featurePrefix) { - typeName = ol.format.WFS.getTypeName_(featurePrefix, featureType); - } else { - typeName = featureType; - } - node.setAttribute('typeName', typeName); - if (srsName) { - node.setAttribute('srsName', srsName); - } - if (featureNS) { - ol.xml.setAttributeNS(node, ol.format.WFS.XMLNS, 'xmlns:' + featurePrefix, - featureNS); - } - var item = /** @type {ol.XmlNodeStackItem} */ (ol.obj.assign({}, context)); - item.node = node; - ol.xml.pushSerializeAndPop(item, - ol.format.WFS.QUERY_SERIALIZERS_, - ol.xml.makeSimpleNodeFactory('PropertyName'), propertyNames, - objectStack); - var filter = context['filter']; - if (filter) { - var child = ol.xml.createElementNS(ol.format.WFS.OGCNS, 'Filter'); - node.appendChild(child); - ol.format.WFS.writeFilterCondition_(child, filter, objectStack); - } -}; - - -/** - * @param {Node} node Node. - * @param {ol.format.filter.Filter} filter Filter. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeFilterCondition_ = function(node, filter, objectStack) { - /** @type {ol.XmlNodeStackItem} */ - var item = {node: node}; - ol.xml.pushSerializeAndPop(item, - ol.format.WFS.GETFEATURE_SERIALIZERS_, - ol.xml.makeSimpleNodeFactory(filter.getTagName()), - [filter], objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {ol.format.filter.Bbox} filter Filter. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeBboxFilter_ = function(node, filter, objectStack) { - var context = objectStack[objectStack.length - 1]; - context['srsName'] = filter.srsName; - - ol.format.WFS.writeOgcPropertyName_(node, filter.geometryName); - ol.format.GML3.prototype.writeGeometryElement(node, filter.extent, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {ol.format.filter.Intersects} filter Filter. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeIntersectsFilter_ = function(node, filter, objectStack) { - var context = objectStack[objectStack.length - 1]; - context['srsName'] = filter.srsName; - - ol.format.WFS.writeOgcPropertyName_(node, filter.geometryName); - ol.format.GML3.prototype.writeGeometryElement(node, filter.geometry, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {ol.format.filter.Within} filter Filter. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeWithinFilter_ = function(node, filter, objectStack) { - var context = objectStack[objectStack.length - 1]; - context['srsName'] = filter.srsName; - - ol.format.WFS.writeOgcPropertyName_(node, filter.geometryName); - ol.format.GML3.prototype.writeGeometryElement(node, filter.geometry, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {ol.format.filter.During} filter Filter. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeDuringFilter_ = function(node, filter, objectStack) { - - var valueReference = ol.xml.createElementNS(ol.format.WFS.FESNS, 'ValueReference'); - ol.format.XSD.writeStringTextNode(valueReference, filter.propertyName); - node.appendChild(valueReference); - - var timePeriod = ol.xml.createElementNS(ol.format.GMLBase.GMLNS, 'TimePeriod'); - - node.appendChild(timePeriod); - - var begin = ol.xml.createElementNS(ol.format.GMLBase.GMLNS, 'begin'); - timePeriod.appendChild(begin); - ol.format.WFS.writeTimeInstant_(begin, filter.begin); - - var end = ol.xml.createElementNS(ol.format.GMLBase.GMLNS, 'end'); - timePeriod.appendChild(end); - ol.format.WFS.writeTimeInstant_(end, filter.end); -}; - - -/** - * @param {Node} node Node. - * @param {ol.format.filter.LogicalNary} filter Filter. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeLogicalFilter_ = function(node, filter, objectStack) { - /** @type {ol.XmlNodeStackItem} */ - var item = {node: node}; - var conditions = filter.conditions; - for (var i = 0, ii = conditions.length; i < ii; ++i) { - var condition = conditions[i]; - ol.xml.pushSerializeAndPop(item, - ol.format.WFS.GETFEATURE_SERIALIZERS_, - ol.xml.makeSimpleNodeFactory(condition.getTagName()), - [condition], objectStack); - } -}; - - -/** - * @param {Node} node Node. - * @param {ol.format.filter.Not} filter Filter. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeNotFilter_ = function(node, filter, objectStack) { - /** @type {ol.XmlNodeStackItem} */ - var item = {node: node}; - var condition = filter.condition; - ol.xml.pushSerializeAndPop(item, - ol.format.WFS.GETFEATURE_SERIALIZERS_, - ol.xml.makeSimpleNodeFactory(condition.getTagName()), - [condition], objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {ol.format.filter.ComparisonBinary} filter Filter. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeComparisonFilter_ = function(node, filter, objectStack) { - if (filter.matchCase !== undefined) { - node.setAttribute('matchCase', filter.matchCase.toString()); - } - ol.format.WFS.writeOgcPropertyName_(node, filter.propertyName); - ol.format.WFS.writeOgcLiteral_(node, '' + filter.expression); -}; - - -/** - * @param {Node} node Node. - * @param {ol.format.filter.IsNull} filter Filter. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeIsNullFilter_ = function(node, filter, objectStack) { - ol.format.WFS.writeOgcPropertyName_(node, filter.propertyName); -}; - - -/** - * @param {Node} node Node. - * @param {ol.format.filter.IsBetween} filter Filter. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeIsBetweenFilter_ = function(node, filter, objectStack) { - ol.format.WFS.writeOgcPropertyName_(node, filter.propertyName); - - var lowerBoundary = ol.xml.createElementNS(ol.format.WFS.OGCNS, 'LowerBoundary'); - node.appendChild(lowerBoundary); - ol.format.WFS.writeOgcLiteral_(lowerBoundary, '' + filter.lowerBoundary); - - var upperBoundary = ol.xml.createElementNS(ol.format.WFS.OGCNS, 'UpperBoundary'); - node.appendChild(upperBoundary); - ol.format.WFS.writeOgcLiteral_(upperBoundary, '' + filter.upperBoundary); -}; - - -/** - * @param {Node} node Node. - * @param {ol.format.filter.IsLike} filter Filter. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeIsLikeFilter_ = function(node, filter, objectStack) { - node.setAttribute('wildCard', filter.wildCard); - node.setAttribute('singleChar', filter.singleChar); - node.setAttribute('escapeChar', filter.escapeChar); - if (filter.matchCase !== undefined) { - node.setAttribute('matchCase', filter.matchCase.toString()); - } - ol.format.WFS.writeOgcPropertyName_(node, filter.propertyName); - ol.format.WFS.writeOgcLiteral_(node, '' + filter.pattern); -}; - - -/** - * @param {string} tagName Tag name. - * @param {Node} node Node. - * @param {string} value Value. - * @private - */ -ol.format.WFS.writeOgcExpression_ = function(tagName, node, value) { - var property = ol.xml.createElementNS(ol.format.WFS.OGCNS, tagName); - ol.format.XSD.writeStringTextNode(property, value); - node.appendChild(property); -}; - - -/** - * @param {Node} node Node. - * @param {string} value PropertyName value. - * @private - */ -ol.format.WFS.writeOgcPropertyName_ = function(node, value) { - ol.format.WFS.writeOgcExpression_('PropertyName', node, value); -}; - - -/** - * @param {Node} node Node. - * @param {string} value PropertyName value. - * @private - */ -ol.format.WFS.writeOgcLiteral_ = function(node, value) { - ol.format.WFS.writeOgcExpression_('Literal', node, value); -}; - - -/** - * @param {Node} node Node. - * @param {string} time PropertyName value. - * @private - */ -ol.format.WFS.writeTimeInstant_ = function(node, time) { - var timeInstant = ol.xml.createElementNS(ol.format.GMLBase.GMLNS, 'TimeInstant'); - node.appendChild(timeInstant); - - var timePosition = ol.xml.createElementNS(ol.format.GMLBase.GMLNS, 'timePosition'); - timeInstant.appendChild(timePosition); - ol.format.XSD.writeStringTextNode(timePosition, time); -}; - - -/** - * @type {Object.<string, Object.<string, ol.XmlSerializer>>} - * @private - */ -ol.format.WFS.GETFEATURE_SERIALIZERS_ = { - 'http://www.opengis.net/wfs': { - 'Query': ol.xml.makeChildAppender(ol.format.WFS.writeQuery_) - }, - 'http://www.opengis.net/ogc': { - 'During': ol.xml.makeChildAppender(ol.format.WFS.writeDuringFilter_), - 'And': ol.xml.makeChildAppender(ol.format.WFS.writeLogicalFilter_), - 'Or': ol.xml.makeChildAppender(ol.format.WFS.writeLogicalFilter_), - 'Not': ol.xml.makeChildAppender(ol.format.WFS.writeNotFilter_), - 'BBOX': ol.xml.makeChildAppender(ol.format.WFS.writeBboxFilter_), - 'Intersects': ol.xml.makeChildAppender(ol.format.WFS.writeIntersectsFilter_), - 'Within': ol.xml.makeChildAppender(ol.format.WFS.writeWithinFilter_), - 'PropertyIsEqualTo': ol.xml.makeChildAppender(ol.format.WFS.writeComparisonFilter_), - 'PropertyIsNotEqualTo': ol.xml.makeChildAppender(ol.format.WFS.writeComparisonFilter_), - 'PropertyIsLessThan': ol.xml.makeChildAppender(ol.format.WFS.writeComparisonFilter_), - 'PropertyIsLessThanOrEqualTo': ol.xml.makeChildAppender(ol.format.WFS.writeComparisonFilter_), - 'PropertyIsGreaterThan': ol.xml.makeChildAppender(ol.format.WFS.writeComparisonFilter_), - 'PropertyIsGreaterThanOrEqualTo': ol.xml.makeChildAppender(ol.format.WFS.writeComparisonFilter_), - 'PropertyIsNull': ol.xml.makeChildAppender(ol.format.WFS.writeIsNullFilter_), - 'PropertyIsBetween': ol.xml.makeChildAppender(ol.format.WFS.writeIsBetweenFilter_), - 'PropertyIsLike': ol.xml.makeChildAppender(ol.format.WFS.writeIsLikeFilter_) - } -}; - - -/** - * Encode filter as WFS `Filter` and return the Node. - * - * @param {ol.format.filter.Filter} filter Filter. - * @return {Node} Result. - * @api - */ -ol.format.WFS.writeFilter = function(filter) { - var child = ol.xml.createElementNS(ol.format.WFS.OGCNS, 'Filter'); - ol.format.WFS.writeFilterCondition_(child, filter, []); - return child; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<string>} featureTypes Feature types. - * @param {Array.<*>} objectStack Node stack. - * @private - */ -ol.format.WFS.writeGetFeature_ = function(node, featureTypes, objectStack) { - var context = /** @type {Object} */ (objectStack[objectStack.length - 1]); - var item = /** @type {ol.XmlNodeStackItem} */ (ol.obj.assign({}, context)); - item.node = node; - ol.xml.pushSerializeAndPop(item, - ol.format.WFS.GETFEATURE_SERIALIZERS_, - ol.xml.makeSimpleNodeFactory('Query'), featureTypes, - objectStack); -}; - - -/** - * Encode format as WFS `GetFeature` and return the Node. - * - * @param {olx.format.WFSWriteGetFeatureOptions} options Options. - * @return {Node} Result. - * @api - */ -ol.format.WFS.prototype.writeGetFeature = function(options) { - var node = ol.xml.createElementNS(ol.format.WFS.WFSNS, 'GetFeature'); - node.setAttribute('service', 'WFS'); - node.setAttribute('version', '1.1.0'); - var filter; - if (options) { - if (options.handle) { - node.setAttribute('handle', options.handle); - } - if (options.outputFormat) { - node.setAttribute('outputFormat', options.outputFormat); - } - if (options.maxFeatures !== undefined) { - node.setAttribute('maxFeatures', options.maxFeatures); - } - if (options.resultType) { - node.setAttribute('resultType', options.resultType); - } - if (options.startIndex !== undefined) { - node.setAttribute('startIndex', options.startIndex); - } - if (options.count !== undefined) { - node.setAttribute('count', options.count); - } - filter = options.filter; - if (options.bbox) { - ol.asserts.assert(options.geometryName, - 12); // `options.geometryName` must also be provided when `options.bbox` is set - var bbox = ol.format.filter.bbox( - /** @type {string} */ (options.geometryName), options.bbox, options.srsName); - if (filter) { - // if bbox and filter are both set, combine the two into a single filter - filter = ol.format.filter.and(filter, bbox); - } else { - filter = bbox; - } - } - } - ol.xml.setAttributeNS(node, 'http://www.w3.org/2001/XMLSchema-instance', - 'xsi:schemaLocation', this.schemaLocation_); - /** @type {ol.XmlNodeStackItem} */ - var context = { - node: node, - 'srsName': options.srsName, - 'featureNS': options.featureNS ? options.featureNS : this.featureNS_, - 'featurePrefix': options.featurePrefix, - 'geometryName': options.geometryName, - 'filter': filter, - 'propertyNames': options.propertyNames ? options.propertyNames : [] - }; - ol.asserts.assert(Array.isArray(options.featureTypes), - 11); // `options.featureTypes` should be an Array - ol.format.WFS.writeGetFeature_(node, /** @type {!Array.<string>} */ (options.featureTypes), [context]); - return node; -}; - - -/** - * Encode format as WFS `Transaction` and return the Node. - * - * @param {Array.<ol.Feature>} inserts The features to insert. - * @param {Array.<ol.Feature>} updates The features to update. - * @param {Array.<ol.Feature>} deletes The features to delete. - * @param {olx.format.WFSWriteTransactionOptions} options Write options. - * @return {Node} Result. - * @api - */ -ol.format.WFS.prototype.writeTransaction = function(inserts, updates, deletes, - options) { - var objectStack = []; - var node = ol.xml.createElementNS(ol.format.WFS.WFSNS, 'Transaction'); - var version = options.version ? - options.version : ol.format.WFS.DEFAULT_VERSION; - var gmlVersion = version === '1.0.0' ? 2 : 3; - node.setAttribute('service', 'WFS'); - node.setAttribute('version', version); - var baseObj; - /** @type {ol.XmlNodeStackItem} */ - var obj; - if (options) { - baseObj = options.gmlOptions ? options.gmlOptions : {}; - if (options.handle) { - node.setAttribute('handle', options.handle); - } - } - var schemaLocation = ol.format.WFS.SCHEMA_LOCATIONS[version]; - ol.xml.setAttributeNS(node, 'http://www.w3.org/2001/XMLSchema-instance', - 'xsi:schemaLocation', schemaLocation); - var featurePrefix = options.featurePrefix ? options.featurePrefix : ol.format.WFS.FEATURE_PREFIX; - if (inserts) { - obj = {node: node, 'featureNS': options.featureNS, - 'featureType': options.featureType, 'featurePrefix': featurePrefix, - 'gmlVersion': gmlVersion, 'hasZ': options.hasZ, 'srsName': options.srsName}; - ol.obj.assign(obj, baseObj); - ol.xml.pushSerializeAndPop(obj, - ol.format.WFS.TRANSACTION_SERIALIZERS_, - ol.xml.makeSimpleNodeFactory('Insert'), inserts, - objectStack); - } - if (updates) { - obj = {node: node, 'featureNS': options.featureNS, - 'featureType': options.featureType, 'featurePrefix': featurePrefix, - 'gmlVersion': gmlVersion, 'hasZ': options.hasZ, 'srsName': options.srsName}; - ol.obj.assign(obj, baseObj); - ol.xml.pushSerializeAndPop(obj, - ol.format.WFS.TRANSACTION_SERIALIZERS_, - ol.xml.makeSimpleNodeFactory('Update'), updates, - objectStack); - } - if (deletes) { - ol.xml.pushSerializeAndPop({node: node, 'featureNS': options.featureNS, - 'featureType': options.featureType, 'featurePrefix': featurePrefix, - 'gmlVersion': gmlVersion, 'srsName': options.srsName}, - ol.format.WFS.TRANSACTION_SERIALIZERS_, - ol.xml.makeSimpleNodeFactory('Delete'), deletes, - objectStack); - } - if (options.nativeElements) { - ol.xml.pushSerializeAndPop({node: node, 'featureNS': options.featureNS, - 'featureType': options.featureType, 'featurePrefix': featurePrefix, - 'gmlVersion': gmlVersion, 'srsName': options.srsName}, - ol.format.WFS.TRANSACTION_SERIALIZERS_, - ol.xml.makeSimpleNodeFactory('Native'), options.nativeElements, - objectStack); - } - return node; -}; - - -/** - * Read the projection from a WFS source. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @return {?ol.proj.Projection} Projection. - * @api - */ -ol.format.WFS.prototype.readProjection; - - -/** - * @inheritDoc - */ -ol.format.WFS.prototype.readProjectionFromDocument = function(doc) { - for (var n = doc.firstChild; n; n = n.nextSibling) { - if (n.nodeType == Node.ELEMENT_NODE) { - return this.readProjectionFromNode(n); - } - } - return null; -}; - - -/** - * @inheritDoc - */ -ol.format.WFS.prototype.readProjectionFromNode = function(node) { - if (node.firstElementChild && - node.firstElementChild.firstElementChild) { - node = node.firstElementChild.firstElementChild; - for (var n = node.firstElementChild; n; n = n.nextElementSibling) { - if (!(n.childNodes.length === 0 || - (n.childNodes.length === 1 && - n.firstChild.nodeType === 3))) { - var objectStack = [{}]; - this.gmlFormat_.readGeometryElement(n, objectStack); - return ol.proj.get(objectStack.pop().srsName); - } - } - } - - return null; -}; - -goog.provide('ol.format.WKT'); - -goog.require('ol'); -goog.require('ol.Feature'); -goog.require('ol.format.Feature'); -goog.require('ol.format.TextFeature'); -goog.require('ol.geom.GeometryCollection'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.LineString'); -goog.require('ol.geom.MultiLineString'); -goog.require('ol.geom.MultiPoint'); -goog.require('ol.geom.MultiPolygon'); -goog.require('ol.geom.Point'); -goog.require('ol.geom.Polygon'); -goog.require('ol.geom.SimpleGeometry'); - - -/** - * @classdesc - * Geometry format for reading and writing data in the `WellKnownText` (WKT) - * format. - * - * @constructor - * @extends {ol.format.TextFeature} - * @param {olx.format.WKTOptions=} opt_options Options. - * @api - */ -ol.format.WKT = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - ol.format.TextFeature.call(this); - - /** - * Split GeometryCollection into multiple features. - * @type {boolean} - * @private - */ - this.splitCollection_ = options.splitCollection !== undefined ? - options.splitCollection : false; - -}; -ol.inherits(ol.format.WKT, ol.format.TextFeature); - - -/** - * @const - * @type {string} - */ -ol.format.WKT.EMPTY = 'EMPTY'; - - -/** - * @const - * @type {string} - */ -ol.format.WKT.Z = 'Z'; - - -/** - * @const - * @type {string} - */ -ol.format.WKT.M = 'M'; - - -/** - * @const - * @type {string} - */ -ol.format.WKT.ZM = 'ZM'; - - -/** - * @param {ol.geom.Point} geom Point geometry. - * @return {string} Coordinates part of Point as WKT. - * @private - */ -ol.format.WKT.encodePointGeometry_ = function(geom) { - var coordinates = geom.getCoordinates(); - if (coordinates.length === 0) { - return ''; - } - return coordinates.join(' '); -}; - - -/** - * @param {ol.geom.MultiPoint} geom MultiPoint geometry. - * @return {string} Coordinates part of MultiPoint as WKT. - * @private - */ -ol.format.WKT.encodeMultiPointGeometry_ = function(geom) { - var array = []; - var components = geom.getPoints(); - for (var i = 0, ii = components.length; i < ii; ++i) { - array.push('(' + ol.format.WKT.encodePointGeometry_(components[i]) + ')'); - } - return array.join(','); -}; - - -/** - * @param {ol.geom.GeometryCollection} geom GeometryCollection geometry. - * @return {string} Coordinates part of GeometryCollection as WKT. - * @private - */ -ol.format.WKT.encodeGeometryCollectionGeometry_ = function(geom) { - var array = []; - var geoms = geom.getGeometries(); - for (var i = 0, ii = geoms.length; i < ii; ++i) { - array.push(ol.format.WKT.encode_(geoms[i])); - } - return array.join(','); -}; - - -/** - * @param {ol.geom.LineString|ol.geom.LinearRing} geom LineString geometry. - * @return {string} Coordinates part of LineString as WKT. - * @private - */ -ol.format.WKT.encodeLineStringGeometry_ = function(geom) { - var coordinates = geom.getCoordinates(); - var array = []; - for (var i = 0, ii = coordinates.length; i < ii; ++i) { - array.push(coordinates[i].join(' ')); - } - return array.join(','); -}; - - -/** - * @param {ol.geom.MultiLineString} geom MultiLineString geometry. - * @return {string} Coordinates part of MultiLineString as WKT. - * @private - */ -ol.format.WKT.encodeMultiLineStringGeometry_ = function(geom) { - var array = []; - var components = geom.getLineStrings(); - for (var i = 0, ii = components.length; i < ii; ++i) { - array.push('(' + ol.format.WKT.encodeLineStringGeometry_( - components[i]) + ')'); - } - return array.join(','); -}; - - -/** - * @param {ol.geom.Polygon} geom Polygon geometry. - * @return {string} Coordinates part of Polygon as WKT. - * @private - */ -ol.format.WKT.encodePolygonGeometry_ = function(geom) { - var array = []; - var rings = geom.getLinearRings(); - for (var i = 0, ii = rings.length; i < ii; ++i) { - array.push('(' + ol.format.WKT.encodeLineStringGeometry_( - rings[i]) + ')'); - } - return array.join(','); -}; - - -/** - * @param {ol.geom.MultiPolygon} geom MultiPolygon geometry. - * @return {string} Coordinates part of MultiPolygon as WKT. - * @private - */ -ol.format.WKT.encodeMultiPolygonGeometry_ = function(geom) { - var array = []; - var components = geom.getPolygons(); - for (var i = 0, ii = components.length; i < ii; ++i) { - array.push('(' + ol.format.WKT.encodePolygonGeometry_( - components[i]) + ')'); - } - return array.join(','); -}; - -/** - * @param {ol.geom.SimpleGeometry} geom SimpleGeometry geometry. - * @return {string} Potential dimensional information for WKT type. - * @private - */ -ol.format.WKT.encodeGeometryLayout_ = function(geom) { - var layout = geom.getLayout(); - var dimInfo = ''; - if (layout === ol.geom.GeometryLayout.XYZ || layout === ol.geom.GeometryLayout.XYZM) { - dimInfo += ol.format.WKT.Z; - } - if (layout === ol.geom.GeometryLayout.XYM || layout === ol.geom.GeometryLayout.XYZM) { - dimInfo += ol.format.WKT.M; - } - return dimInfo; -}; - - -/** - * Encode a geometry as WKT. - * @param {ol.geom.Geometry} geom The geometry to encode. - * @return {string} WKT string for the geometry. - * @private - */ -ol.format.WKT.encode_ = function(geom) { - var type = geom.getType(); - var geometryEncoder = ol.format.WKT.GeometryEncoder_[type]; - var enc = geometryEncoder(geom); - type = type.toUpperCase(); - if (geom instanceof ol.geom.SimpleGeometry) { - var dimInfo = ol.format.WKT.encodeGeometryLayout_(geom); - if (dimInfo.length > 0) { - type += ' ' + dimInfo; - } - } - if (enc.length === 0) { - return type + ' ' + ol.format.WKT.EMPTY; - } - return type + '(' + enc + ')'; -}; - - -/** - * @const - * @type {Object.<string, function(ol.geom.Geometry): string>} - * @private - */ -ol.format.WKT.GeometryEncoder_ = { - 'Point': ol.format.WKT.encodePointGeometry_, - 'LineString': ol.format.WKT.encodeLineStringGeometry_, - 'Polygon': ol.format.WKT.encodePolygonGeometry_, - 'MultiPoint': ol.format.WKT.encodeMultiPointGeometry_, - 'MultiLineString': ol.format.WKT.encodeMultiLineStringGeometry_, - 'MultiPolygon': ol.format.WKT.encodeMultiPolygonGeometry_, - 'GeometryCollection': ol.format.WKT.encodeGeometryCollectionGeometry_ -}; - - -/** - * Parse a WKT string. - * @param {string} wkt WKT string. - * @return {ol.geom.Geometry|undefined} - * The geometry created. - * @private - */ -ol.format.WKT.prototype.parse_ = function(wkt) { - var lexer = new ol.format.WKT.Lexer(wkt); - var parser = new ol.format.WKT.Parser(lexer); - return parser.parse(); -}; - - -/** - * Read a feature from a WKT source. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {ol.Feature} Feature. - * @api - */ -ol.format.WKT.prototype.readFeature; - - -/** - * @inheritDoc - */ -ol.format.WKT.prototype.readFeatureFromText = function(text, opt_options) { - var geom = this.readGeometryFromText(text, opt_options); - if (geom) { - var feature = new ol.Feature(); - feature.setGeometry(geom); - return feature; - } - return null; -}; - - -/** - * Read all features from a WKT source. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {Array.<ol.Feature>} Features. - * @api - */ -ol.format.WKT.prototype.readFeatures; - - -/** - * @inheritDoc - */ -ol.format.WKT.prototype.readFeaturesFromText = function(text, opt_options) { - var geometries = []; - var geometry = this.readGeometryFromText(text, opt_options); - if (this.splitCollection_ && - geometry.getType() == ol.geom.GeometryType.GEOMETRY_COLLECTION) { - geometries = (/** @type {ol.geom.GeometryCollection} */ (geometry)) - .getGeometriesArray(); - } else { - geometries = [geometry]; - } - var feature, features = []; - for (var i = 0, ii = geometries.length; i < ii; ++i) { - feature = new ol.Feature(); - feature.setGeometry(geometries[i]); - features.push(feature); - } - return features; -}; - - -/** - * Read a single geometry from a WKT source. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Read options. - * @return {ol.geom.Geometry} Geometry. - * @api - */ -ol.format.WKT.prototype.readGeometry; - - -/** - * @inheritDoc - */ -ol.format.WKT.prototype.readGeometryFromText = function(text, opt_options) { - var geometry = this.parse_(text); - if (geometry) { - return /** @type {ol.geom.Geometry} */ ( - ol.format.Feature.transformWithOptions(geometry, false, opt_options)); - } else { - return null; - } -}; - - -/** - * Encode a feature as a WKT string. - * - * @function - * @param {ol.Feature} feature Feature. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {string} WKT string. - * @api - */ -ol.format.WKT.prototype.writeFeature; - - -/** - * @inheritDoc - */ -ol.format.WKT.prototype.writeFeatureText = function(feature, opt_options) { - var geometry = feature.getGeometry(); - if (geometry) { - return this.writeGeometryText(geometry, opt_options); - } - return ''; -}; - - -/** - * Encode an array of features as a WKT string. - * - * @function - * @param {Array.<ol.Feature>} features Features. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {string} WKT string. - * @api - */ -ol.format.WKT.prototype.writeFeatures; - - -/** - * @inheritDoc - */ -ol.format.WKT.prototype.writeFeaturesText = function(features, opt_options) { - if (features.length == 1) { - return this.writeFeatureText(features[0], opt_options); - } - var geometries = []; - for (var i = 0, ii = features.length; i < ii; ++i) { - geometries.push(features[i].getGeometry()); - } - var collection = new ol.geom.GeometryCollection(geometries); - return this.writeGeometryText(collection, opt_options); -}; - - -/** - * Write a single geometry as a WKT string. - * - * @function - * @param {ol.geom.Geometry} geometry Geometry. - * @param {olx.format.WriteOptions=} opt_options Write options. - * @return {string} WKT string. - * @api - */ -ol.format.WKT.prototype.writeGeometry; - - -/** - * @inheritDoc - */ -ol.format.WKT.prototype.writeGeometryText = function(geometry, opt_options) { - return ol.format.WKT.encode_(/** @type {ol.geom.Geometry} */ ( - ol.format.Feature.transformWithOptions(geometry, true, opt_options))); -}; - - -/** - * @const - * @enum {number} - * @private - */ -ol.format.WKT.TokenType_ = { - TEXT: 1, - LEFT_PAREN: 2, - RIGHT_PAREN: 3, - NUMBER: 4, - COMMA: 5, - EOF: 6 -}; - - -/** - * Class to tokenize a WKT string. - * @param {string} wkt WKT string. - * @constructor - * @protected - */ -ol.format.WKT.Lexer = function(wkt) { - - /** - * @type {string} - */ - this.wkt = wkt; - - /** - * @type {number} - * @private - */ - this.index_ = -1; -}; - - -/** - * @param {string} c Character. - * @return {boolean} Whether the character is alphabetic. - * @private - */ -ol.format.WKT.Lexer.prototype.isAlpha_ = function(c) { - return c >= 'a' && c <= 'z' || c >= 'A' && c <= 'Z'; -}; - - -/** - * @param {string} c Character. - * @param {boolean=} opt_decimal Whether the string number - * contains a dot, i.e. is a decimal number. - * @return {boolean} Whether the character is numeric. - * @private - */ -ol.format.WKT.Lexer.prototype.isNumeric_ = function(c, opt_decimal) { - var decimal = opt_decimal !== undefined ? opt_decimal : false; - return c >= '0' && c <= '9' || c == '.' && !decimal; -}; - - -/** - * @param {string} c Character. - * @return {boolean} Whether the character is whitespace. - * @private - */ -ol.format.WKT.Lexer.prototype.isWhiteSpace_ = function(c) { - return c == ' ' || c == '\t' || c == '\r' || c == '\n'; -}; - - -/** - * @return {string} Next string character. - * @private - */ -ol.format.WKT.Lexer.prototype.nextChar_ = function() { - return this.wkt.charAt(++this.index_); -}; - - -/** - * Fetch and return the next token. - * @return {!ol.WKTToken} Next string token. - */ -ol.format.WKT.Lexer.prototype.nextToken = function() { - var c = this.nextChar_(); - var token = {position: this.index_, value: c}; - - if (c == '(') { - token.type = ol.format.WKT.TokenType_.LEFT_PAREN; - } else if (c == ',') { - token.type = ol.format.WKT.TokenType_.COMMA; - } else if (c == ')') { - token.type = ol.format.WKT.TokenType_.RIGHT_PAREN; - } else if (this.isNumeric_(c) || c == '-') { - token.type = ol.format.WKT.TokenType_.NUMBER; - token.value = this.readNumber_(); - } else if (this.isAlpha_(c)) { - token.type = ol.format.WKT.TokenType_.TEXT; - token.value = this.readText_(); - } else if (this.isWhiteSpace_(c)) { - return this.nextToken(); - } else if (c === '') { - token.type = ol.format.WKT.TokenType_.EOF; - } else { - throw new Error('Unexpected character: ' + c); - } - - return token; -}; - - -/** - * @return {number} Numeric token value. - * @private - */ -ol.format.WKT.Lexer.prototype.readNumber_ = function() { - var c, index = this.index_; - var decimal = false; - var scientificNotation = false; - do { - if (c == '.') { - decimal = true; - } else if (c == 'e' || c == 'E') { - scientificNotation = true; - } - c = this.nextChar_(); - } while ( - this.isNumeric_(c, decimal) || - // if we haven't detected a scientific number before, 'e' or 'E' - // hint that we should continue to read - !scientificNotation && (c == 'e' || c == 'E') || - // once we know that we have a scientific number, both '-' and '+' - // are allowed - scientificNotation && (c == '-' || c == '+') - ); - return parseFloat(this.wkt.substring(index, this.index_--)); -}; - - -/** - * @return {string} String token value. - * @private - */ -ol.format.WKT.Lexer.prototype.readText_ = function() { - var c, index = this.index_; - do { - c = this.nextChar_(); - } while (this.isAlpha_(c)); - return this.wkt.substring(index, this.index_--).toUpperCase(); -}; - - -/** - * Class to parse the tokens from the WKT string. - * @param {ol.format.WKT.Lexer} lexer The lexer. - * @constructor - * @protected - */ -ol.format.WKT.Parser = function(lexer) { - - /** - * @type {ol.format.WKT.Lexer} - * @private - */ - this.lexer_ = lexer; - - /** - * @type {ol.WKTToken} - * @private - */ - this.token_; - - /** - * @type {ol.geom.GeometryLayout} - * @private - */ - this.layout_ = ol.geom.GeometryLayout.XY; -}; - - -/** - * Fetch the next token form the lexer and replace the active token. - * @private - */ -ol.format.WKT.Parser.prototype.consume_ = function() { - this.token_ = this.lexer_.nextToken(); -}; - -/** - * Tests if the given type matches the type of the current token. - * @param {ol.format.WKT.TokenType_} type Token type. - * @return {boolean} Whether the token matches the given type. - */ -ol.format.WKT.Parser.prototype.isTokenType = function(type) { - var isMatch = this.token_.type == type; - return isMatch; -}; - - -/** - * If the given type matches the current token, consume it. - * @param {ol.format.WKT.TokenType_} type Token type. - * @return {boolean} Whether the token matches the given type. - */ -ol.format.WKT.Parser.prototype.match = function(type) { - var isMatch = this.isTokenType(type); - if (isMatch) { - this.consume_(); - } - return isMatch; -}; - - -/** - * Try to parse the tokens provided by the lexer. - * @return {ol.geom.Geometry} The geometry. - */ -ol.format.WKT.Parser.prototype.parse = function() { - this.consume_(); - var geometry = this.parseGeometry_(); - return geometry; -}; - - -/** - * Try to parse the dimensional info. - * @return {ol.geom.GeometryLayout} The layout. - * @private - */ -ol.format.WKT.Parser.prototype.parseGeometryLayout_ = function() { - var layout = ol.geom.GeometryLayout.XY; - var dimToken = this.token_; - if (this.isTokenType(ol.format.WKT.TokenType_.TEXT)) { - var dimInfo = dimToken.value; - if (dimInfo === ol.format.WKT.Z) { - layout = ol.geom.GeometryLayout.XYZ; - } else if (dimInfo === ol.format.WKT.M) { - layout = ol.geom.GeometryLayout.XYM; - } else if (dimInfo === ol.format.WKT.ZM) { - layout = ol.geom.GeometryLayout.XYZM; - } - if (layout !== ol.geom.GeometryLayout.XY) { - this.consume_(); - } - } - return layout; -}; - - -/** - * @return {!ol.geom.Geometry} The geometry. - * @private - */ -ol.format.WKT.Parser.prototype.parseGeometry_ = function() { - var token = this.token_; - if (this.match(ol.format.WKT.TokenType_.TEXT)) { - var geomType = token.value; - this.layout_ = this.parseGeometryLayout_(); - if (geomType == ol.geom.GeometryType.GEOMETRY_COLLECTION.toUpperCase()) { - var geometries = this.parseGeometryCollectionText_(); - return new ol.geom.GeometryCollection(geometries); - } else { - var parser = ol.format.WKT.Parser.GeometryParser_[geomType]; - var ctor = ol.format.WKT.Parser.GeometryConstructor_[geomType]; - if (!parser || !ctor) { - throw new Error('Invalid geometry type: ' + geomType); - } - var coordinates = parser.call(this); - return new ctor(coordinates, this.layout_); - } - } - throw new Error(this.formatErrorMessage_()); -}; - - -/** - * @return {!Array.<ol.geom.Geometry>} A collection of geometries. - * @private - */ -ol.format.WKT.Parser.prototype.parseGeometryCollectionText_ = function() { - if (this.match(ol.format.WKT.TokenType_.LEFT_PAREN)) { - var geometries = []; - do { - geometries.push(this.parseGeometry_()); - } while (this.match(ol.format.WKT.TokenType_.COMMA)); - if (this.match(ol.format.WKT.TokenType_.RIGHT_PAREN)) { - return geometries; - } - } else if (this.isEmptyGeometry_()) { - return []; - } - throw new Error(this.formatErrorMessage_()); -}; - - -/** - * @return {Array.<number>} All values in a point. - * @private - */ -ol.format.WKT.Parser.prototype.parsePointText_ = function() { - if (this.match(ol.format.WKT.TokenType_.LEFT_PAREN)) { - var coordinates = this.parsePoint_(); - if (this.match(ol.format.WKT.TokenType_.RIGHT_PAREN)) { - return coordinates; - } - } else if (this.isEmptyGeometry_()) { - return null; - } - throw new Error(this.formatErrorMessage_()); -}; - - -/** - * @return {!Array.<!Array.<number>>} All points in a linestring. - * @private - */ -ol.format.WKT.Parser.prototype.parseLineStringText_ = function() { - if (this.match(ol.format.WKT.TokenType_.LEFT_PAREN)) { - var coordinates = this.parsePointList_(); - if (this.match(ol.format.WKT.TokenType_.RIGHT_PAREN)) { - return coordinates; - } - } else if (this.isEmptyGeometry_()) { - return []; - } - throw new Error(this.formatErrorMessage_()); -}; - - -/** - * @return {!Array.<!Array.<number>>} All points in a polygon. - * @private - */ -ol.format.WKT.Parser.prototype.parsePolygonText_ = function() { - if (this.match(ol.format.WKT.TokenType_.LEFT_PAREN)) { - var coordinates = this.parseLineStringTextList_(); - if (this.match(ol.format.WKT.TokenType_.RIGHT_PAREN)) { - return coordinates; - } - } else if (this.isEmptyGeometry_()) { - return []; - } - throw new Error(this.formatErrorMessage_()); -}; - - -/** - * @return {!Array.<!Array.<number>>} All points in a multipoint. - * @private - */ -ol.format.WKT.Parser.prototype.parseMultiPointText_ = function() { - if (this.match(ol.format.WKT.TokenType_.LEFT_PAREN)) { - var coordinates; - if (this.token_.type == ol.format.WKT.TokenType_.LEFT_PAREN) { - coordinates = this.parsePointTextList_(); - } else { - coordinates = this.parsePointList_(); - } - if (this.match(ol.format.WKT.TokenType_.RIGHT_PAREN)) { - return coordinates; - } - } else if (this.isEmptyGeometry_()) { - return []; - } - throw new Error(this.formatErrorMessage_()); -}; - - -/** - * @return {!Array.<!Array.<number>>} All linestring points - * in a multilinestring. - * @private - */ -ol.format.WKT.Parser.prototype.parseMultiLineStringText_ = function() { - if (this.match(ol.format.WKT.TokenType_.LEFT_PAREN)) { - var coordinates = this.parseLineStringTextList_(); - if (this.match(ol.format.WKT.TokenType_.RIGHT_PAREN)) { - return coordinates; - } - } else if (this.isEmptyGeometry_()) { - return []; - } - throw new Error(this.formatErrorMessage_()); -}; - - -/** - * @return {!Array.<!Array.<number>>} All polygon points in a multipolygon. - * @private - */ -ol.format.WKT.Parser.prototype.parseMultiPolygonText_ = function() { - if (this.match(ol.format.WKT.TokenType_.LEFT_PAREN)) { - var coordinates = this.parsePolygonTextList_(); - if (this.match(ol.format.WKT.TokenType_.RIGHT_PAREN)) { - return coordinates; - } - } else if (this.isEmptyGeometry_()) { - return []; - } - throw new Error(this.formatErrorMessage_()); -}; - - -/** - * @return {!Array.<number>} A point. - * @private - */ -ol.format.WKT.Parser.prototype.parsePoint_ = function() { - var coordinates = []; - var dimensions = this.layout_.length; - for (var i = 0; i < dimensions; ++i) { - var token = this.token_; - if (this.match(ol.format.WKT.TokenType_.NUMBER)) { - coordinates.push(token.value); - } else { - break; - } - } - if (coordinates.length == dimensions) { - return coordinates; - } - throw new Error(this.formatErrorMessage_()); -}; - - -/** - * @return {!Array.<!Array.<number>>} An array of points. - * @private - */ -ol.format.WKT.Parser.prototype.parsePointList_ = function() { - var coordinates = [this.parsePoint_()]; - while (this.match(ol.format.WKT.TokenType_.COMMA)) { - coordinates.push(this.parsePoint_()); - } - return coordinates; -}; - - -/** - * @return {!Array.<!Array.<number>>} An array of points. - * @private - */ -ol.format.WKT.Parser.prototype.parsePointTextList_ = function() { - var coordinates = [this.parsePointText_()]; - while (this.match(ol.format.WKT.TokenType_.COMMA)) { - coordinates.push(this.parsePointText_()); - } - return coordinates; -}; - - -/** - * @return {!Array.<!Array.<number>>} An array of points. - * @private - */ -ol.format.WKT.Parser.prototype.parseLineStringTextList_ = function() { - var coordinates = [this.parseLineStringText_()]; - while (this.match(ol.format.WKT.TokenType_.COMMA)) { - coordinates.push(this.parseLineStringText_()); - } - return coordinates; -}; - - -/** - * @return {!Array.<!Array.<number>>} An array of points. - * @private - */ -ol.format.WKT.Parser.prototype.parsePolygonTextList_ = function() { - var coordinates = [this.parsePolygonText_()]; - while (this.match(ol.format.WKT.TokenType_.COMMA)) { - coordinates.push(this.parsePolygonText_()); - } - return coordinates; -}; - - -/** - * @return {boolean} Whether the token implies an empty geometry. - * @private - */ -ol.format.WKT.Parser.prototype.isEmptyGeometry_ = function() { - var isEmpty = this.isTokenType(ol.format.WKT.TokenType_.TEXT) && - this.token_.value == ol.format.WKT.EMPTY; - if (isEmpty) { - this.consume_(); - } - return isEmpty; -}; - - -/** - * Create an error message for an unexpected token error. - * @return {string} Error message. - * @private - */ -ol.format.WKT.Parser.prototype.formatErrorMessage_ = function() { - return 'Unexpected `' + this.token_.value + '` at position ' + - this.token_.position + ' in `' + this.lexer_.wkt + '`'; -}; - - -/** - * @enum {function (new:ol.geom.Geometry, Array, ol.geom.GeometryLayout)} - * @private - */ -ol.format.WKT.Parser.GeometryConstructor_ = { - 'POINT': ol.geom.Point, - 'LINESTRING': ol.geom.LineString, - 'POLYGON': ol.geom.Polygon, - 'MULTIPOINT': ol.geom.MultiPoint, - 'MULTILINESTRING': ol.geom.MultiLineString, - 'MULTIPOLYGON': ol.geom.MultiPolygon -}; - - -/** - * @enum {(function(): Array)} - * @private - */ -ol.format.WKT.Parser.GeometryParser_ = { - 'POINT': ol.format.WKT.Parser.prototype.parsePointText_, - 'LINESTRING': ol.format.WKT.Parser.prototype.parseLineStringText_, - 'POLYGON': ol.format.WKT.Parser.prototype.parsePolygonText_, - 'MULTIPOINT': ol.format.WKT.Parser.prototype.parseMultiPointText_, - 'MULTILINESTRING': ol.format.WKT.Parser.prototype.parseMultiLineStringText_, - 'MULTIPOLYGON': ol.format.WKT.Parser.prototype.parseMultiPolygonText_ -}; - -goog.provide('ol.format.WMSCapabilities'); - -goog.require('ol'); -goog.require('ol.format.XLink'); -goog.require('ol.format.XML'); -goog.require('ol.format.XSD'); -goog.require('ol.xml'); - - -/** - * @classdesc - * Format for reading WMS capabilities data - * - * @constructor - * @extends {ol.format.XML} - * @api - */ -ol.format.WMSCapabilities = function() { - - ol.format.XML.call(this); - - /** - * @type {string|undefined} - */ - this.version = undefined; -}; -ol.inherits(ol.format.WMSCapabilities, ol.format.XML); - - -/** - * Read a WMS capabilities document. - * - * @function - * @param {Document|Node|string} source The XML source. - * @return {Object} An object representing the WMS capabilities. - * @api - */ -ol.format.WMSCapabilities.prototype.read; - - -/** - * @inheritDoc - */ -ol.format.WMSCapabilities.prototype.readFromDocument = function(doc) { - for (var n = doc.firstChild; n; n = n.nextSibling) { - if (n.nodeType == Node.ELEMENT_NODE) { - return this.readFromNode(n); - } - } - return null; -}; - - -/** - * @inheritDoc - */ -ol.format.WMSCapabilities.prototype.readFromNode = function(node) { - this.version = node.getAttribute('version').trim(); - var wmsCapabilityObject = ol.xml.pushParseAndPop({ - 'version': this.version - }, ol.format.WMSCapabilities.PARSERS_, node, []); - return wmsCapabilityObject ? wmsCapabilityObject : null; -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Attribution object. - */ -ol.format.WMSCapabilities.readAttribution_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - {}, ol.format.WMSCapabilities.ATTRIBUTION_PARSERS_, node, objectStack); -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object} Bounding box object. - */ -ol.format.WMSCapabilities.readBoundingBox_ = function(node, objectStack) { - var extent = [ - ol.format.XSD.readDecimalString(node.getAttribute('minx')), - ol.format.XSD.readDecimalString(node.getAttribute('miny')), - ol.format.XSD.readDecimalString(node.getAttribute('maxx')), - ol.format.XSD.readDecimalString(node.getAttribute('maxy')) - ]; - - var resolutions = [ - ol.format.XSD.readDecimalString(node.getAttribute('resx')), - ol.format.XSD.readDecimalString(node.getAttribute('resy')) - ]; - - return { - 'crs': node.getAttribute('CRS'), - 'extent': extent, - 'res': resolutions - }; -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {ol.Extent|undefined} Bounding box object. - */ -ol.format.WMSCapabilities.readEXGeographicBoundingBox_ = function(node, objectStack) { - var geographicBoundingBox = ol.xml.pushParseAndPop( - {}, - ol.format.WMSCapabilities.EX_GEOGRAPHIC_BOUNDING_BOX_PARSERS_, - node, objectStack); - if (!geographicBoundingBox) { - return undefined; - } - var westBoundLongitude = /** @type {number|undefined} */ - (geographicBoundingBox['westBoundLongitude']); - var southBoundLatitude = /** @type {number|undefined} */ - (geographicBoundingBox['southBoundLatitude']); - var eastBoundLongitude = /** @type {number|undefined} */ - (geographicBoundingBox['eastBoundLongitude']); - var northBoundLatitude = /** @type {number|undefined} */ - (geographicBoundingBox['northBoundLatitude']); - if (westBoundLongitude === undefined || southBoundLatitude === undefined || - eastBoundLongitude === undefined || northBoundLatitude === undefined) { - return undefined; - } - return [ - westBoundLongitude, southBoundLatitude, - eastBoundLongitude, northBoundLatitude - ]; -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} Capability object. - */ -ol.format.WMSCapabilities.readCapability_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - {}, ol.format.WMSCapabilities.CAPABILITY_PARSERS_, node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} Service object. - */ -ol.format.WMSCapabilities.readService_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - {}, ol.format.WMSCapabilities.SERVICE_PARSERS_, node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} Contact information object. - */ -ol.format.WMSCapabilities.readContactInformation_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - {}, ol.format.WMSCapabilities.CONTACT_INFORMATION_PARSERS_, - node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} Contact person object. - */ -ol.format.WMSCapabilities.readContactPersonPrimary_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - {}, ol.format.WMSCapabilities.CONTACT_PERSON_PARSERS_, - node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} Contact address object. - */ -ol.format.WMSCapabilities.readContactAddress_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - {}, ol.format.WMSCapabilities.CONTACT_ADDRESS_PARSERS_, - node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Array.<string>|undefined} Format array. - */ -ol.format.WMSCapabilities.readException_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - [], ol.format.WMSCapabilities.EXCEPTION_PARSERS_, node, objectStack); -}; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @private - * @return {Object|undefined} Layer object. - */ -ol.format.WMSCapabilities.readCapabilityLayer_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - {}, ol.format.WMSCapabilities.LAYER_PARSERS_, node, objectStack); -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Layer object. - */ -ol.format.WMSCapabilities.readLayer_ = function(node, objectStack) { - var parentLayerObject = /** @type {Object.<string,*>} */ - (objectStack[objectStack.length - 1]); - - var layerObject = ol.xml.pushParseAndPop( - {}, ol.format.WMSCapabilities.LAYER_PARSERS_, node, objectStack); - - if (!layerObject) { - return undefined; - } - var queryable = - ol.format.XSD.readBooleanString(node.getAttribute('queryable')); - if (queryable === undefined) { - queryable = parentLayerObject['queryable']; - } - layerObject['queryable'] = queryable !== undefined ? queryable : false; - - var cascaded = ol.format.XSD.readNonNegativeIntegerString( - node.getAttribute('cascaded')); - if (cascaded === undefined) { - cascaded = parentLayerObject['cascaded']; - } - layerObject['cascaded'] = cascaded; - - var opaque = ol.format.XSD.readBooleanString(node.getAttribute('opaque')); - if (opaque === undefined) { - opaque = parentLayerObject['opaque']; - } - layerObject['opaque'] = opaque !== undefined ? opaque : false; - - var noSubsets = - ol.format.XSD.readBooleanString(node.getAttribute('noSubsets')); - if (noSubsets === undefined) { - noSubsets = parentLayerObject['noSubsets']; - } - layerObject['noSubsets'] = noSubsets !== undefined ? noSubsets : false; - - var fixedWidth = - ol.format.XSD.readDecimalString(node.getAttribute('fixedWidth')); - if (!fixedWidth) { - fixedWidth = parentLayerObject['fixedWidth']; - } - layerObject['fixedWidth'] = fixedWidth; - - var fixedHeight = - ol.format.XSD.readDecimalString(node.getAttribute('fixedHeight')); - if (!fixedHeight) { - fixedHeight = parentLayerObject['fixedHeight']; - } - layerObject['fixedHeight'] = fixedHeight; - - // See 7.2.4.8 - var addKeys = ['Style', 'CRS', 'AuthorityURL']; - addKeys.forEach(function(key) { - if (key in parentLayerObject) { - var childValue = layerObject[key] || []; - layerObject[key] = childValue.concat(parentLayerObject[key]); - } - }); - - var replaceKeys = ['EX_GeographicBoundingBox', 'BoundingBox', 'Dimension', - 'Attribution', 'MinScaleDenominator', 'MaxScaleDenominator']; - replaceKeys.forEach(function(key) { - if (!(key in layerObject)) { - var parentValue = parentLayerObject[key]; - layerObject[key] = parentValue; - } - }); - - return layerObject; -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object} Dimension object. - */ -ol.format.WMSCapabilities.readDimension_ = function(node, objectStack) { - var dimensionObject = { - 'name': node.getAttribute('name'), - 'units': node.getAttribute('units'), - 'unitSymbol': node.getAttribute('unitSymbol'), - 'default': node.getAttribute('default'), - 'multipleValues': ol.format.XSD.readBooleanString( - node.getAttribute('multipleValues')), - 'nearestValue': ol.format.XSD.readBooleanString( - node.getAttribute('nearestValue')), - 'current': ol.format.XSD.readBooleanString(node.getAttribute('current')), - 'values': ol.format.XSD.readString(node) - }; - return dimensionObject; -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Online resource object. - */ -ol.format.WMSCapabilities.readFormatOnlineresource_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - {}, ol.format.WMSCapabilities.FORMAT_ONLINERESOURCE_PARSERS_, - node, objectStack); -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Request object. - */ -ol.format.WMSCapabilities.readRequest_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - {}, ol.format.WMSCapabilities.REQUEST_PARSERS_, node, objectStack); -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} DCP type object. - */ -ol.format.WMSCapabilities.readDCPType_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - {}, ol.format.WMSCapabilities.DCPTYPE_PARSERS_, node, objectStack); -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} HTTP object. - */ -ol.format.WMSCapabilities.readHTTP_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - {}, ol.format.WMSCapabilities.HTTP_PARSERS_, node, objectStack); -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Operation type object. - */ -ol.format.WMSCapabilities.readOperationType_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - {}, ol.format.WMSCapabilities.OPERATIONTYPE_PARSERS_, node, objectStack); -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Online resource object. - */ -ol.format.WMSCapabilities.readSizedFormatOnlineresource_ = function(node, objectStack) { - var formatOnlineresource = - ol.format.WMSCapabilities.readFormatOnlineresource_(node, objectStack); - if (formatOnlineresource) { - var size = [ - ol.format.XSD.readNonNegativeIntegerString(node.getAttribute('width')), - ol.format.XSD.readNonNegativeIntegerString(node.getAttribute('height')) - ]; - formatOnlineresource['size'] = size; - return formatOnlineresource; - } - return undefined; -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Authority URL object. - */ -ol.format.WMSCapabilities.readAuthorityURL_ = function(node, objectStack) { - var authorityObject = - ol.format.WMSCapabilities.readFormatOnlineresource_(node, objectStack); - if (authorityObject) { - authorityObject['name'] = node.getAttribute('name'); - return authorityObject; - } - return undefined; -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Metadata URL object. - */ -ol.format.WMSCapabilities.readMetadataURL_ = function(node, objectStack) { - var metadataObject = - ol.format.WMSCapabilities.readFormatOnlineresource_(node, objectStack); - if (metadataObject) { - metadataObject['type'] = node.getAttribute('type'); - return metadataObject; - } - return undefined; -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Style object. - */ -ol.format.WMSCapabilities.readStyle_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - {}, ol.format.WMSCapabilities.STYLE_PARSERS_, node, objectStack); -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Array.<string>|undefined} Keyword list. - */ -ol.format.WMSCapabilities.readKeywordList_ = function(node, objectStack) { - return ol.xml.pushParseAndPop( - [], ol.format.WMSCapabilities.KEYWORDLIST_PARSERS_, node, objectStack); -}; - - -/** - * @const - * @private - * @type {Array.<string>} - */ -ol.format.WMSCapabilities.NAMESPACE_URIS_ = [ - null, - 'http://www.opengis.net/wms' -]; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMSCapabilities.PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMSCapabilities.NAMESPACE_URIS_, { - 'Service': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readService_), - 'Capability': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readCapability_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMSCapabilities.CAPABILITY_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMSCapabilities.NAMESPACE_URIS_, { - 'Request': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readRequest_), - 'Exception': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readException_), - 'Layer': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readCapabilityLayer_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMSCapabilities.SERVICE_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMSCapabilities.NAMESPACE_URIS_, { - 'Name': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'Title': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'Abstract': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'KeywordList': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readKeywordList_), - 'OnlineResource': ol.xml.makeObjectPropertySetter( - ol.format.XLink.readHref), - 'ContactInformation': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readContactInformation_), - 'Fees': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'AccessConstraints': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'LayerLimit': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readNonNegativeInteger), - 'MaxWidth': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readNonNegativeInteger), - 'MaxHeight': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readNonNegativeInteger) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMSCapabilities.CONTACT_INFORMATION_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMSCapabilities.NAMESPACE_URIS_, { - 'ContactPersonPrimary': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readContactPersonPrimary_), - 'ContactPosition': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'ContactAddress': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readContactAddress_), - 'ContactVoiceTelephone': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'ContactFacsimileTelephone': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'ContactElectronicMailAddress': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMSCapabilities.CONTACT_PERSON_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMSCapabilities.NAMESPACE_URIS_, { - 'ContactPerson': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'ContactOrganization': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMSCapabilities.CONTACT_ADDRESS_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMSCapabilities.NAMESPACE_URIS_, { - 'AddressType': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'Address': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'City': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'StateOrProvince': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'PostCode': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'Country': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMSCapabilities.EXCEPTION_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMSCapabilities.NAMESPACE_URIS_, { - 'Format': ol.xml.makeArrayPusher(ol.format.XSD.readString) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMSCapabilities.LAYER_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMSCapabilities.NAMESPACE_URIS_, { - 'Name': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'Title': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'Abstract': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'KeywordList': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readKeywordList_), - 'CRS': ol.xml.makeObjectPropertyPusher(ol.format.XSD.readString), - 'EX_GeographicBoundingBox': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readEXGeographicBoundingBox_), - 'BoundingBox': ol.xml.makeObjectPropertyPusher( - ol.format.WMSCapabilities.readBoundingBox_), - 'Dimension': ol.xml.makeObjectPropertyPusher( - ol.format.WMSCapabilities.readDimension_), - 'Attribution': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readAttribution_), - 'AuthorityURL': ol.xml.makeObjectPropertyPusher( - ol.format.WMSCapabilities.readAuthorityURL_), - 'Identifier': ol.xml.makeObjectPropertyPusher(ol.format.XSD.readString), - 'MetadataURL': ol.xml.makeObjectPropertyPusher( - ol.format.WMSCapabilities.readMetadataURL_), - 'DataURL': ol.xml.makeObjectPropertyPusher( - ol.format.WMSCapabilities.readFormatOnlineresource_), - 'FeatureListURL': ol.xml.makeObjectPropertyPusher( - ol.format.WMSCapabilities.readFormatOnlineresource_), - 'Style': ol.xml.makeObjectPropertyPusher( - ol.format.WMSCapabilities.readStyle_), - 'MinScaleDenominator': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readDecimal), - 'MaxScaleDenominator': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readDecimal), - 'Layer': ol.xml.makeObjectPropertyPusher( - ol.format.WMSCapabilities.readLayer_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMSCapabilities.ATTRIBUTION_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMSCapabilities.NAMESPACE_URIS_, { - 'Title': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'OnlineResource': ol.xml.makeObjectPropertySetter( - ol.format.XLink.readHref), - 'LogoURL': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readSizedFormatOnlineresource_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMSCapabilities.EX_GEOGRAPHIC_BOUNDING_BOX_PARSERS_ = - ol.xml.makeStructureNS(ol.format.WMSCapabilities.NAMESPACE_URIS_, { - 'westBoundLongitude': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readDecimal), - 'eastBoundLongitude': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readDecimal), - 'southBoundLatitude': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readDecimal), - 'northBoundLatitude': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readDecimal) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMSCapabilities.REQUEST_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMSCapabilities.NAMESPACE_URIS_, { - 'GetCapabilities': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readOperationType_), - 'GetMap': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readOperationType_), - 'GetFeatureInfo': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readOperationType_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMSCapabilities.OPERATIONTYPE_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMSCapabilities.NAMESPACE_URIS_, { - 'Format': ol.xml.makeObjectPropertyPusher(ol.format.XSD.readString), - 'DCPType': ol.xml.makeObjectPropertyPusher( - ol.format.WMSCapabilities.readDCPType_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMSCapabilities.DCPTYPE_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMSCapabilities.NAMESPACE_URIS_, { - 'HTTP': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readHTTP_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMSCapabilities.HTTP_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMSCapabilities.NAMESPACE_URIS_, { - 'Get': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readFormatOnlineresource_), - 'Post': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readFormatOnlineresource_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMSCapabilities.STYLE_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMSCapabilities.NAMESPACE_URIS_, { - 'Name': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'Title': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'Abstract': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'LegendURL': ol.xml.makeObjectPropertyPusher( - ol.format.WMSCapabilities.readSizedFormatOnlineresource_), - 'StyleSheetURL': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readFormatOnlineresource_), - 'StyleURL': ol.xml.makeObjectPropertySetter( - ol.format.WMSCapabilities.readFormatOnlineresource_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMSCapabilities.FORMAT_ONLINERESOURCE_PARSERS_ = - ol.xml.makeStructureNS(ol.format.WMSCapabilities.NAMESPACE_URIS_, { - 'Format': ol.xml.makeObjectPropertySetter(ol.format.XSD.readString), - 'OnlineResource': ol.xml.makeObjectPropertySetter( - ol.format.XLink.readHref) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMSCapabilities.KEYWORDLIST_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMSCapabilities.NAMESPACE_URIS_, { - 'Keyword': ol.xml.makeArrayPusher(ol.format.XSD.readString) - }); - -goog.provide('ol.format.WMSGetFeatureInfo'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.format.GML2'); -goog.require('ol.format.XMLFeature'); -goog.require('ol.obj'); -goog.require('ol.xml'); - - -/** - * @classdesc - * Format for reading WMSGetFeatureInfo format. It uses - * {@link ol.format.GML2} to read features. - * - * @constructor - * @extends {ol.format.XMLFeature} - * @param {olx.format.WMSGetFeatureInfoOptions=} opt_options Options. - * @api - */ -ol.format.WMSGetFeatureInfo = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - /** - * @private - * @type {string} - */ - this.featureNS_ = 'http://mapserver.gis.umn.edu/mapserver'; - - - /** - * @private - * @type {ol.format.GML2} - */ - this.gmlFormat_ = new ol.format.GML2(); - - - /** - * @private - * @type {Array.<string>} - */ - this.layers_ = options.layers ? options.layers : null; - - ol.format.XMLFeature.call(this); -}; -ol.inherits(ol.format.WMSGetFeatureInfo, ol.format.XMLFeature); - - -/** - * @const - * @type {string} - * @private - */ -ol.format.WMSGetFeatureInfo.featureIdentifier_ = '_feature'; - - -/** - * @const - * @type {string} - * @private - */ -ol.format.WMSGetFeatureInfo.layerIdentifier_ = '_layer'; - - -/** - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Array.<ol.Feature>} Features. - * @private - */ -ol.format.WMSGetFeatureInfo.prototype.readFeatures_ = function(node, objectStack) { - node.setAttribute('namespaceURI', this.featureNS_); - var localName = node.localName; - /** @type {Array.<ol.Feature>} */ - var features = []; - if (node.childNodes.length === 0) { - return features; - } - if (localName == 'msGMLOutput') { - for (var i = 0, ii = node.childNodes.length; i < ii; i++) { - var layer = node.childNodes[i]; - if (layer.nodeType !== Node.ELEMENT_NODE) { - continue; - } - var context = objectStack[0]; - - var toRemove = ol.format.WMSGetFeatureInfo.layerIdentifier_; - var layerName = layer.localName.replace(toRemove, ''); - - if (this.layers_ && !ol.array.includes(this.layers_, layerName)) { - continue; - } - - var featureType = layerName + - ol.format.WMSGetFeatureInfo.featureIdentifier_; - - context['featureType'] = featureType; - context['featureNS'] = this.featureNS_; - - var parsers = {}; - parsers[featureType] = ol.xml.makeArrayPusher( - this.gmlFormat_.readFeatureElement, this.gmlFormat_); - var parsersNS = ol.xml.makeStructureNS( - [context['featureNS'], null], parsers); - layer.setAttribute('namespaceURI', this.featureNS_); - var layerFeatures = ol.xml.pushParseAndPop( - [], parsersNS, layer, objectStack, this.gmlFormat_); - if (layerFeatures) { - ol.array.extend(features, layerFeatures); - } - } - } - if (localName == 'FeatureCollection') { - var gmlFeatures = ol.xml.pushParseAndPop([], - this.gmlFormat_.FEATURE_COLLECTION_PARSERS, node, - [{}], this.gmlFormat_); - if (gmlFeatures) { - features = gmlFeatures; - } - } - return features; -}; - - -/** - * Read all features from a WMSGetFeatureInfo response. - * - * @function - * @param {Document|Node|Object|string} source Source. - * @param {olx.format.ReadOptions=} opt_options Options. - * @return {Array.<ol.Feature>} Features. - * @api - */ -ol.format.WMSGetFeatureInfo.prototype.readFeatures; - - -/** - * @inheritDoc - */ -ol.format.WMSGetFeatureInfo.prototype.readFeaturesFromNode = function(node, opt_options) { - var options = {}; - if (opt_options) { - ol.obj.assign(options, this.getReadOptions(node, opt_options)); - } - return this.readFeatures_(node, [options]); -}; - - -/** - * Not implemented. - * @inheritDoc - */ -ol.format.WMSGetFeatureInfo.prototype.writeFeatureNode = function(feature, opt_options) {}; - - -/** - * Not implemented. - * @inheritDoc - */ -ol.format.WMSGetFeatureInfo.prototype.writeFeaturesNode = function(features, opt_options) {}; - - -/** - * Not implemented. - * @inheritDoc - */ -ol.format.WMSGetFeatureInfo.prototype.writeGeometryNode = function(geometry, opt_options) {}; - -goog.provide('ol.format.WMTSCapabilities'); - -goog.require('ol'); -goog.require('ol.extent'); -goog.require('ol.format.OWS'); -goog.require('ol.format.XLink'); -goog.require('ol.format.XML'); -goog.require('ol.format.XSD'); -goog.require('ol.xml'); - - -/** - * @classdesc - * Format for reading WMTS capabilities data. - * - * @constructor - * @extends {ol.format.XML} - * @api - */ -ol.format.WMTSCapabilities = function() { - ol.format.XML.call(this); - - /** - * @type {ol.format.OWS} - * @private - */ - this.owsParser_ = new ol.format.OWS(); -}; -ol.inherits(ol.format.WMTSCapabilities, ol.format.XML); - - -/** - * Read a WMTS capabilities document. - * - * @function - * @param {Document|Node|string} source The XML source. - * @return {Object} An object representing the WMTS capabilities. - * @api - */ -ol.format.WMTSCapabilities.prototype.read; - - -/** - * @inheritDoc - */ -ol.format.WMTSCapabilities.prototype.readFromDocument = function(doc) { - for (var n = doc.firstChild; n; n = n.nextSibling) { - if (n.nodeType == Node.ELEMENT_NODE) { - return this.readFromNode(n); - } - } - return null; -}; - - -/** - * @inheritDoc - */ -ol.format.WMTSCapabilities.prototype.readFromNode = function(node) { - var version = node.getAttribute('version').trim(); - var WMTSCapabilityObject = this.owsParser_.readFromNode(node); - if (!WMTSCapabilityObject) { - return null; - } - WMTSCapabilityObject['version'] = version; - WMTSCapabilityObject = ol.xml.pushParseAndPop(WMTSCapabilityObject, - ol.format.WMTSCapabilities.PARSERS_, node, []); - return WMTSCapabilityObject ? WMTSCapabilityObject : null; -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Attribution object. - */ -ol.format.WMTSCapabilities.readContents_ = function(node, objectStack) { - return ol.xml.pushParseAndPop({}, - ol.format.WMTSCapabilities.CONTENTS_PARSERS_, node, objectStack); -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Layers object. - */ -ol.format.WMTSCapabilities.readLayer_ = function(node, objectStack) { - return ol.xml.pushParseAndPop({}, - ol.format.WMTSCapabilities.LAYER_PARSERS_, node, objectStack); -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Tile Matrix Set object. - */ -ol.format.WMTSCapabilities.readTileMatrixSet_ = function(node, objectStack) { - return ol.xml.pushParseAndPop({}, - ol.format.WMTSCapabilities.TMS_PARSERS_, node, objectStack); -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Style object. - */ -ol.format.WMTSCapabilities.readStyle_ = function(node, objectStack) { - var style = ol.xml.pushParseAndPop({}, - ol.format.WMTSCapabilities.STYLE_PARSERS_, node, objectStack); - if (!style) { - return undefined; - } - var isDefault = node.getAttribute('isDefault') === 'true'; - style['isDefault'] = isDefault; - return style; - -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Tile Matrix Set Link object. - */ -ol.format.WMTSCapabilities.readTileMatrixSetLink_ = function(node, - objectStack) { - return ol.xml.pushParseAndPop({}, - ol.format.WMTSCapabilities.TMS_LINKS_PARSERS_, node, objectStack); -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Dimension object. - */ -ol.format.WMTSCapabilities.readDimensions_ = function(node, objectStack) { - return ol.xml.pushParseAndPop({}, - ol.format.WMTSCapabilities.DIMENSION_PARSERS_, node, objectStack); -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Resource URL object. - */ -ol.format.WMTSCapabilities.readResourceUrl_ = function(node, objectStack) { - var format = node.getAttribute('format'); - var template = node.getAttribute('template'); - var resourceType = node.getAttribute('resourceType'); - var resource = {}; - if (format) { - resource['format'] = format; - } - if (template) { - resource['template'] = template; - } - if (resourceType) { - resource['resourceType'] = resourceType; - } - return resource; -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} WGS84 BBox object. - */ -ol.format.WMTSCapabilities.readWgs84BoundingBox_ = function(node, objectStack) { - var coordinates = ol.xml.pushParseAndPop([], - ol.format.WMTSCapabilities.WGS84_BBOX_READERS_, node, objectStack); - if (coordinates.length != 2) { - return undefined; - } - return ol.extent.boundingExtent(coordinates); -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Legend object. - */ -ol.format.WMTSCapabilities.readLegendUrl_ = function(node, objectStack) { - var legend = {}; - legend['format'] = node.getAttribute('format'); - legend['href'] = ol.format.XLink.readHref(node); - return legend; -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} Coordinates object. - */ -ol.format.WMTSCapabilities.readCoordinates_ = function(node, objectStack) { - var coordinates = ol.format.XSD.readString(node).split(' '); - if (!coordinates || coordinates.length != 2) { - return undefined; - } - var x = +coordinates[0]; - var y = +coordinates[1]; - if (isNaN(x) || isNaN(y)) { - return undefined; - } - return [x, y]; -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} TileMatrix object. - */ -ol.format.WMTSCapabilities.readTileMatrix_ = function(node, objectStack) { - return ol.xml.pushParseAndPop({}, - ol.format.WMTSCapabilities.TM_PARSERS_, node, objectStack); -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} TileMatrixSetLimits Object. - */ -ol.format.WMTSCapabilities.readTileMatrixLimitsList_ = function(node, - objectStack) { - return ol.xml.pushParseAndPop([], - ol.format.WMTSCapabilities.TMS_LIMITS_LIST_PARSERS_, node, - objectStack); -}; - - -/** - * @private - * @param {Node} node Node. - * @param {Array.<*>} objectStack Object stack. - * @return {Object|undefined} TileMatrixLimits Array. - */ -ol.format.WMTSCapabilities.readTileMatrixLimits_ = function(node, objectStack) { - return ol.xml.pushParseAndPop({}, - ol.format.WMTSCapabilities.TMS_LIMITS_PARSERS_, node, objectStack); -}; - - -/** - * @const - * @private - * @type {Array.<string>} - */ -ol.format.WMTSCapabilities.NAMESPACE_URIS_ = [ - null, - 'http://www.opengis.net/wmts/1.0' -]; - - -/** - * @const - * @private - * @type {Array.<string>} - */ -ol.format.WMTSCapabilities.OWS_NAMESPACE_URIS_ = [ - null, - 'http://www.opengis.net/ows/1.1' -]; - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMTSCapabilities.PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMTSCapabilities.NAMESPACE_URIS_, { - 'Contents': ol.xml.makeObjectPropertySetter( - ol.format.WMTSCapabilities.readContents_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMTSCapabilities.CONTENTS_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMTSCapabilities.NAMESPACE_URIS_, { - 'Layer': ol.xml.makeObjectPropertyPusher( - ol.format.WMTSCapabilities.readLayer_), - 'TileMatrixSet': ol.xml.makeObjectPropertyPusher( - ol.format.WMTSCapabilities.readTileMatrixSet_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMTSCapabilities.LAYER_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMTSCapabilities.NAMESPACE_URIS_, { - 'Style': ol.xml.makeObjectPropertyPusher( - ol.format.WMTSCapabilities.readStyle_), - 'Format': ol.xml.makeObjectPropertyPusher( - ol.format.XSD.readString), - 'TileMatrixSetLink': ol.xml.makeObjectPropertyPusher( - ol.format.WMTSCapabilities.readTileMatrixSetLink_), - 'Dimension': ol.xml.makeObjectPropertyPusher( - ol.format.WMTSCapabilities.readDimensions_), - 'ResourceURL': ol.xml.makeObjectPropertyPusher( - ol.format.WMTSCapabilities.readResourceUrl_) - }, ol.xml.makeStructureNS(ol.format.WMTSCapabilities.OWS_NAMESPACE_URIS_, { - 'Title': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'Abstract': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'WGS84BoundingBox': ol.xml.makeObjectPropertySetter( - ol.format.WMTSCapabilities.readWgs84BoundingBox_), - 'Identifier': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString) - })); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMTSCapabilities.STYLE_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMTSCapabilities.NAMESPACE_URIS_, { - 'LegendURL': ol.xml.makeObjectPropertyPusher( - ol.format.WMTSCapabilities.readLegendUrl_) - }, ol.xml.makeStructureNS(ol.format.WMTSCapabilities.OWS_NAMESPACE_URIS_, { - 'Title': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'Identifier': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString) - })); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMTSCapabilities.TMS_LINKS_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMTSCapabilities.NAMESPACE_URIS_, { - 'TileMatrixSet': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'TileMatrixSetLimits': ol.xml.makeObjectPropertySetter( - ol.format.WMTSCapabilities.readTileMatrixLimitsList_) - }); - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMTSCapabilities.TMS_LIMITS_LIST_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMTSCapabilities.NAMESPACE_URIS_, { - 'TileMatrixLimits': ol.xml.makeArrayPusher( - ol.format.WMTSCapabilities.readTileMatrixLimits_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMTSCapabilities.TMS_LIMITS_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMTSCapabilities.NAMESPACE_URIS_, { - 'TileMatrix': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'MinTileRow': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readNonNegativeInteger), - 'MaxTileRow': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readNonNegativeInteger), - 'MinTileCol': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readNonNegativeInteger), - 'MaxTileCol': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readNonNegativeInteger) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMTSCapabilities.DIMENSION_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMTSCapabilities.NAMESPACE_URIS_, { - 'Default': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'Value': ol.xml.makeObjectPropertyPusher( - ol.format.XSD.readString) - }, ol.xml.makeStructureNS(ol.format.WMTSCapabilities.OWS_NAMESPACE_URIS_, { - 'Identifier': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString) - })); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMTSCapabilities.WGS84_BBOX_READERS_ = ol.xml.makeStructureNS( - ol.format.WMTSCapabilities.OWS_NAMESPACE_URIS_, { - 'LowerCorner': ol.xml.makeArrayPusher( - ol.format.WMTSCapabilities.readCoordinates_), - 'UpperCorner': ol.xml.makeArrayPusher( - ol.format.WMTSCapabilities.readCoordinates_) - }); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMTSCapabilities.TMS_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMTSCapabilities.NAMESPACE_URIS_, { - 'WellKnownScaleSet': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'TileMatrix': ol.xml.makeObjectPropertyPusher( - ol.format.WMTSCapabilities.readTileMatrix_) - }, ol.xml.makeStructureNS(ol.format.WMTSCapabilities.OWS_NAMESPACE_URIS_, { - 'SupportedCRS': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString), - 'Identifier': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString) - })); - - -/** - * @const - * @type {Object.<string, Object.<string, ol.XmlParser>>} - * @private - */ -ol.format.WMTSCapabilities.TM_PARSERS_ = ol.xml.makeStructureNS( - ol.format.WMTSCapabilities.NAMESPACE_URIS_, { - 'TopLeftCorner': ol.xml.makeObjectPropertySetter( - ol.format.WMTSCapabilities.readCoordinates_), - 'ScaleDenominator': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readDecimal), - 'TileWidth': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readNonNegativeInteger), - 'TileHeight': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readNonNegativeInteger), - 'MatrixWidth': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readNonNegativeInteger), - 'MatrixHeight': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readNonNegativeInteger) - }, ol.xml.makeStructureNS(ol.format.WMTSCapabilities.OWS_NAMESPACE_URIS_, { - 'Identifier': ol.xml.makeObjectPropertySetter( - ol.format.XSD.readString) - })); - -goog.provide('ol.GeolocationProperty'); - - -/** - * @enum {string} - */ -ol.GeolocationProperty = { - ACCURACY: 'accuracy', - ACCURACY_GEOMETRY: 'accuracyGeometry', - ALTITUDE: 'altitude', - ALTITUDE_ACCURACY: 'altitudeAccuracy', - HEADING: 'heading', - POSITION: 'position', - PROJECTION: 'projection', - SPEED: 'speed', - TRACKING: 'tracking', - TRACKING_OPTIONS: 'trackingOptions' -}; - -// FIXME handle geolocation not supported - -goog.provide('ol.Geolocation'); - -goog.require('ol'); -goog.require('ol.GeolocationProperty'); -goog.require('ol.Object'); -goog.require('ol.Sphere'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.geom.Polygon'); -goog.require('ol.has'); -goog.require('ol.math'); -goog.require('ol.proj'); -goog.require('ol.proj.EPSG4326'); - - -/** - * @classdesc - * Helper class for providing HTML5 Geolocation capabilities. - * The [Geolocation API](http://www.w3.org/TR/geolocation-API/) - * is used to locate a user's position. - * - * To get notified of position changes, register a listener for the generic - * `change` event on your instance of `ol.Geolocation`. - * - * Example: - * - * var geolocation = new ol.Geolocation({ - * // take the projection to use from the map's view - * projection: view.getProjection() - * }); - * // listen to changes in position - * geolocation.on('change', function(evt) { - * window.console.log(geolocation.getPosition()); - * }); - * - * @fires error - * @constructor - * @extends {ol.Object} - * @param {olx.GeolocationOptions=} opt_options Options. - * @api - */ -ol.Geolocation = function(opt_options) { - - ol.Object.call(this); - - var options = opt_options || {}; - - /** - * The unprojected (EPSG:4326) device position. - * @private - * @type {ol.Coordinate} - */ - this.position_ = null; - - /** - * @private - * @type {ol.TransformFunction} - */ - this.transform_ = ol.proj.identityTransform; - - /** - * @private - * @type {ol.Sphere} - */ - this.sphere_ = new ol.Sphere(ol.proj.EPSG4326.RADIUS); - - /** - * @private - * @type {number|undefined} - */ - this.watchId_ = undefined; - - ol.events.listen( - this, ol.Object.getChangeEventType(ol.GeolocationProperty.PROJECTION), - this.handleProjectionChanged_, this); - ol.events.listen( - this, ol.Object.getChangeEventType(ol.GeolocationProperty.TRACKING), - this.handleTrackingChanged_, this); - - if (options.projection !== undefined) { - this.setProjection(options.projection); - } - if (options.trackingOptions !== undefined) { - this.setTrackingOptions(options.trackingOptions); - } - - this.setTracking(options.tracking !== undefined ? options.tracking : false); - -}; -ol.inherits(ol.Geolocation, ol.Object); - - -/** - * @inheritDoc - */ -ol.Geolocation.prototype.disposeInternal = function() { - this.setTracking(false); - ol.Object.prototype.disposeInternal.call(this); -}; - - -/** - * @private - */ -ol.Geolocation.prototype.handleProjectionChanged_ = function() { - var projection = this.getProjection(); - if (projection) { - this.transform_ = ol.proj.getTransformFromProjections( - ol.proj.get('EPSG:4326'), projection); - if (this.position_) { - this.set( - ol.GeolocationProperty.POSITION, this.transform_(this.position_)); - } - } -}; - - -/** - * @private - */ -ol.Geolocation.prototype.handleTrackingChanged_ = function() { - if (ol.has.GEOLOCATION) { - var tracking = this.getTracking(); - if (tracking && this.watchId_ === undefined) { - this.watchId_ = navigator.geolocation.watchPosition( - this.positionChange_.bind(this), - this.positionError_.bind(this), - this.getTrackingOptions()); - } else if (!tracking && this.watchId_ !== undefined) { - navigator.geolocation.clearWatch(this.watchId_); - this.watchId_ = undefined; - } - } -}; - - -/** - * @private - * @param {GeolocationPosition} position position event. - */ -ol.Geolocation.prototype.positionChange_ = function(position) { - var coords = position.coords; - this.set(ol.GeolocationProperty.ACCURACY, coords.accuracy); - this.set(ol.GeolocationProperty.ALTITUDE, - coords.altitude === null ? undefined : coords.altitude); - this.set(ol.GeolocationProperty.ALTITUDE_ACCURACY, - coords.altitudeAccuracy === null ? - undefined : coords.altitudeAccuracy); - this.set(ol.GeolocationProperty.HEADING, coords.heading === null ? - undefined : ol.math.toRadians(coords.heading)); - if (!this.position_) { - this.position_ = [coords.longitude, coords.latitude]; - } else { - this.position_[0] = coords.longitude; - this.position_[1] = coords.latitude; - } - var projectedPosition = this.transform_(this.position_); - this.set(ol.GeolocationProperty.POSITION, projectedPosition); - this.set(ol.GeolocationProperty.SPEED, - coords.speed === null ? undefined : coords.speed); - var geometry = ol.geom.Polygon.circular( - this.sphere_, this.position_, coords.accuracy); - geometry.applyTransform(this.transform_); - this.set(ol.GeolocationProperty.ACCURACY_GEOMETRY, geometry); - this.changed(); -}; - -/** - * Triggered when the Geolocation returns an error. - * @event error - * @api - */ - -/** - * @private - * @param {GeolocationPositionError} error error object. - */ -ol.Geolocation.prototype.positionError_ = function(error) { - error.type = ol.events.EventType.ERROR; - this.setTracking(false); - this.dispatchEvent(/** @type {{type: string, target: undefined}} */ (error)); -}; - - -/** - * Get the accuracy of the position in meters. - * @return {number|undefined} The accuracy of the position measurement in - * meters. - * @observable - * @api - */ -ol.Geolocation.prototype.getAccuracy = function() { - return /** @type {number|undefined} */ ( - this.get(ol.GeolocationProperty.ACCURACY)); -}; - - -/** - * Get a geometry of the position accuracy. - * @return {?ol.geom.Polygon} A geometry of the position accuracy. - * @observable - * @api - */ -ol.Geolocation.prototype.getAccuracyGeometry = function() { - return /** @type {?ol.geom.Polygon} */ ( - this.get(ol.GeolocationProperty.ACCURACY_GEOMETRY) || null); -}; - - -/** - * Get the altitude associated with the position. - * @return {number|undefined} The altitude of the position in meters above mean - * sea level. - * @observable - * @api - */ -ol.Geolocation.prototype.getAltitude = function() { - return /** @type {number|undefined} */ ( - this.get(ol.GeolocationProperty.ALTITUDE)); -}; - - -/** - * Get the altitude accuracy of the position. - * @return {number|undefined} The accuracy of the altitude measurement in - * meters. - * @observable - * @api - */ -ol.Geolocation.prototype.getAltitudeAccuracy = function() { - return /** @type {number|undefined} */ ( - this.get(ol.GeolocationProperty.ALTITUDE_ACCURACY)); -}; - - -/** - * Get the heading as radians clockwise from North. - * @return {number|undefined} The heading of the device in radians from north. - * @observable - * @api - */ -ol.Geolocation.prototype.getHeading = function() { - return /** @type {number|undefined} */ ( - this.get(ol.GeolocationProperty.HEADING)); -}; - - -/** - * Get the position of the device. - * @return {ol.Coordinate|undefined} The current position of the device reported - * in the current projection. - * @observable - * @api - */ -ol.Geolocation.prototype.getPosition = function() { - return /** @type {ol.Coordinate|undefined} */ ( - this.get(ol.GeolocationProperty.POSITION)); -}; - - -/** - * Get the projection associated with the position. - * @return {ol.proj.Projection|undefined} The projection the position is - * reported in. - * @observable - * @api - */ -ol.Geolocation.prototype.getProjection = function() { - return /** @type {ol.proj.Projection|undefined} */ ( - this.get(ol.GeolocationProperty.PROJECTION)); -}; - - -/** - * Get the speed in meters per second. - * @return {number|undefined} The instantaneous speed of the device in meters - * per second. - * @observable - * @api - */ -ol.Geolocation.prototype.getSpeed = function() { - return /** @type {number|undefined} */ ( - this.get(ol.GeolocationProperty.SPEED)); -}; - - -/** - * Determine if the device location is being tracked. - * @return {boolean} The device location is being tracked. - * @observable - * @api - */ -ol.Geolocation.prototype.getTracking = function() { - return /** @type {boolean} */ ( - this.get(ol.GeolocationProperty.TRACKING)); -}; - - -/** - * Get the tracking options. - * @see http://www.w3.org/TR/geolocation-API/#position-options - * @return {GeolocationPositionOptions|undefined} PositionOptions as defined by - * the [HTML5 Geolocation spec - * ](http://www.w3.org/TR/geolocation-API/#position_options_interface). - * @observable - * @api - */ -ol.Geolocation.prototype.getTrackingOptions = function() { - return /** @type {GeolocationPositionOptions|undefined} */ ( - this.get(ol.GeolocationProperty.TRACKING_OPTIONS)); -}; - - -/** - * Set the projection to use for transforming the coordinates. - * @param {ol.ProjectionLike} projection The projection the position is - * reported in. - * @observable - * @api - */ -ol.Geolocation.prototype.setProjection = function(projection) { - this.set(ol.GeolocationProperty.PROJECTION, ol.proj.get(projection)); -}; - - -/** - * Enable or disable tracking. - * @param {boolean} tracking Enable tracking. - * @observable - * @api - */ -ol.Geolocation.prototype.setTracking = function(tracking) { - this.set(ol.GeolocationProperty.TRACKING, tracking); -}; - - -/** - * Set the tracking options. - * @see http://www.w3.org/TR/geolocation-API/#position-options - * @param {GeolocationPositionOptions} options PositionOptions as defined by the - * [HTML5 Geolocation spec - * ](http://www.w3.org/TR/geolocation-API/#position_options_interface). - * @observable - * @api - */ -ol.Geolocation.prototype.setTrackingOptions = function(options) { - this.set(ol.GeolocationProperty.TRACKING_OPTIONS, options); -}; - -goog.provide('ol.geom.Circle'); - -goog.require('ol'); -goog.require('ol.extent'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.SimpleGeometry'); -goog.require('ol.geom.flat.deflate'); - - -/** - * @classdesc - * Circle geometry. - * - * @constructor - * @extends {ol.geom.SimpleGeometry} - * @param {ol.Coordinate} center Center. - * @param {number=} opt_radius Radius. - * @param {ol.geom.GeometryLayout=} opt_layout Layout. - * @api - */ -ol.geom.Circle = function(center, opt_radius, opt_layout) { - ol.geom.SimpleGeometry.call(this); - var radius = opt_radius ? opt_radius : 0; - this.setCenterAndRadius(center, radius, opt_layout); -}; -ol.inherits(ol.geom.Circle, ol.geom.SimpleGeometry); - - -/** - * Make a complete copy of the geometry. - * @return {!ol.geom.Circle} Clone. - * @override - * @api - */ -ol.geom.Circle.prototype.clone = function() { - var circle = new ol.geom.Circle(null); - circle.setFlatCoordinates(this.layout, this.flatCoordinates.slice()); - return circle; -}; - - -/** - * @inheritDoc - */ -ol.geom.Circle.prototype.closestPointXY = function(x, y, closestPoint, minSquaredDistance) { - var flatCoordinates = this.flatCoordinates; - var dx = x - flatCoordinates[0]; - var dy = y - flatCoordinates[1]; - var squaredDistance = dx * dx + dy * dy; - if (squaredDistance < minSquaredDistance) { - var i; - if (squaredDistance === 0) { - for (i = 0; i < this.stride; ++i) { - closestPoint[i] = flatCoordinates[i]; - } - } else { - var delta = this.getRadius() / Math.sqrt(squaredDistance); - closestPoint[0] = flatCoordinates[0] + delta * dx; - closestPoint[1] = flatCoordinates[1] + delta * dy; - for (i = 2; i < this.stride; ++i) { - closestPoint[i] = flatCoordinates[i]; - } - } - closestPoint.length = this.stride; - return squaredDistance; - } else { - return minSquaredDistance; - } -}; - - -/** - * @inheritDoc - */ -ol.geom.Circle.prototype.containsXY = function(x, y) { - var flatCoordinates = this.flatCoordinates; - var dx = x - flatCoordinates[0]; - var dy = y - flatCoordinates[1]; - return dx * dx + dy * dy <= this.getRadiusSquared_(); -}; - - -/** - * Return the center of the circle as {@link ol.Coordinate coordinate}. - * @return {ol.Coordinate} Center. - * @api - */ -ol.geom.Circle.prototype.getCenter = function() { - return this.flatCoordinates.slice(0, this.stride); -}; - - -/** - * @inheritDoc - */ -ol.geom.Circle.prototype.computeExtent = function(extent) { - var flatCoordinates = this.flatCoordinates; - var radius = flatCoordinates[this.stride] - flatCoordinates[0]; - return ol.extent.createOrUpdate( - flatCoordinates[0] - radius, flatCoordinates[1] - radius, - flatCoordinates[0] + radius, flatCoordinates[1] + radius, - extent); -}; - - -/** - * Return the radius of the circle. - * @return {number} Radius. - * @api - */ -ol.geom.Circle.prototype.getRadius = function() { - return Math.sqrt(this.getRadiusSquared_()); -}; - - -/** - * @private - * @return {number} Radius squared. - */ -ol.geom.Circle.prototype.getRadiusSquared_ = function() { - var dx = this.flatCoordinates[this.stride] - this.flatCoordinates[0]; - var dy = this.flatCoordinates[this.stride + 1] - this.flatCoordinates[1]; - return dx * dx + dy * dy; -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.Circle.prototype.getType = function() { - return ol.geom.GeometryType.CIRCLE; -}; - - -/** - * @inheritDoc - * @api - */ -ol.geom.Circle.prototype.intersectsExtent = function(extent) { - var circleExtent = this.getExtent(); - if (ol.extent.intersects(extent, circleExtent)) { - var center = this.getCenter(); - - if (extent[0] <= center[0] && extent[2] >= center[0]) { - return true; - } - if (extent[1] <= center[1] && extent[3] >= center[1]) { - return true; - } - - return ol.extent.forEachCorner(extent, this.intersectsCoordinate, this); - } - return false; - -}; - - -/** - * Set the center of the circle as {@link ol.Coordinate coordinate}. - * @param {ol.Coordinate} center Center. - * @api - */ -ol.geom.Circle.prototype.setCenter = function(center) { - var stride = this.stride; - var radius = this.flatCoordinates[stride] - this.flatCoordinates[0]; - var flatCoordinates = center.slice(); - flatCoordinates[stride] = flatCoordinates[0] + radius; - var i; - for (i = 1; i < stride; ++i) { - flatCoordinates[stride + i] = center[i]; - } - this.setFlatCoordinates(this.layout, flatCoordinates); -}; - - -/** - * Set the center (as {@link ol.Coordinate coordinate}) and the radius (as - * number) of the circle. - * @param {ol.Coordinate} center Center. - * @param {number} radius Radius. - * @param {ol.geom.GeometryLayout=} opt_layout Layout. - * @api - */ -ol.geom.Circle.prototype.setCenterAndRadius = function(center, radius, opt_layout) { - if (!center) { - this.setFlatCoordinates(ol.geom.GeometryLayout.XY, null); - } else { - this.setLayout(opt_layout, center, 0); - if (!this.flatCoordinates) { - this.flatCoordinates = []; - } - /** @type {Array.<number>} */ - var flatCoordinates = this.flatCoordinates; - var offset = ol.geom.flat.deflate.coordinate( - flatCoordinates, 0, center, this.stride); - flatCoordinates[offset++] = flatCoordinates[0] + radius; - var i, ii; - for (i = 1, ii = this.stride; i < ii; ++i) { - flatCoordinates[offset++] = flatCoordinates[i]; - } - flatCoordinates.length = offset; - this.changed(); - } -}; - - -/** - * @inheritDoc - */ -ol.geom.Circle.prototype.getCoordinates = function() {}; - - -/** - * @inheritDoc - */ -ol.geom.Circle.prototype.setCoordinates = function(coordinates, opt_layout) {}; - - -/** - * @param {ol.geom.GeometryLayout} layout Layout. - * @param {Array.<number>} flatCoordinates Flat coordinates. - */ -ol.geom.Circle.prototype.setFlatCoordinates = function(layout, flatCoordinates) { - this.setFlatCoordinatesInternal(layout, flatCoordinates); - this.changed(); -}; - - -/** - * Set the radius of the circle. The radius is in the units of the projection. - * @param {number} radius Radius. - * @api - */ -ol.geom.Circle.prototype.setRadius = function(radius) { - this.flatCoordinates[this.stride] = this.flatCoordinates[0] + radius; - this.changed(); -}; - - -/** - * Transform each coordinate of the circle from one coordinate reference system - * to another. The geometry is modified in place. - * If you do not want the geometry modified in place, first clone() it and - * then use this function on the clone. - * - * Internally a circle is currently represented by two points: the center of - * the circle `[cx, cy]`, and the point to the right of the circle - * `[cx + r, cy]`. This `transform` function just transforms these two points. - * So the resulting geometry is also a circle, and that circle does not - * correspond to the shape that would be obtained by transforming every point - * of the original circle. - * - * @param {ol.ProjectionLike} source The current projection. Can be a - * string identifier or a {@link ol.proj.Projection} object. - * @param {ol.ProjectionLike} destination The desired projection. Can be a - * string identifier or a {@link ol.proj.Projection} object. - * @return {ol.geom.Circle} This geometry. Note that original geometry is - * modified in place. - * @function - * @api - */ -ol.geom.Circle.prototype.transform; - -goog.provide('ol.geom.flat.geodesic'); - -goog.require('ol.math'); -goog.require('ol.proj'); - - -/** - * @private - * @param {function(number): ol.Coordinate} interpolate Interpolate function. - * @param {ol.TransformFunction} transform Transform from longitude/latitude to - * projected coordinates. - * @param {number} squaredTolerance Squared tolerance. - * @return {Array.<number>} Flat coordinates. - */ -ol.geom.flat.geodesic.line_ = function(interpolate, transform, squaredTolerance) { - // FIXME reduce garbage generation - // FIXME optimize stack operations - - /** @type {Array.<number>} */ - var flatCoordinates = []; - - var geoA = interpolate(0); - var geoB = interpolate(1); - - var a = transform(geoA); - var b = transform(geoB); - - /** @type {Array.<ol.Coordinate>} */ - var geoStack = [geoB, geoA]; - /** @type {Array.<ol.Coordinate>} */ - var stack = [b, a]; - /** @type {Array.<number>} */ - var fractionStack = [1, 0]; - - /** @type {Object.<string, boolean>} */ - var fractions = {}; - - var maxIterations = 1e5; - var geoM, m, fracA, fracB, fracM, key; - - while (--maxIterations > 0 && fractionStack.length > 0) { - // Pop the a coordinate off the stack - fracA = fractionStack.pop(); - geoA = geoStack.pop(); - a = stack.pop(); - // Add the a coordinate if it has not been added yet - key = fracA.toString(); - if (!(key in fractions)) { - flatCoordinates.push(a[0], a[1]); - fractions[key] = true; - } - // Pop the b coordinate off the stack - fracB = fractionStack.pop(); - geoB = geoStack.pop(); - b = stack.pop(); - // Find the m point between the a and b coordinates - fracM = (fracA + fracB) / 2; - geoM = interpolate(fracM); - m = transform(geoM); - if (ol.math.squaredSegmentDistance(m[0], m[1], a[0], a[1], - b[0], b[1]) < squaredTolerance) { - // If the m point is sufficiently close to the straight line, then we - // discard it. Just use the b coordinate and move on to the next line - // segment. - flatCoordinates.push(b[0], b[1]); - key = fracB.toString(); - fractions[key] = true; - } else { - // Otherwise, we need to subdivide the current line segment. Split it - // into two and push the two line segments onto the stack. - fractionStack.push(fracB, fracM, fracM, fracA); - stack.push(b, m, m, a); - geoStack.push(geoB, geoM, geoM, geoA); - } - } - - return flatCoordinates; -}; - - -/** -* Generate a great-circle arcs between two lat/lon points. -* @param {number} lon1 Longitude 1 in degrees. -* @param {number} lat1 Latitude 1 in degrees. -* @param {number} lon2 Longitude 2 in degrees. -* @param {number} lat2 Latitude 2 in degrees. - * @param {ol.proj.Projection} projection Projection. -* @param {number} squaredTolerance Squared tolerance. -* @return {Array.<number>} Flat coordinates. -*/ -ol.geom.flat.geodesic.greatCircleArc = function( - lon1, lat1, lon2, lat2, projection, squaredTolerance) { - - var geoProjection = ol.proj.get('EPSG:4326'); - - var cosLat1 = Math.cos(ol.math.toRadians(lat1)); - var sinLat1 = Math.sin(ol.math.toRadians(lat1)); - var cosLat2 = Math.cos(ol.math.toRadians(lat2)); - var sinLat2 = Math.sin(ol.math.toRadians(lat2)); - var cosDeltaLon = Math.cos(ol.math.toRadians(lon2 - lon1)); - var sinDeltaLon = Math.sin(ol.math.toRadians(lon2 - lon1)); - var d = sinLat1 * sinLat2 + cosLat1 * cosLat2 * cosDeltaLon; - - return ol.geom.flat.geodesic.line_( - /** - * @param {number} frac Fraction. - * @return {ol.Coordinate} Coordinate. - */ - function(frac) { - if (1 <= d) { - return [lon2, lat2]; - } - var D = frac * Math.acos(d); - var cosD = Math.cos(D); - var sinD = Math.sin(D); - var y = sinDeltaLon * cosLat2; - var x = cosLat1 * sinLat2 - sinLat1 * cosLat2 * cosDeltaLon; - var theta = Math.atan2(y, x); - var lat = Math.asin(sinLat1 * cosD + cosLat1 * sinD * Math.cos(theta)); - var lon = ol.math.toRadians(lon1) + - Math.atan2(Math.sin(theta) * sinD * cosLat1, - cosD - sinLat1 * Math.sin(lat)); - return [ol.math.toDegrees(lon), ol.math.toDegrees(lat)]; - }, ol.proj.getTransform(geoProjection, projection), squaredTolerance); -}; - - -/** - * Generate a meridian (line at constant longitude). - * @param {number} lon Longitude. - * @param {number} lat1 Latitude 1. - * @param {number} lat2 Latitude 2. - * @param {ol.proj.Projection} projection Projection. - * @param {number} squaredTolerance Squared tolerance. - * @return {Array.<number>} Flat coordinates. - */ -ol.geom.flat.geodesic.meridian = function(lon, lat1, lat2, projection, squaredTolerance) { - var epsg4326Projection = ol.proj.get('EPSG:4326'); - return ol.geom.flat.geodesic.line_( - /** - * @param {number} frac Fraction. - * @return {ol.Coordinate} Coordinate. - */ - function(frac) { - return [lon, lat1 + ((lat2 - lat1) * frac)]; - }, - ol.proj.getTransform(epsg4326Projection, projection), squaredTolerance); -}; - - -/** - * Generate a parallel (line at constant latitude). - * @param {number} lat Latitude. - * @param {number} lon1 Longitude 1. - * @param {number} lon2 Longitude 2. - * @param {ol.proj.Projection} projection Projection. - * @param {number} squaredTolerance Squared tolerance. - * @return {Array.<number>} Flat coordinates. - */ -ol.geom.flat.geodesic.parallel = function(lat, lon1, lon2, projection, squaredTolerance) { - var epsg4326Projection = ol.proj.get('EPSG:4326'); - return ol.geom.flat.geodesic.line_( - /** - * @param {number} frac Fraction. - * @return {ol.Coordinate} Coordinate. - */ - function(frac) { - return [lon1 + ((lon2 - lon1) * frac), lat]; - }, - ol.proj.getTransform(epsg4326Projection, projection), squaredTolerance); -}; - -goog.provide('ol.geom.flat.topology'); - -goog.require('ol.geom.flat.area'); - -/** - * Check if the linestring is a boundary. - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @return {boolean} The linestring is a boundary. - */ -ol.geom.flat.topology.lineStringIsClosed = function(flatCoordinates, offset, end, stride) { - var lastCoord = end - stride; - if (flatCoordinates[offset] === flatCoordinates[lastCoord] && - flatCoordinates[offset + 1] === flatCoordinates[lastCoord + 1] && (end - offset) / stride > 3) { - return !!ol.geom.flat.area.linearRing(flatCoordinates, offset, end, stride); - } - return false; -}; - -goog.provide('ol.Graticule'); - -goog.require('ol.coordinate'); -goog.require('ol.extent'); -goog.require('ol.geom.GeometryLayout'); -goog.require('ol.geom.LineString'); -goog.require('ol.geom.Point'); -goog.require('ol.geom.flat.geodesic'); -goog.require('ol.math'); -goog.require('ol.proj'); -goog.require('ol.render.EventType'); -goog.require('ol.style.Fill'); -goog.require('ol.style.Stroke'); -goog.require('ol.style.Text'); - - -/** - * Render a grid for a coordinate system on a map. - * @constructor - * @param {olx.GraticuleOptions=} opt_options Options. - * @api - */ -ol.Graticule = function(opt_options) { - var options = opt_options || {}; - - /** - * @type {ol.PluggableMap} - * @private - */ - this.map_ = null; - - /** - * @type {ol.proj.Projection} - * @private - */ - this.projection_ = null; - - /** - * @type {number} - * @private - */ - this.maxLat_ = Infinity; - - /** - * @type {number} - * @private - */ - this.maxLon_ = Infinity; - - /** - * @type {number} - * @private - */ - this.minLat_ = -Infinity; - - /** - * @type {number} - * @private - */ - this.minLon_ = -Infinity; - - /** - * @type {number} - * @private - */ - this.maxLatP_ = Infinity; - - /** - * @type {number} - * @private - */ - this.maxLonP_ = Infinity; - - /** - * @type {number} - * @private - */ - this.minLatP_ = -Infinity; - - /** - * @type {number} - * @private - */ - this.minLonP_ = -Infinity; - - /** - * @type {number} - * @private - */ - this.targetSize_ = options.targetSize !== undefined ? - options.targetSize : 100; - - /** - * @type {number} - * @private - */ - this.maxLines_ = options.maxLines !== undefined ? options.maxLines : 100; - - /** - * @type {Array.<ol.geom.LineString>} - * @private - */ - this.meridians_ = []; - - /** - * @type {Array.<ol.geom.LineString>} - * @private - */ - this.parallels_ = []; - - /** - * @type {ol.style.Stroke} - * @private - */ - this.strokeStyle_ = options.strokeStyle !== undefined ? - options.strokeStyle : ol.Graticule.DEFAULT_STROKE_STYLE_; - - /** - * @type {ol.TransformFunction|undefined} - * @private - */ - this.fromLonLatTransform_ = undefined; - - /** - * @type {ol.TransformFunction|undefined} - * @private - */ - this.toLonLatTransform_ = undefined; - - /** - * @type {ol.Coordinate} - * @private - */ - this.projectionCenterLonLat_ = null; - - /** - * @type {Array.<ol.GraticuleLabelDataType>} - * @private - */ - this.meridiansLabels_ = null; - - /** - * @type {Array.<ol.GraticuleLabelDataType>} - * @private - */ - this.parallelsLabels_ = null; - - if (options.showLabels == true) { - var degreesToString = ol.coordinate.degreesToStringHDMS; - - /** - * @type {null|function(number):string} - * @private - */ - this.lonLabelFormatter_ = options.lonLabelFormatter == undefined ? - degreesToString.bind(this, 'EW') : options.lonLabelFormatter; - - /** - * @type {function(number):string} - * @private - */ - this.latLabelFormatter_ = options.latLabelFormatter == undefined ? - degreesToString.bind(this, 'NS') : options.latLabelFormatter; - - /** - * Longitude label position in fractions (0..1) of view extent. 0 means - * bottom, 1 means top. - * @type {number} - * @private - */ - this.lonLabelPosition_ = options.lonLabelPosition == undefined ? 0 : - options.lonLabelPosition; - - /** - * Latitude Label position in fractions (0..1) of view extent. 0 means left, 1 - * means right. - * @type {number} - * @private - */ - this.latLabelPosition_ = options.latLabelPosition == undefined ? 1 : - options.latLabelPosition; - - /** - * @type {ol.style.Text} - * @private - */ - this.lonLabelStyle_ = options.lonLabelStyle !== undefined ? options.lonLabelStyle : - new ol.style.Text({ - font: '12px Calibri,sans-serif', - textBaseline: 'bottom', - fill: new ol.style.Fill({ - color: 'rgba(0,0,0,1)' - }), - stroke: new ol.style.Stroke({ - color: 'rgba(255,255,255,1)', - width: 3 - }) - }); - - /** - * @type {ol.style.Text} - * @private - */ - this.latLabelStyle_ = options.latLabelStyle !== undefined ? options.latLabelStyle : - new ol.style.Text({ - font: '12px Calibri,sans-serif', - textAlign: 'end', - fill: new ol.style.Fill({ - color: 'rgba(0,0,0,1)' - }), - stroke: new ol.style.Stroke({ - color: 'rgba(255,255,255,1)', - width: 3 - }) - }); - - this.meridiansLabels_ = []; - this.parallelsLabels_ = []; - } - - this.setMap(options.map !== undefined ? options.map : null); -}; - - -/** - * @type {ol.style.Stroke} - * @private - * @const - */ -ol.Graticule.DEFAULT_STROKE_STYLE_ = new ol.style.Stroke({ - color: 'rgba(0,0,0,0.2)' -}); - - -/** - * TODO can be configurable - * @type {Array.<number>} - * @private - */ -ol.Graticule.intervals_ = [90, 45, 30, 20, 10, 5, 2, 1, 0.5, 0.2, 0.1, 0.05, - 0.01, 0.005, 0.002, 0.001]; - - -/** - * @param {number} lon Longitude. - * @param {number} minLat Minimal latitude. - * @param {number} maxLat Maximal latitude. - * @param {number} squaredTolerance Squared tolerance. - * @param {ol.Extent} extent Extent. - * @param {number} index Index. - * @return {number} Index. - * @private - */ -ol.Graticule.prototype.addMeridian_ = function(lon, minLat, maxLat, squaredTolerance, extent, index) { - var lineString = this.getMeridian_(lon, minLat, maxLat, - squaredTolerance, index); - if (ol.extent.intersects(lineString.getExtent(), extent)) { - if (this.meridiansLabels_) { - var textPoint = this.getMeridianPoint_(lineString, extent, index); - this.meridiansLabels_[index] = { - geom: textPoint, - text: this.lonLabelFormatter_(lon) - }; - } - this.meridians_[index++] = lineString; - } - return index; -}; - -/** - * @param {ol.geom.LineString} lineString Meridian - * @param {ol.Extent} extent Extent. - * @param {number} index Index. - * @return {ol.geom.Point} Meridian point. - * @private - */ -ol.Graticule.prototype.getMeridianPoint_ = function(lineString, extent, index) { - var flatCoordinates = lineString.getFlatCoordinates(); - var clampedBottom = Math.max(extent[1], flatCoordinates[1]); - var clampedTop = Math.min(extent[3], flatCoordinates[flatCoordinates.length - 1]); - var lat = ol.math.clamp( - extent[1] + Math.abs(extent[1] - extent[3]) * this.lonLabelPosition_, - clampedBottom, clampedTop); - var coordinate = [flatCoordinates[0], lat]; - var point = this.meridiansLabels_[index] !== undefined ? - this.meridiansLabels_[index].geom : new ol.geom.Point(null); - point.setCoordinates(coordinate); - return point; -}; - - -/** - * @param {number} lat Latitude. - * @param {number} minLon Minimal longitude. - * @param {number} maxLon Maximal longitude. - * @param {number} squaredTolerance Squared tolerance. - * @param {ol.Extent} extent Extent. - * @param {number} index Index. - * @return {number} Index. - * @private - */ -ol.Graticule.prototype.addParallel_ = function(lat, minLon, maxLon, squaredTolerance, extent, index) { - var lineString = this.getParallel_(lat, minLon, maxLon, squaredTolerance, - index); - if (ol.extent.intersects(lineString.getExtent(), extent)) { - if (this.parallelsLabels_) { - var textPoint = this.getParallelPoint_(lineString, extent, index); - this.parallelsLabels_[index] = { - geom: textPoint, - text: this.latLabelFormatter_(lat) - }; - } - this.parallels_[index++] = lineString; - } - return index; -}; - - -/** - * @param {ol.geom.LineString} lineString Parallels. - * @param {ol.Extent} extent Extent. - * @param {number} index Index. - * @return {ol.geom.Point} Parallel point. - * @private - */ -ol.Graticule.prototype.getParallelPoint_ = function(lineString, extent, index) { - var flatCoordinates = lineString.getFlatCoordinates(); - var clampedLeft = Math.max(extent[0], flatCoordinates[0]); - var clampedRight = Math.min(extent[2], flatCoordinates[flatCoordinates.length - 2]); - var lon = ol.math.clamp( - extent[0] + Math.abs(extent[0] - extent[2]) * this.latLabelPosition_, - clampedLeft, clampedRight); - var coordinate = [lon, flatCoordinates[1]]; - var point = this.parallelsLabels_[index] !== undefined ? - this.parallelsLabels_[index].geom : new ol.geom.Point(null); - point.setCoordinates(coordinate); - return point; -}; - - -/** - * @param {ol.Extent} extent Extent. - * @param {ol.Coordinate} center Center. - * @param {number} resolution Resolution. - * @param {number} squaredTolerance Squared tolerance. - * @private - */ -ol.Graticule.prototype.createGraticule_ = function(extent, center, resolution, squaredTolerance) { - - var interval = this.getInterval_(resolution); - if (interval == -1) { - this.meridians_.length = this.parallels_.length = 0; - if (this.meridiansLabels_) { - this.meridiansLabels_.length = 0; - } - if (this.parallelsLabels_) { - this.parallelsLabels_.length = 0; - } - return; - } - - var centerLonLat = this.toLonLatTransform_(center); - var centerLon = centerLonLat[0]; - var centerLat = centerLonLat[1]; - var maxLines = this.maxLines_; - var cnt, idx, lat, lon; - - var validExtent = [ - Math.max(extent[0], this.minLonP_), - Math.max(extent[1], this.minLatP_), - Math.min(extent[2], this.maxLonP_), - Math.min(extent[3], this.maxLatP_) - ]; - - validExtent = ol.proj.transformExtent(validExtent, this.projection_, - 'EPSG:4326'); - var maxLat = validExtent[3]; - var maxLon = validExtent[2]; - var minLat = validExtent[1]; - var minLon = validExtent[0]; - - // Create meridians - - centerLon = Math.floor(centerLon / interval) * interval; - lon = ol.math.clamp(centerLon, this.minLon_, this.maxLon_); - - idx = this.addMeridian_(lon, minLat, maxLat, squaredTolerance, extent, 0); - - cnt = 0; - while (lon != this.minLon_ && cnt++ < maxLines) { - lon = Math.max(lon - interval, this.minLon_); - idx = this.addMeridian_(lon, minLat, maxLat, squaredTolerance, extent, idx); - } - - lon = ol.math.clamp(centerLon, this.minLon_, this.maxLon_); - - cnt = 0; - while (lon != this.maxLon_ && cnt++ < maxLines) { - lon = Math.min(lon + interval, this.maxLon_); - idx = this.addMeridian_(lon, minLat, maxLat, squaredTolerance, extent, idx); - } - - this.meridians_.length = idx; - if (this.meridiansLabels_) { - this.meridiansLabels_.length = idx; - } - - // Create parallels - - centerLat = Math.floor(centerLat / interval) * interval; - lat = ol.math.clamp(centerLat, this.minLat_, this.maxLat_); - - idx = this.addParallel_(lat, minLon, maxLon, squaredTolerance, extent, 0); - - cnt = 0; - while (lat != this.minLat_ && cnt++ < maxLines) { - lat = Math.max(lat - interval, this.minLat_); - idx = this.addParallel_(lat, minLon, maxLon, squaredTolerance, extent, idx); - } - - lat = ol.math.clamp(centerLat, this.minLat_, this.maxLat_); - - cnt = 0; - while (lat != this.maxLat_ && cnt++ < maxLines) { - lat = Math.min(lat + interval, this.maxLat_); - idx = this.addParallel_(lat, minLon, maxLon, squaredTolerance, extent, idx); - } - - this.parallels_.length = idx; - if (this.parallelsLabels_) { - this.parallelsLabels_.length = idx; - } - -}; - - -/** - * @param {number} resolution Resolution. - * @return {number} The interval in degrees. - * @private - */ -ol.Graticule.prototype.getInterval_ = function(resolution) { - var centerLon = this.projectionCenterLonLat_[0]; - var centerLat = this.projectionCenterLonLat_[1]; - var interval = -1; - var i, ii, delta, dist; - var target = Math.pow(this.targetSize_ * resolution, 2); - /** @type {Array.<number>} **/ - var p1 = []; - /** @type {Array.<number>} **/ - var p2 = []; - for (i = 0, ii = ol.Graticule.intervals_.length; i < ii; ++i) { - delta = ol.Graticule.intervals_[i] / 2; - p1[0] = centerLon - delta; - p1[1] = centerLat - delta; - p2[0] = centerLon + delta; - p2[1] = centerLat + delta; - this.fromLonLatTransform_(p1, p1); - this.fromLonLatTransform_(p2, p2); - dist = Math.pow(p2[0] - p1[0], 2) + Math.pow(p2[1] - p1[1], 2); - if (dist <= target) { - break; - } - interval = ol.Graticule.intervals_[i]; - } - return interval; -}; - - -/** - * Get the map associated with this graticule. - * @return {ol.PluggableMap} The map. - * @api - */ -ol.Graticule.prototype.getMap = function() { - return this.map_; -}; - - -/** - * @param {number} lon Longitude. - * @param {number} minLat Minimal latitude. - * @param {number} maxLat Maximal latitude. - * @param {number} squaredTolerance Squared tolerance. - * @return {ol.geom.LineString} The meridian line string. - * @param {number} index Index. - * @private - */ -ol.Graticule.prototype.getMeridian_ = function(lon, minLat, maxLat, - squaredTolerance, index) { - var flatCoordinates = ol.geom.flat.geodesic.meridian(lon, - minLat, maxLat, this.projection_, squaredTolerance); - var lineString = this.meridians_[index] !== undefined ? - this.meridians_[index] : new ol.geom.LineString(null); - lineString.setFlatCoordinates(ol.geom.GeometryLayout.XY, flatCoordinates); - return lineString; -}; - - -/** - * Get the list of meridians. Meridians are lines of equal longitude. - * @return {Array.<ol.geom.LineString>} The meridians. - * @api - */ -ol.Graticule.prototype.getMeridians = function() { - return this.meridians_; -}; - - -/** - * @param {number} lat Latitude. - * @param {number} minLon Minimal longitude. - * @param {number} maxLon Maximal longitude. - * @param {number} squaredTolerance Squared tolerance. - * @return {ol.geom.LineString} The parallel line string. - * @param {number} index Index. - * @private - */ -ol.Graticule.prototype.getParallel_ = function(lat, minLon, maxLon, - squaredTolerance, index) { - var flatCoordinates = ol.geom.flat.geodesic.parallel(lat, - minLon, maxLon, this.projection_, squaredTolerance); - var lineString = this.parallels_[index] !== undefined ? - this.parallels_[index] : new ol.geom.LineString(null); - lineString.setFlatCoordinates(ol.geom.GeometryLayout.XY, flatCoordinates); - return lineString; -}; - - -/** - * Get the list of parallels. Parallels are lines of equal latitude. - * @return {Array.<ol.geom.LineString>} The parallels. - * @api - */ -ol.Graticule.prototype.getParallels = function() { - return this.parallels_; -}; - - -/** - * @param {ol.render.Event} e Event. - * @private - */ -ol.Graticule.prototype.handlePostCompose_ = function(e) { - var vectorContext = e.vectorContext; - var frameState = e.frameState; - var extent = frameState.extent; - var viewState = frameState.viewState; - var center = viewState.center; - var projection = viewState.projection; - var resolution = viewState.resolution; - var pixelRatio = frameState.pixelRatio; - var squaredTolerance = - resolution * resolution / (4 * pixelRatio * pixelRatio); - - var updateProjectionInfo = !this.projection_ || - !ol.proj.equivalent(this.projection_, projection); - - if (updateProjectionInfo) { - this.updateProjectionInfo_(projection); - } - - this.createGraticule_(extent, center, resolution, squaredTolerance); - - // Draw the lines - vectorContext.setFillStrokeStyle(null, this.strokeStyle_); - var i, l, line; - for (i = 0, l = this.meridians_.length; i < l; ++i) { - line = this.meridians_[i]; - vectorContext.drawGeometry(line); - } - for (i = 0, l = this.parallels_.length; i < l; ++i) { - line = this.parallels_[i]; - vectorContext.drawGeometry(line); - } - var labelData; - if (this.meridiansLabels_) { - for (i = 0, l = this.meridiansLabels_.length; i < l; ++i) { - labelData = this.meridiansLabels_[i]; - this.lonLabelStyle_.setText(labelData.text); - vectorContext.setTextStyle(this.lonLabelStyle_); - vectorContext.drawGeometry(labelData.geom); - } - } - if (this.parallelsLabels_) { - for (i = 0, l = this.parallelsLabels_.length; i < l; ++i) { - labelData = this.parallelsLabels_[i]; - this.latLabelStyle_.setText(labelData.text); - vectorContext.setTextStyle(this.latLabelStyle_); - vectorContext.drawGeometry(labelData.geom); - } - } -}; - - -/** - * @param {ol.proj.Projection} projection Projection. - * @private - */ -ol.Graticule.prototype.updateProjectionInfo_ = function(projection) { - var epsg4326Projection = ol.proj.get('EPSG:4326'); - - var extent = projection.getExtent(); - var worldExtent = projection.getWorldExtent(); - var worldExtentP = ol.proj.transformExtent(worldExtent, - epsg4326Projection, projection); - - var maxLat = worldExtent[3]; - var maxLon = worldExtent[2]; - var minLat = worldExtent[1]; - var minLon = worldExtent[0]; - - var maxLatP = worldExtentP[3]; - var maxLonP = worldExtentP[2]; - var minLatP = worldExtentP[1]; - var minLonP = worldExtentP[0]; - - this.maxLat_ = maxLat; - this.maxLon_ = maxLon; - this.minLat_ = minLat; - this.minLon_ = minLon; - - this.maxLatP_ = maxLatP; - this.maxLonP_ = maxLonP; - this.minLatP_ = minLatP; - this.minLonP_ = minLonP; - - - this.fromLonLatTransform_ = ol.proj.getTransform( - epsg4326Projection, projection); - - this.toLonLatTransform_ = ol.proj.getTransform( - projection, epsg4326Projection); - - this.projectionCenterLonLat_ = this.toLonLatTransform_( - ol.extent.getCenter(extent)); - - this.projection_ = projection; -}; - - -/** - * Set the map for this graticule. The graticule will be rendered on the - * provided map. - * @param {ol.PluggableMap} map Map. - * @api - */ -ol.Graticule.prototype.setMap = function(map) { - if (this.map_) { - this.map_.un(ol.render.EventType.POSTCOMPOSE, - this.handlePostCompose_, this); - this.map_.render(); - } - if (map) { - map.on(ol.render.EventType.POSTCOMPOSE, - this.handlePostCompose_, this); - map.render(); - } - this.map_ = map; -}; - -goog.provide('ol.ImageBase'); - -goog.require('ol'); -goog.require('ol.events.EventTarget'); -goog.require('ol.events.EventType'); - - -/** - * @constructor - * @abstract - * @extends {ol.events.EventTarget} - * @param {ol.Extent} extent Extent. - * @param {number|undefined} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.ImageState} state State. - * @param {Array.<ol.Attribution>} attributions Attributions. - */ -ol.ImageBase = function(extent, resolution, pixelRatio, state, attributions) { - - ol.events.EventTarget.call(this); - - /** - * @private - * @type {Array.<ol.Attribution>} - */ - this.attributions_ = attributions; - - /** - * @protected - * @type {ol.Extent} - */ - this.extent = extent; - - /** - * @private - * @type {number} - */ - this.pixelRatio_ = pixelRatio; - - /** - * @protected - * @type {number|undefined} - */ - this.resolution = resolution; - - /** - * @protected - * @type {ol.ImageState} - */ - this.state = state; - -}; -ol.inherits(ol.ImageBase, ol.events.EventTarget); - - -/** - * @protected - */ -ol.ImageBase.prototype.changed = function() { - this.dispatchEvent(ol.events.EventType.CHANGE); -}; - - -/** - * @return {Array.<ol.Attribution>} Attributions. - */ -ol.ImageBase.prototype.getAttributions = function() { - return this.attributions_; -}; - - -/** - * @return {ol.Extent} Extent. - */ -ol.ImageBase.prototype.getExtent = function() { - return this.extent; -}; - - -/** - * @abstract - * @return {HTMLCanvasElement|Image|HTMLVideoElement} Image. - */ -ol.ImageBase.prototype.getImage = function() {}; - - -/** - * @return {number} PixelRatio. - */ -ol.ImageBase.prototype.getPixelRatio = function() { - return this.pixelRatio_; -}; - - -/** - * @return {number} Resolution. - */ -ol.ImageBase.prototype.getResolution = function() { - return /** @type {number} */ (this.resolution); -}; - - -/** - * @return {ol.ImageState} State. - */ -ol.ImageBase.prototype.getState = function() { - return this.state; -}; - - -/** - * Load not yet loaded URI. - * @abstract - */ -ol.ImageBase.prototype.load = function() {}; - -goog.provide('ol.Image'); - -goog.require('ol'); -goog.require('ol.ImageBase'); -goog.require('ol.ImageState'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.extent'); - - -/** - * @constructor - * @extends {ol.ImageBase} - * @param {ol.Extent} extent Extent. - * @param {number|undefined} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @param {Array.<ol.Attribution>} attributions Attributions. - * @param {string} src Image source URI. - * @param {?string} crossOrigin Cross origin. - * @param {ol.ImageLoadFunctionType} imageLoadFunction Image load function. - */ -ol.Image = function(extent, resolution, pixelRatio, attributions, src, - crossOrigin, imageLoadFunction) { - - ol.ImageBase.call(this, extent, resolution, pixelRatio, ol.ImageState.IDLE, - attributions); - - /** - * @private - * @type {string} - */ - this.src_ = src; - - /** - * @private - * @type {HTMLCanvasElement|Image|HTMLVideoElement} - */ - this.image_ = new Image(); - if (crossOrigin !== null) { - this.image_.crossOrigin = crossOrigin; - } - - /** - * @private - * @type {Array.<ol.EventsKey>} - */ - this.imageListenerKeys_ = null; - - /** - * @protected - * @type {ol.ImageState} - */ - this.state = ol.ImageState.IDLE; - - /** - * @private - * @type {ol.ImageLoadFunctionType} - */ - this.imageLoadFunction_ = imageLoadFunction; - -}; -ol.inherits(ol.Image, ol.ImageBase); - - -/** - * @inheritDoc - * @api - */ -ol.Image.prototype.getImage = function() { - return this.image_; -}; - - -/** - * Tracks loading or read errors. - * - * @private - */ -ol.Image.prototype.handleImageError_ = function() { - this.state = ol.ImageState.ERROR; - this.unlistenImage_(); - this.changed(); -}; - - -/** - * Tracks successful image load. - * - * @private - */ -ol.Image.prototype.handleImageLoad_ = function() { - if (this.resolution === undefined) { - this.resolution = ol.extent.getHeight(this.extent) / this.image_.height; - } - this.state = ol.ImageState.LOADED; - this.unlistenImage_(); - this.changed(); -}; - - -/** - * Load the image or retry if loading previously failed. - * Loading is taken care of by the tile queue, and calling this method is - * only needed for preloading or for reloading in case of an error. - * @override - * @api - */ -ol.Image.prototype.load = function() { - if (this.state == ol.ImageState.IDLE || this.state == ol.ImageState.ERROR) { - this.state = ol.ImageState.LOADING; - this.changed(); - this.imageListenerKeys_ = [ - ol.events.listenOnce(this.image_, ol.events.EventType.ERROR, - this.handleImageError_, this), - ol.events.listenOnce(this.image_, ol.events.EventType.LOAD, - this.handleImageLoad_, this) - ]; - this.imageLoadFunction_(this, this.src_); - } -}; - - -/** - * @param {HTMLCanvasElement|Image|HTMLVideoElement} image Image. - */ -ol.Image.prototype.setImage = function(image) { - this.image_ = image; -}; - - -/** - * Discards event handlers which listen for load completion or errors. - * - * @private - */ -ol.Image.prototype.unlistenImage_ = function() { - this.imageListenerKeys_.forEach(ol.events.unlistenByKey); - this.imageListenerKeys_ = null; -}; - -goog.provide('ol.ImageCanvas'); - -goog.require('ol'); -goog.require('ol.ImageBase'); -goog.require('ol.ImageState'); - - -/** - * @constructor - * @extends {ol.ImageBase} - * @param {ol.Extent} extent Extent. - * @param {number} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @param {Array.<ol.Attribution>} attributions Attributions. - * @param {HTMLCanvasElement} canvas Canvas. - * @param {ol.ImageCanvasLoader=} opt_loader Optional loader function to - * support asynchronous canvas drawing. - */ -ol.ImageCanvas = function(extent, resolution, pixelRatio, attributions, - canvas, opt_loader) { - - /** - * Optional canvas loader function. - * @type {?ol.ImageCanvasLoader} - * @private - */ - this.loader_ = opt_loader !== undefined ? opt_loader : null; - - var state = opt_loader !== undefined ? - ol.ImageState.IDLE : ol.ImageState.LOADED; - - ol.ImageBase.call(this, extent, resolution, pixelRatio, state, attributions); - - /** - * @private - * @type {HTMLCanvasElement} - */ - this.canvas_ = canvas; - - /** - * @private - * @type {Error} - */ - this.error_ = null; - -}; -ol.inherits(ol.ImageCanvas, ol.ImageBase); - - -/** - * Get any error associated with asynchronous rendering. - * @return {Error} Any error that occurred during rendering. - */ -ol.ImageCanvas.prototype.getError = function() { - return this.error_; -}; - - -/** - * Handle async drawing complete. - * @param {Error} err Any error during drawing. - * @private - */ -ol.ImageCanvas.prototype.handleLoad_ = function(err) { - if (err) { - this.error_ = err; - this.state = ol.ImageState.ERROR; - } else { - this.state = ol.ImageState.LOADED; - } - this.changed(); -}; - - -/** - * @inheritDoc - */ -ol.ImageCanvas.prototype.load = function() { - if (this.state == ol.ImageState.IDLE) { - this.state = ol.ImageState.LOADING; - this.changed(); - this.loader_(this.handleLoad_.bind(this)); - } -}; - - -/** - * @inheritDoc - */ -ol.ImageCanvas.prototype.getImage = function() { - return this.canvas_; -}; - -goog.provide('ol.Tile'); - -goog.require('ol'); -goog.require('ol.TileState'); -goog.require('ol.easing'); -goog.require('ol.events.EventTarget'); -goog.require('ol.events.EventType'); - - -/** - * @classdesc - * Base class for tiles. - * - * @constructor - * @abstract - * @extends {ol.events.EventTarget} - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {ol.TileState} state State. - * @param {olx.TileOptions=} opt_options Tile options. - */ -ol.Tile = function(tileCoord, state, opt_options) { - ol.events.EventTarget.call(this); - - var options = opt_options ? opt_options : {}; - - /** - * @type {ol.TileCoord} - */ - this.tileCoord = tileCoord; - - /** - * @protected - * @type {ol.TileState} - */ - this.state = state; - - /** - * An "interim" tile for this tile. The interim tile may be used while this - * one is loading, for "smooth" transitions when changing params/dimensions - * on the source. - * @type {ol.Tile} - */ - this.interimTile = null; - - /** - * A key assigned to the tile. This is used by the tile source to determine - * if this tile can effectively be used, or if a new tile should be created - * and this one be used as an interim tile for this new tile. - * @type {string} - */ - this.key = ''; - - /** - * The duration for the opacity transition. - * @type {number} - */ - this.transition_ = options.transition === undefined ? - 250 : options.transition; - - /** - * Lookup of start times for rendering transitions. If the start time is - * equal to -1, the transition is complete. - * @type {Object.<number, number>} - */ - this.transitionStarts_ = {}; - -}; -ol.inherits(ol.Tile, ol.events.EventTarget); - - -/** - * @protected - */ -ol.Tile.prototype.changed = function() { - this.dispatchEvent(ol.events.EventType.CHANGE); -}; - - -/** - * @return {string} Key. - */ -ol.Tile.prototype.getKey = function() { - return this.key + '/' + this.tileCoord; -}; - -/** - * Get the interim tile most suitable for rendering using the chain of interim - * tiles. This corresponds to the most recent tile that has been loaded, if no - * such tile exists, the original tile is returned. - * @return {!ol.Tile} Best tile for rendering. - */ -ol.Tile.prototype.getInterimTile = function() { - if (!this.interimTile) { - //empty chain - return this; - } - var tile = this.interimTile; - - // find the first loaded tile and return it. Since the chain is sorted in - // decreasing order of creation time, there is no need to search the remainder - // of the list (all those tiles correspond to older requests and will be - // cleaned up by refreshInterimChain) - do { - if (tile.getState() == ol.TileState.LOADED) { - return tile; - } - tile = tile.interimTile; - } while (tile); - - // we can not find a better tile - return this; -}; - -/** - * Goes through the chain of interim tiles and discards sections of the chain - * that are no longer relevant. - */ -ol.Tile.prototype.refreshInterimChain = function() { - if (!this.interimTile) { - return; - } - - var tile = this.interimTile; - var prev = this; - - do { - if (tile.getState() == ol.TileState.LOADED) { - //we have a loaded tile, we can discard the rest of the list - //we would could abort any LOADING tile request - //older than this tile (i.e. any LOADING tile following this entry in the chain) - tile.interimTile = null; - break; - } else if (tile.getState() == ol.TileState.LOADING) { - //keep this LOADING tile any loaded tiles later in the chain are - //older than this tile, so we're still interested in the request - prev = tile; - } else if (tile.getState() == ol.TileState.IDLE) { - //the head of the list is the most current tile, we don't need - //to start any other requests for this chain - prev.interimTile = tile.interimTile; - } else { - prev = tile; - } - tile = prev.interimTile; - } while (tile); -}; - -/** - * Get the tile coordinate for this tile. - * @return {ol.TileCoord} The tile coordinate. - * @api - */ -ol.Tile.prototype.getTileCoord = function() { - return this.tileCoord; -}; - - -/** - * @return {ol.TileState} State. - */ -ol.Tile.prototype.getState = function() { - return this.state; -}; - -/** - * @param {ol.TileState} state State. - */ -ol.Tile.prototype.setState = function(state) { - this.state = state; - this.changed(); -}; - -/** - * Load the image or retry if loading previously failed. - * Loading is taken care of by the tile queue, and calling this method is - * only needed for preloading or for reloading in case of an error. - * @abstract - * @api - */ -ol.Tile.prototype.load = function() {}; - -/** - * Get the alpha value for rendering. - * @param {number} id An id for the renderer. - * @param {number} time The render frame time. - * @return {number} A number between 0 and 1. - */ -ol.Tile.prototype.getAlpha = function(id, time) { - if (!this.transition_) { - return 1; - } - - var start = this.transitionStarts_[id]; - if (!start) { - start = time; - this.transitionStarts_[id] = start; - } else if (start === -1) { - return 1; - } - - var delta = time - start + (1000 / 60); // avoid rendering at 0 - if (delta >= this.transition_) { - return 1; - } - return ol.easing.easeIn(delta / this.transition_); -}; - -/** - * Determine if a tile is in an alpha transition. A tile is considered in - * transition if tile.getAlpha() has not yet been called or has been called - * and returned 1. - * @param {number} id An id for the renderer. - * @return {boolean} The tile is in transition. - */ -ol.Tile.prototype.inTransition = function(id) { - if (!this.transition_) { - return false; - } - return this.transitionStarts_[id] !== -1; -}; - -/** - * Mark a transition as complete. - * @param {number} id An id for the renderer. - */ -ol.Tile.prototype.endTransition = function(id) { - if (this.transition_) { - this.transitionStarts_[id] = -1; - } -}; - -goog.provide('ol.ImageTile'); - -goog.require('ol'); -goog.require('ol.Tile'); -goog.require('ol.TileState'); -goog.require('ol.dom'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); - - -/** - * @constructor - * @extends {ol.Tile} - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {ol.TileState} state State. - * @param {string} src Image source URI. - * @param {?string} crossOrigin Cross origin. - * @param {ol.TileLoadFunctionType} tileLoadFunction Tile load function. - * @param {olx.TileOptions=} opt_options Tile options. - */ -ol.ImageTile = function(tileCoord, state, src, crossOrigin, tileLoadFunction, opt_options) { - - ol.Tile.call(this, tileCoord, state, opt_options); - - /** - * Image URI - * - * @private - * @type {string} - */ - this.src_ = src; - - /** - * @private - * @type {Image|HTMLCanvasElement} - */ - this.image_ = new Image(); - if (crossOrigin !== null) { - this.image_.crossOrigin = crossOrigin; - } - - /** - * @private - * @type {Array.<ol.EventsKey>} - */ - this.imageListenerKeys_ = null; - - /** - * @private - * @type {ol.TileLoadFunctionType} - */ - this.tileLoadFunction_ = tileLoadFunction; - -}; -ol.inherits(ol.ImageTile, ol.Tile); - - -/** - * @inheritDoc - */ -ol.ImageTile.prototype.disposeInternal = function() { - if (this.state == ol.TileState.LOADING) { - this.unlistenImage_(); - this.image_.src = ol.ImageTile.blankImageUrl; - } - if (this.interimTile) { - this.interimTile.dispose(); - } - this.state = ol.TileState.ABORT; - this.changed(); - ol.Tile.prototype.disposeInternal.call(this); -}; - - -/** - * Get the HTML image element for this tile (may be a Canvas, Image, or Video). - * @return {HTMLCanvasElement|HTMLImageElement|HTMLVideoElement} Image. - * @api - */ -ol.ImageTile.prototype.getImage = function() { - return this.image_; -}; - - -/** - * @inheritDoc - */ -ol.ImageTile.prototype.getKey = function() { - return this.src_; -}; - - -/** - * Tracks loading or read errors. - * - * @private - */ -ol.ImageTile.prototype.handleImageError_ = function() { - this.state = ol.TileState.ERROR; - this.unlistenImage_(); - this.image_.src = ol.ImageTile.blankImageUrl; - this.changed(); -}; - - -/** - * Tracks successful image load. - * - * @private - */ -ol.ImageTile.prototype.handleImageLoad_ = function() { - if (this.image_.naturalWidth && this.image_.naturalHeight) { - this.state = ol.TileState.LOADED; - } else { - this.state = ol.TileState.EMPTY; - } - this.unlistenImage_(); - this.changed(); -}; - - -/** - * @inheritDoc - * @api - */ -ol.ImageTile.prototype.load = function() { - if (this.state == ol.TileState.IDLE || this.state == ol.TileState.ERROR) { - this.state = ol.TileState.LOADING; - this.changed(); - this.imageListenerKeys_ = [ - ol.events.listenOnce(this.image_, ol.events.EventType.ERROR, - this.handleImageError_, this), - ol.events.listenOnce(this.image_, ol.events.EventType.LOAD, - this.handleImageLoad_, this) - ]; - this.tileLoadFunction_(this, this.src_); - } -}; - - -/** - * Discards event handlers which listen for load completion or errors. - * - * @private - */ -ol.ImageTile.prototype.unlistenImage_ = function() { - this.imageListenerKeys_.forEach(ol.events.unlistenByKey); - this.imageListenerKeys_ = null; -}; - - -/** - * Data URI for a blank image. - * @type {string} - */ -ol.ImageTile.blankImageUrl = (function() { - var ctx = ol.dom.createCanvasContext2D(1, 1); - ctx.fillStyle = 'rgba(0,0,0,0)'; - ctx.fillRect(0, 0, 1, 1); - return ctx.canvas.toDataURL('image/png'); -})(); - -// FIXME should handle all geo-referenced data, not just vector data - -goog.provide('ol.interaction.DragAndDrop'); - -goog.require('ol'); -goog.require('ol.functions'); -goog.require('ol.events'); -goog.require('ol.events.Event'); -goog.require('ol.events.EventType'); -goog.require('ol.interaction.Interaction'); -goog.require('ol.proj'); - - -/** - * @classdesc - * Handles input of vector data by drag and drop. - * - * @constructor - * @extends {ol.interaction.Interaction} - * @fires ol.interaction.DragAndDrop.Event - * @param {olx.interaction.DragAndDropOptions=} opt_options Options. - * @api - */ -ol.interaction.DragAndDrop = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - ol.interaction.Interaction.call(this, { - handleEvent: ol.interaction.DragAndDrop.handleEvent - }); - - /** - * @private - * @type {Array.<function(new: ol.format.Feature)>} - */ - this.formatConstructors_ = options.formatConstructors ? - options.formatConstructors : []; - - /** - * @private - * @type {ol.proj.Projection} - */ - this.projection_ = options.projection ? - ol.proj.get(options.projection) : null; - - /** - * @private - * @type {Array.<ol.EventsKey>} - */ - this.dropListenKeys_ = null; - - /** - * @private - * @type {ol.source.Vector} - */ - this.source_ = options.source || null; - - /** - * @private - * @type {Element} - */ - this.target = options.target ? options.target : null; - -}; -ol.inherits(ol.interaction.DragAndDrop, ol.interaction.Interaction); - - -/** - * @param {Event} event Event. - * @this {ol.interaction.DragAndDrop} - * @private - */ -ol.interaction.DragAndDrop.handleDrop_ = function(event) { - var files = event.dataTransfer.files; - var i, ii, file; - for (i = 0, ii = files.length; i < ii; ++i) { - file = files.item(i); - var reader = new FileReader(); - reader.addEventListener(ol.events.EventType.LOAD, - this.handleResult_.bind(this, file)); - reader.readAsText(file); - } -}; - - -/** - * @param {Event} event Event. - * @private - */ -ol.interaction.DragAndDrop.handleStop_ = function(event) { - event.stopPropagation(); - event.preventDefault(); - event.dataTransfer.dropEffect = 'copy'; -}; - - -/** - * @param {File} file File. - * @param {Event} event Load event. - * @private - */ -ol.interaction.DragAndDrop.prototype.handleResult_ = function(file, event) { - var result = event.target.result; - var map = this.getMap(); - var projection = this.projection_; - if (!projection) { - var view = map.getView(); - projection = view.getProjection(); - } - - var formatConstructors = this.formatConstructors_; - var features = []; - var i, ii; - for (i = 0, ii = formatConstructors.length; i < ii; ++i) { - /** - * Avoid "cannot instantiate abstract class" error. - * @type {Function} - */ - var formatConstructor = formatConstructors[i]; - /** - * @type {ol.format.Feature} - */ - var format = new formatConstructor(); - features = this.tryReadFeatures_(format, result, { - featureProjection: projection - }); - if (features && features.length > 0) { - break; - } - } - if (this.source_) { - this.source_.clear(); - this.source_.addFeatures(features); - } - this.dispatchEvent( - new ol.interaction.DragAndDrop.Event( - ol.interaction.DragAndDrop.EventType_.ADD_FEATURES, file, - features, projection)); -}; - - -/** - * Handles the {@link ol.MapBrowserEvent map browser event} unconditionally and - * neither prevents the browser default nor stops event propagation. - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} `false` to stop event propagation. - * @this {ol.interaction.DragAndDrop} - * @api - */ -ol.interaction.DragAndDrop.handleEvent = ol.functions.TRUE; - - -/** - * @private - */ -ol.interaction.DragAndDrop.prototype.registerListeners_ = function() { - var map = this.getMap(); - if (map) { - var dropArea = this.target ? this.target : map.getViewport(); - this.dropListenKeys_ = [ - ol.events.listen(dropArea, ol.events.EventType.DROP, - ol.interaction.DragAndDrop.handleDrop_, this), - ol.events.listen(dropArea, ol.events.EventType.DRAGENTER, - ol.interaction.DragAndDrop.handleStop_, this), - ol.events.listen(dropArea, ol.events.EventType.DRAGOVER, - ol.interaction.DragAndDrop.handleStop_, this), - ol.events.listen(dropArea, ol.events.EventType.DROP, - ol.interaction.DragAndDrop.handleStop_, this) - ]; - } -}; - - -/** - * @inheritDoc - */ -ol.interaction.DragAndDrop.prototype.setActive = function(active) { - ol.interaction.Interaction.prototype.setActive.call(this, active); - if (active) { - this.registerListeners_(); - } else { - this.unregisterListeners_(); - } -}; - - -/** - * @inheritDoc - */ -ol.interaction.DragAndDrop.prototype.setMap = function(map) { - this.unregisterListeners_(); - ol.interaction.Interaction.prototype.setMap.call(this, map); - if (this.getActive()) { - this.registerListeners_(); - } -}; - - -/** - * @param {ol.format.Feature} format Format. - * @param {string} text Text. - * @param {olx.format.ReadOptions} options Read options. - * @private - * @return {Array.<ol.Feature>} Features. - */ -ol.interaction.DragAndDrop.prototype.tryReadFeatures_ = function(format, text, options) { - try { - return format.readFeatures(text, options); - } catch (e) { - return null; - } -}; - - -/** - * @private - */ -ol.interaction.DragAndDrop.prototype.unregisterListeners_ = function() { - if (this.dropListenKeys_) { - this.dropListenKeys_.forEach(ol.events.unlistenByKey); - this.dropListenKeys_ = null; - } -}; - - -/** - * @enum {string} - * @private - */ -ol.interaction.DragAndDrop.EventType_ = { - /** - * Triggered when features are added - * @event ol.interaction.DragAndDrop.Event#addfeatures - * @api - */ - ADD_FEATURES: 'addfeatures' -}; - - -/** - * @classdesc - * Events emitted by {@link ol.interaction.DragAndDrop} instances are instances - * of this type. - * - * @constructor - * @extends {ol.events.Event} - * @implements {oli.interaction.DragAndDropEvent} - * @param {ol.interaction.DragAndDrop.EventType_} type Type. - * @param {File} file File. - * @param {Array.<ol.Feature>=} opt_features Features. - * @param {ol.proj.Projection=} opt_projection Projection. - */ -ol.interaction.DragAndDrop.Event = function(type, file, opt_features, opt_projection) { - - ol.events.Event.call(this, type); - - /** - * The features parsed from dropped data. - * @type {Array.<ol.Feature>|undefined} - * @api - */ - this.features = opt_features; - - /** - * The dropped file. - * @type {File} - * @api - */ - this.file = file; - - /** - * The feature projection. - * @type {ol.proj.Projection|undefined} - * @api - */ - this.projection = opt_projection; - -}; -ol.inherits(ol.interaction.DragAndDrop.Event, ol.events.Event); - -goog.provide('ol.interaction.DragRotateAndZoom'); - -goog.require('ol'); -goog.require('ol.RotationConstraint'); -goog.require('ol.ViewHint'); -goog.require('ol.events.condition'); -goog.require('ol.interaction.Interaction'); -goog.require('ol.interaction.Pointer'); - - -/** - * @classdesc - * Allows the user to zoom and rotate the map by clicking and dragging - * on the map. By default, this interaction is limited to when the shift - * key is held down. - * - * This interaction is only supported for mouse devices. - * - * And this interaction is not included in the default interactions. - * - * @constructor - * @extends {ol.interaction.Pointer} - * @param {olx.interaction.DragRotateAndZoomOptions=} opt_options Options. - * @api - */ -ol.interaction.DragRotateAndZoom = function(opt_options) { - - var options = opt_options ? opt_options : {}; - - ol.interaction.Pointer.call(this, { - handleDownEvent: ol.interaction.DragRotateAndZoom.handleDownEvent_, - handleDragEvent: ol.interaction.DragRotateAndZoom.handleDragEvent_, - handleUpEvent: ol.interaction.DragRotateAndZoom.handleUpEvent_ - }); - - /** - * @private - * @type {ol.EventsConditionType} - */ - this.condition_ = options.condition ? - options.condition : ol.events.condition.shiftKeyOnly; - - /** - * @private - * @type {number|undefined} - */ - this.lastAngle_ = undefined; - - /** - * @private - * @type {number|undefined} - */ - this.lastMagnitude_ = undefined; - - /** - * @private - * @type {number} - */ - this.lastScaleDelta_ = 0; - - /** - * @private - * @type {number} - */ - this.duration_ = options.duration !== undefined ? options.duration : 400; - -}; -ol.inherits(ol.interaction.DragRotateAndZoom, ol.interaction.Pointer); - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @this {ol.interaction.DragRotateAndZoom} - * @private - */ -ol.interaction.DragRotateAndZoom.handleDragEvent_ = function(mapBrowserEvent) { - if (!ol.events.condition.mouseOnly(mapBrowserEvent)) { - return; - } - - var map = mapBrowserEvent.map; - var size = map.getSize(); - var offset = mapBrowserEvent.pixel; - var deltaX = offset[0] - size[0] / 2; - var deltaY = size[1] / 2 - offset[1]; - var theta = Math.atan2(deltaY, deltaX); - var magnitude = Math.sqrt(deltaX * deltaX + deltaY * deltaY); - var view = map.getView(); - if (view.getConstraints().rotation !== ol.RotationConstraint.disable && this.lastAngle_ !== undefined) { - var angleDelta = theta - this.lastAngle_; - ol.interaction.Interaction.rotateWithoutConstraints( - view, view.getRotation() - angleDelta); - } - this.lastAngle_ = theta; - if (this.lastMagnitude_ !== undefined) { - var resolution = this.lastMagnitude_ * (view.getResolution() / magnitude); - ol.interaction.Interaction.zoomWithoutConstraints(view, resolution); - } - if (this.lastMagnitude_ !== undefined) { - this.lastScaleDelta_ = this.lastMagnitude_ / magnitude; - } - this.lastMagnitude_ = magnitude; -}; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Stop drag sequence? - * @this {ol.interaction.DragRotateAndZoom} - * @private - */ -ol.interaction.DragRotateAndZoom.handleUpEvent_ = function(mapBrowserEvent) { - if (!ol.events.condition.mouseOnly(mapBrowserEvent)) { - return true; - } - - var map = mapBrowserEvent.map; - var view = map.getView(); - view.setHint(ol.ViewHint.INTERACTING, -1); - var direction = this.lastScaleDelta_ - 1; - ol.interaction.Interaction.rotate(view, view.getRotation()); - ol.interaction.Interaction.zoom(view, view.getResolution(), - undefined, this.duration_, direction); - this.lastScaleDelta_ = 0; - return false; -}; - - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Start drag sequence? - * @this {ol.interaction.DragRotateAndZoom} - * @private - */ -ol.interaction.DragRotateAndZoom.handleDownEvent_ = function(mapBrowserEvent) { - if (!ol.events.condition.mouseOnly(mapBrowserEvent)) { - return false; - } - - if (this.condition_(mapBrowserEvent)) { - mapBrowserEvent.map.getView().setHint(ol.ViewHint.INTERACTING, 1); - this.lastAngle_ = undefined; - this.lastMagnitude_ = undefined; - return true; - } else { - return false; - } -}; - -goog.provide('ol.interaction.DrawEventType'); - - -/** - * @enum {string} - */ -ol.interaction.DrawEventType = { - /** - * Triggered upon feature draw start - * @event ol.interaction.Draw.Event#drawstart - * @api - */ - DRAWSTART: 'drawstart', - /** - * Triggered upon feature draw end - * @event ol.interaction.Draw.Event#drawend - * @api - */ - DRAWEND: 'drawend' -}; - -goog.provide('ol.layer.Vector'); - -goog.require('ol'); -goog.require('ol.LayerType'); -goog.require('ol.layer.Layer'); -goog.require('ol.obj'); -goog.require('ol.style.Style'); - - -/** - * @classdesc - * Vector data that is rendered client-side. - * Note that any property set in the options is set as a {@link ol.Object} - * property on the layer object; for example, setting `title: 'My Title'` in the - * options means that `title` is observable, and has get/set accessors. - * - * @constructor - * @extends {ol.layer.Layer} - * @fires ol.render.Event - * @param {olx.layer.VectorOptions=} opt_options Options. - * @api - */ -ol.layer.Vector = function(opt_options) { - var options = opt_options ? - opt_options : /** @type {olx.layer.VectorOptions} */ ({}); - - var baseOptions = ol.obj.assign({}, options); - - delete baseOptions.style; - delete baseOptions.renderBuffer; - delete baseOptions.updateWhileAnimating; - delete baseOptions.updateWhileInteracting; - ol.layer.Layer.call(this, /** @type {olx.layer.LayerOptions} */ (baseOptions)); - - /** - * @type {number} - * @private - */ - this.renderBuffer_ = options.renderBuffer !== undefined ? - options.renderBuffer : 100; - - /** - * User provided style. - * @type {ol.style.Style|Array.<ol.style.Style>|ol.StyleFunction} - * @private - */ - this.style_ = null; - - /** - * Style function for use within the library. - * @type {ol.StyleFunction|undefined} - * @private - */ - this.styleFunction_ = undefined; - - this.setStyle(options.style); - - /** - * @type {boolean} - * @private - */ - this.updateWhileAnimating_ = options.updateWhileAnimating !== undefined ? - options.updateWhileAnimating : false; - - /** - * @type {boolean} - * @private - */ - this.updateWhileInteracting_ = options.updateWhileInteracting !== undefined ? - options.updateWhileInteracting : false; - - /** - * The layer type. - * @protected - * @type {ol.LayerType} - */ - this.type = ol.LayerType.VECTOR; - -}; -ol.inherits(ol.layer.Vector, ol.layer.Layer); - - -/** - * @return {number|undefined} Render buffer. - */ -ol.layer.Vector.prototype.getRenderBuffer = function() { - return this.renderBuffer_; -}; - - -/** - * @return {function(ol.Feature, ol.Feature): number|null|undefined} Render - * order. - */ -ol.layer.Vector.prototype.getRenderOrder = function() { - return /** @type {ol.RenderOrderFunction|null|undefined} */ ( - this.get(ol.layer.Vector.Property_.RENDER_ORDER)); -}; - - -/** - * Return the associated {@link ol.source.Vector vectorsource} of the layer. - * @function - * @return {ol.source.Vector} Source. - * @api - */ -ol.layer.Vector.prototype.getSource; - - -/** - * Get the style for features. This returns whatever was passed to the `style` - * option at construction or to the `setStyle` method. - * @return {ol.style.Style|Array.<ol.style.Style>|ol.StyleFunction} - * Layer style. - * @api - */ -ol.layer.Vector.prototype.getStyle = function() { - return this.style_; -}; - - -/** - * Get the style function. - * @return {ol.StyleFunction|undefined} Layer style function. - * @api - */ -ol.layer.Vector.prototype.getStyleFunction = function() { - return this.styleFunction_; -}; - - -/** - * @return {boolean} Whether the rendered layer should be updated while - * animating. - */ -ol.layer.Vector.prototype.getUpdateWhileAnimating = function() { - return this.updateWhileAnimating_; -}; - - -/** - * @return {boolean} Whether the rendered layer should be updated while - * interacting. - */ -ol.layer.Vector.prototype.getUpdateWhileInteracting = function() { - return this.updateWhileInteracting_; -}; - - -/** - * @param {ol.RenderOrderFunction|null|undefined} renderOrder - * Render order. - */ -ol.layer.Vector.prototype.setRenderOrder = function(renderOrder) { - this.set(ol.layer.Vector.Property_.RENDER_ORDER, renderOrder); -}; - - -/** - * Set the style for features. This can be a single style object, an array - * of styles, or a function that takes a feature and resolution and returns - * an array of styles. If it is `undefined` the default style is used. If - * it is `null` the layer has no style (a `null` style), so only features - * that have their own styles will be rendered in the layer. See - * {@link ol.style} for information on the default style. - * @param {ol.style.Style|Array.<ol.style.Style>|ol.StyleFunction|null|undefined} - * style Layer style. - * @api - */ -ol.layer.Vector.prototype.setStyle = function(style) { - this.style_ = style !== undefined ? style : ol.style.Style.defaultFunction; - this.styleFunction_ = style === null ? - undefined : ol.style.Style.createFunction(this.style_); - this.changed(); -}; - - -/** - * @enum {string} - * @private - */ -ol.layer.Vector.Property_ = { - RENDER_ORDER: 'renderOrder' -}; - -goog.provide('ol.loadingstrategy'); - - -/** - * Strategy function for loading all features with a single request. - * @param {ol.Extent} extent Extent. - * @param {number} resolution Resolution. - * @return {Array.<ol.Extent>} Extents. - * @api - */ -ol.loadingstrategy.all = function(extent, resolution) { - return [[-Infinity, -Infinity, Infinity, Infinity]]; -}; - - -/** - * Strategy function for loading features based on the view's extent and - * resolution. - * @param {ol.Extent} extent Extent. - * @param {number} resolution Resolution. - * @return {Array.<ol.Extent>} Extents. - * @api - */ -ol.loadingstrategy.bbox = function(extent, resolution) { - return [extent]; -}; - - -/** - * Creates a strategy function for loading features based on a tile grid. - * @param {ol.tilegrid.TileGrid} tileGrid Tile grid. - * @return {function(ol.Extent, number): Array.<ol.Extent>} Loading strategy. - * @api - */ -ol.loadingstrategy.tile = function(tileGrid) { - return ( - /** - * @param {ol.Extent} extent Extent. - * @param {number} resolution Resolution. - * @return {Array.<ol.Extent>} Extents. - */ - function(extent, resolution) { - var z = tileGrid.getZForResolution(resolution); - var tileRange = tileGrid.getTileRangeForExtentAndZ(extent, z); - /** @type {Array.<ol.Extent>} */ - var extents = []; - /** @type {ol.TileCoord} */ - var tileCoord = [z, 0, 0]; - for (tileCoord[1] = tileRange.minX; tileCoord[1] <= tileRange.maxX; - ++tileCoord[1]) { - for (tileCoord[2] = tileRange.minY; tileCoord[2] <= tileRange.maxY; - ++tileCoord[2]) { - extents.push(tileGrid.getTileCoordExtent(tileCoord)); - } - } - return extents; - }); -}; - -goog.provide('ol.source.Source'); - -goog.require('ol'); -goog.require('ol.Attribution'); -goog.require('ol.Object'); -goog.require('ol.proj'); -goog.require('ol.source.State'); - - -/** - * @classdesc - * Abstract base class; normally only used for creating subclasses and not - * instantiated in apps. - * Base class for {@link ol.layer.Layer} sources. - * - * A generic `change` event is triggered when the state of the source changes. - * - * @constructor - * @abstract - * @extends {ol.Object} - * @param {ol.SourceSourceOptions} options Source options. - * @api - */ -ol.source.Source = function(options) { - - ol.Object.call(this); - - /** - * @private - * @type {ol.proj.Projection} - */ - this.projection_ = ol.proj.get(options.projection); - - /** - * @private - * @type {Array.<ol.Attribution>} - */ - this.attributions_ = ol.source.Source.toAttributionsArray_(options.attributions); - - /** - * @private - * @type {string|olx.LogoOptions|undefined} - */ - this.logo_ = options.logo; - - /** - * @private - * @type {ol.source.State} - */ - this.state_ = options.state !== undefined ? - options.state : ol.source.State.READY; - - /** - * @private - * @type {boolean} - */ - this.wrapX_ = options.wrapX !== undefined ? options.wrapX : false; - -}; -ol.inherits(ol.source.Source, ol.Object); - -/** - * Turns various ways of defining an attribution to an array of `ol.Attributions`. - * - * @param {ol.AttributionLike|undefined} - * attributionLike The attributions as string, array of strings, - * `ol.Attribution`, array of `ol.Attribution` or undefined. - * @return {Array.<ol.Attribution>} The array of `ol.Attribution` or null if - * `undefined` was given. - */ -ol.source.Source.toAttributionsArray_ = function(attributionLike) { - if (typeof attributionLike === 'string') { - return [new ol.Attribution({html: attributionLike})]; - } else if (attributionLike instanceof ol.Attribution) { - return [attributionLike]; - } else if (Array.isArray(attributionLike)) { - var len = attributionLike.length; - var attributions = new Array(len); - for (var i = 0; i < len; i++) { - var item = attributionLike[i]; - if (typeof item === 'string') { - attributions[i] = new ol.Attribution({html: item}); - } else { - attributions[i] = item; - } - } - return attributions; - } else { - return null; - } -}; - - -/** - * @param {ol.Coordinate} coordinate Coordinate. - * @param {number} resolution Resolution. - * @param {number} rotation Rotation. - * @param {number} hitTolerance Hit tolerance in pixels. - * @param {Object.<string, boolean>} skippedFeatureUids Skipped feature uids. - * @param {function((ol.Feature|ol.render.Feature)): T} callback Feature - * callback. - * @return {T|undefined} Callback result. - * @template T - */ -ol.source.Source.prototype.forEachFeatureAtCoordinate = ol.nullFunction; - - -/** - * Get the attributions of the source. - * @return {Array.<ol.Attribution>} Attributions. - * @api - */ -ol.source.Source.prototype.getAttributions = function() { - return this.attributions_; -}; - - -/** - * Get the logo of the source. - * @return {string|olx.LogoOptions|undefined} Logo. - * @api - */ -ol.source.Source.prototype.getLogo = function() { - return this.logo_; -}; - - -/** - * Get the projection of the source. - * @return {ol.proj.Projection} Projection. - * @api - */ -ol.source.Source.prototype.getProjection = function() { - return this.projection_; -}; - - -/** - * @abstract - * @return {Array.<number>|undefined} Resolutions. - */ -ol.source.Source.prototype.getResolutions = function() {}; - - -/** - * Get the state of the source, see {@link ol.source.State} for possible states. - * @return {ol.source.State} State. - * @api - */ -ol.source.Source.prototype.getState = function() { - return this.state_; -}; - - -/** - * @return {boolean|undefined} Wrap X. - */ -ol.source.Source.prototype.getWrapX = function() { - return this.wrapX_; -}; - - -/** - * Refreshes the source and finally dispatches a 'change' event. - * @api - */ -ol.source.Source.prototype.refresh = function() { - this.changed(); -}; - - -/** - * Set the attributions of the source. - * @param {ol.AttributionLike|undefined} attributions Attributions. - * Can be passed as `string`, `Array<string>`, `{@link ol.Attribution}`, - * `Array<{@link ol.Attribution}>` or `undefined`. - * @api - */ -ol.source.Source.prototype.setAttributions = function(attributions) { - this.attributions_ = ol.source.Source.toAttributionsArray_(attributions); - this.changed(); -}; - - -/** - * Set the logo of the source. - * @param {string|olx.LogoOptions|undefined} logo Logo. - */ -ol.source.Source.prototype.setLogo = function(logo) { - this.logo_ = logo; -}; - - -/** - * Set the state of the source. - * @param {ol.source.State} state State. - * @protected - */ -ol.source.Source.prototype.setState = function(state) { - this.state_ = state; - this.changed(); -}; - -goog.provide('ol.source.VectorEventType'); - -/** - * @enum {string} - */ -ol.source.VectorEventType = { - /** - * Triggered when a feature is added to the source. - * @event ol.source.Vector.Event#addfeature - * @api - */ - ADDFEATURE: 'addfeature', - - /** - * Triggered when a feature is updated. - * @event ol.source.Vector.Event#changefeature - * @api - */ - CHANGEFEATURE: 'changefeature', - - /** - * Triggered when the clear method is called on the source. - * @event ol.source.Vector.Event#clear - * @api - */ - CLEAR: 'clear', - - /** - * Triggered when a feature is removed from the source. - * See {@link ol.source.Vector#clear source.clear()} for exceptions. - * @event ol.source.Vector.Event#removefeature - * @api - */ - REMOVEFEATURE: 'removefeature' -}; - - -/** - * @fileoverview - * @suppress {accessControls, ambiguousFunctionDecl, checkDebuggerStatement, checkRegExp, checkTypes, checkVars, const, constantProperty, deprecated, duplicate, es5Strict, fileoverviewTags, missingProperties, nonStandardJsDocs, strictModuleDepCheck, suspiciousCode, undefinedNames, undefinedVars, unknownDefines, unusedLocalVariables, uselessCode, visibility} - */ -goog.provide('ol.ext.rbush'); - -/** @typedef {function(*)} */ -ol.ext.rbush = function() {}; - -(function() {(function (exports) { -'use strict'; - -'use strict'; -var quickselect = partialSort; -function partialSort(arr, k, left, right, compare) { - left = left || 0; - right = right || (arr.length - 1); - compare = compare || defaultCompare; - while (right > left) { - if (right - left > 600) { - var n = right - left + 1; - var m = k - left + 1; - var z = Math.log(n); - var s = 0.5 * Math.exp(2 * z / 3); - var sd = 0.5 * Math.sqrt(z * s * (n - s) / n) * (m - n / 2 < 0 ? -1 : 1); - var newLeft = Math.max(left, Math.floor(k - m * s / n + sd)); - var newRight = Math.min(right, Math.floor(k + (n - m) * s / n + sd)); - partialSort(arr, k, newLeft, newRight, compare); - } - var t = arr[k]; - var i = left; - var j = right; - swap(arr, left, k); - if (compare(arr[right], t) > 0) swap(arr, left, right); - while (i < j) { - swap(arr, i, j); - i++; - j--; - while (compare(arr[i], t) < 0) i++; - while (compare(arr[j], t) > 0) j--; - } - if (compare(arr[left], t) === 0) swap(arr, left, j); - else { - j++; - swap(arr, j, right); - } - if (j <= k) left = j + 1; - if (k <= j) right = j - 1; - } -} -function swap(arr, i, j) { - var tmp = arr[i]; - arr[i] = arr[j]; - arr[j] = tmp; -} -function defaultCompare(a, b) { - return a < b ? -1 : a > b ? 1 : 0; -} - -'use strict'; -var rbush_1 = rbush; -function rbush(maxEntries, format) { - if (!(this instanceof rbush)) return new rbush(maxEntries, format); - this._maxEntries = Math.max(4, maxEntries || 9); - this._minEntries = Math.max(2, Math.ceil(this._maxEntries * 0.4)); - if (format) { - this._initFormat(format); - } - this.clear(); -} -rbush.prototype = { - all: function () { - return this._all(this.data, []); - }, - search: function (bbox) { - var node = this.data, - result = [], - toBBox = this.toBBox; - if (!intersects(bbox, node)) return result; - var nodesToSearch = [], - i, len, child, childBBox; - while (node) { - for (i = 0, len = node.children.length; i < len; i++) { - child = node.children[i]; - childBBox = node.leaf ? toBBox(child) : child; - if (intersects(bbox, childBBox)) { - if (node.leaf) result.push(child); - else if (contains(bbox, childBBox)) this._all(child, result); - else nodesToSearch.push(child); - } - } - node = nodesToSearch.pop(); - } - return result; - }, - collides: function (bbox) { - var node = this.data, - toBBox = this.toBBox; - if (!intersects(bbox, node)) return false; - var nodesToSearch = [], - i, len, child, childBBox; - while (node) { - for (i = 0, len = node.children.length; i < len; i++) { - child = node.children[i]; - childBBox = node.leaf ? toBBox(child) : child; - if (intersects(bbox, childBBox)) { - if (node.leaf || contains(bbox, childBBox)) return true; - nodesToSearch.push(child); - } - } - node = nodesToSearch.pop(); - } - return false; - }, - load: function (data) { - if (!(data && data.length)) return this; - if (data.length < this._minEntries) { - for (var i = 0, len = data.length; i < len; i++) { - this.insert(data[i]); - } - return this; - } - var node = this._build(data.slice(), 0, data.length - 1, 0); - if (!this.data.children.length) { - this.data = node; - } else if (this.data.height === node.height) { - this._splitRoot(this.data, node); - } else { - if (this.data.height < node.height) { - var tmpNode = this.data; - this.data = node; - node = tmpNode; - } - this._insert(node, this.data.height - node.height - 1, true); - } - return this; - }, - insert: function (item) { - if (item) this._insert(item, this.data.height - 1); - return this; - }, - clear: function () { - this.data = createNode([]); - return this; - }, - remove: function (item, equalsFn) { - if (!item) return this; - var node = this.data, - bbox = this.toBBox(item), - path = [], - indexes = [], - i, parent, index, goingUp; - while (node || path.length) { - if (!node) { - node = path.pop(); - parent = path[path.length - 1]; - i = indexes.pop(); - goingUp = true; - } - if (node.leaf) { - index = findItem(item, node.children, equalsFn); - if (index !== -1) { - node.children.splice(index, 1); - path.push(node); - this._condense(path); - return this; - } - } - if (!goingUp && !node.leaf && contains(node, bbox)) { - path.push(node); - indexes.push(i); - i = 0; - parent = node; - node = node.children[0]; - } else if (parent) { - i++; - node = parent.children[i]; - goingUp = false; - } else node = null; - } - return this; - }, - toBBox: function (item) { return item; }, - compareMinX: compareNodeMinX, - compareMinY: compareNodeMinY, - toJSON: function () { return this.data; }, - fromJSON: function (data) { - this.data = data; - return this; - }, - _all: function (node, result) { - var nodesToSearch = []; - while (node) { - if (node.leaf) result.push.apply(result, node.children); - else nodesToSearch.push.apply(nodesToSearch, node.children); - node = nodesToSearch.pop(); - } - return result; - }, - _build: function (items, left, right, height) { - var N = right - left + 1, - M = this._maxEntries, - node; - if (N <= M) { - node = createNode(items.slice(left, right + 1)); - calcBBox(node, this.toBBox); - return node; - } - if (!height) { - height = Math.ceil(Math.log(N) / Math.log(M)); - M = Math.ceil(N / Math.pow(M, height - 1)); - } - node = createNode([]); - node.leaf = false; - node.height = height; - var N2 = Math.ceil(N / M), - N1 = N2 * Math.ceil(Math.sqrt(M)), - i, j, right2, right3; - multiSelect(items, left, right, N1, this.compareMinX); - for (i = left; i <= right; i += N1) { - right2 = Math.min(i + N1 - 1, right); - multiSelect(items, i, right2, N2, this.compareMinY); - for (j = i; j <= right2; j += N2) { - right3 = Math.min(j + N2 - 1, right2); - node.children.push(this._build(items, j, right3, height - 1)); - } - } - calcBBox(node, this.toBBox); - return node; - }, - _chooseSubtree: function (bbox, node, level, path) { - var i, len, child, targetNode, area, enlargement, minArea, minEnlargement; - while (true) { - path.push(node); - if (node.leaf || path.length - 1 === level) break; - minArea = minEnlargement = Infinity; - for (i = 0, len = node.children.length; i < len; i++) { - child = node.children[i]; - area = bboxArea(child); - enlargement = enlargedArea(bbox, child) - area; - if (enlargement < minEnlargement) { - minEnlargement = enlargement; - minArea = area < minArea ? area : minArea; - targetNode = child; - } else if (enlargement === minEnlargement) { - if (area < minArea) { - minArea = area; - targetNode = child; - } - } - } - node = targetNode || node.children[0]; - } - return node; - }, - _insert: function (item, level, isNode) { - var toBBox = this.toBBox, - bbox = isNode ? item : toBBox(item), - insertPath = []; - var node = this._chooseSubtree(bbox, this.data, level, insertPath); - node.children.push(item); - extend(node, bbox); - while (level >= 0) { - if (insertPath[level].children.length > this._maxEntries) { - this._split(insertPath, level); - level--; - } else break; - } - this._adjustParentBBoxes(bbox, insertPath, level); - }, - _split: function (insertPath, level) { - var node = insertPath[level], - M = node.children.length, - m = this._minEntries; - this._chooseSplitAxis(node, m, M); - var splitIndex = this._chooseSplitIndex(node, m, M); - var newNode = createNode(node.children.splice(splitIndex, node.children.length - splitIndex)); - newNode.height = node.height; - newNode.leaf = node.leaf; - calcBBox(node, this.toBBox); - calcBBox(newNode, this.toBBox); - if (level) insertPath[level - 1].children.push(newNode); - else this._splitRoot(node, newNode); - }, - _splitRoot: function (node, newNode) { - this.data = createNode([node, newNode]); - this.data.height = node.height + 1; - this.data.leaf = false; - calcBBox(this.data, this.toBBox); - }, - _chooseSplitIndex: function (node, m, M) { - var i, bbox1, bbox2, overlap, area, minOverlap, minArea, index; - minOverlap = minArea = Infinity; - for (i = m; i <= M - m; i++) { - bbox1 = distBBox(node, 0, i, this.toBBox); - bbox2 = distBBox(node, i, M, this.toBBox); - overlap = intersectionArea(bbox1, bbox2); - area = bboxArea(bbox1) + bboxArea(bbox2); - if (overlap < minOverlap) { - minOverlap = overlap; - index = i; - minArea = area < minArea ? area : minArea; - } else if (overlap === minOverlap) { - if (area < minArea) { - minArea = area; - index = i; - } - } - } - return index; - }, - _chooseSplitAxis: function (node, m, M) { - var compareMinX = node.leaf ? this.compareMinX : compareNodeMinX, - compareMinY = node.leaf ? this.compareMinY : compareNodeMinY, - xMargin = this._allDistMargin(node, m, M, compareMinX), - yMargin = this._allDistMargin(node, m, M, compareMinY); - if (xMargin < yMargin) node.children.sort(compareMinX); - }, - _allDistMargin: function (node, m, M, compare) { - node.children.sort(compare); - var toBBox = this.toBBox, - leftBBox = distBBox(node, 0, m, toBBox), - rightBBox = distBBox(node, M - m, M, toBBox), - margin = bboxMargin(leftBBox) + bboxMargin(rightBBox), - i, child; - for (i = m; i < M - m; i++) { - child = node.children[i]; - extend(leftBBox, node.leaf ? toBBox(child) : child); - margin += bboxMargin(leftBBox); - } - for (i = M - m - 1; i >= m; i--) { - child = node.children[i]; - extend(rightBBox, node.leaf ? toBBox(child) : child); - margin += bboxMargin(rightBBox); - } - return margin; - }, - _adjustParentBBoxes: function (bbox, path, level) { - for (var i = level; i >= 0; i--) { - extend(path[i], bbox); - } - }, - _condense: function (path) { - for (var i = path.length - 1, siblings; i >= 0; i--) { - if (path[i].children.length === 0) { - if (i > 0) { - siblings = path[i - 1].children; - siblings.splice(siblings.indexOf(path[i]), 1); - } else this.clear(); - } else calcBBox(path[i], this.toBBox); - } - }, - _initFormat: function (format) { - var compareArr = ['return a', ' - b', ';']; - this.compareMinX = new Function('a', 'b', compareArr.join(format[0])); - this.compareMinY = new Function('a', 'b', compareArr.join(format[1])); - this.toBBox = new Function('a', - 'return {minX: a' + format[0] + - ', minY: a' + format[1] + - ', maxX: a' + format[2] + - ', maxY: a' + format[3] + '};'); - } -}; -function findItem(item, items, equalsFn) { - if (!equalsFn) return items.indexOf(item); - for (var i = 0; i < items.length; i++) { - if (equalsFn(item, items[i])) return i; - } - return -1; -} -function calcBBox(node, toBBox) { - distBBox(node, 0, node.children.length, toBBox, node); -} -function distBBox(node, k, p, toBBox, destNode) { - if (!destNode) destNode = createNode(null); - destNode.minX = Infinity; - destNode.minY = Infinity; - destNode.maxX = -Infinity; - destNode.maxY = -Infinity; - for (var i = k, child; i < p; i++) { - child = node.children[i]; - extend(destNode, node.leaf ? toBBox(child) : child); - } - return destNode; -} -function extend(a, b) { - a.minX = Math.min(a.minX, b.minX); - a.minY = Math.min(a.minY, b.minY); - a.maxX = Math.max(a.maxX, b.maxX); - a.maxY = Math.max(a.maxY, b.maxY); - return a; -} -function compareNodeMinX(a, b) { return a.minX - b.minX; } -function compareNodeMinY(a, b) { return a.minY - b.minY; } -function bboxArea(a) { return (a.maxX - a.minX) * (a.maxY - a.minY); } -function bboxMargin(a) { return (a.maxX - a.minX) + (a.maxY - a.minY); } -function enlargedArea(a, b) { - return (Math.max(b.maxX, a.maxX) - Math.min(b.minX, a.minX)) * - (Math.max(b.maxY, a.maxY) - Math.min(b.minY, a.minY)); -} -function intersectionArea(a, b) { - var minX = Math.max(a.minX, b.minX), - minY = Math.max(a.minY, b.minY), - maxX = Math.min(a.maxX, b.maxX), - maxY = Math.min(a.maxY, b.maxY); - return Math.max(0, maxX - minX) * - Math.max(0, maxY - minY); -} -function contains(a, b) { - return a.minX <= b.minX && - a.minY <= b.minY && - b.maxX <= a.maxX && - b.maxY <= a.maxY; -} -function intersects(a, b) { - return b.minX <= a.maxX && - b.minY <= a.maxY && - b.maxX >= a.minX && - b.maxY >= a.minY; -} -function createNode(children) { - return { - children: children, - height: 1, - leaf: true, - minX: Infinity, - minY: Infinity, - maxX: -Infinity, - maxY: -Infinity - }; -} -function multiSelect(arr, left, right, n, compare) { - var stack = [left, right], - mid; - while (stack.length) { - right = stack.pop(); - left = stack.pop(); - if (right - left <= n) continue; - mid = left + Math.ceil((right - left) / n / 2) * n; - quickselect(arr, mid, left, right, compare); - stack.push(left, mid, mid, right); - } -} - -exports['default'] = rbush_1; - -}((this.rbush = this.rbush || {})));}).call(ol.ext); -ol.ext.rbush = ol.ext.rbush.default; - -goog.provide('ol.structs.RBush'); - -goog.require('ol'); -goog.require('ol.ext.rbush'); -goog.require('ol.extent'); -goog.require('ol.obj'); - - -/** - * Wrapper around the RBush by Vladimir Agafonkin. - * - * @constructor - * @param {number=} opt_maxEntries Max entries. - * @see https://github.com/mourner/rbush - * @struct - * @template T - */ -ol.structs.RBush = function(opt_maxEntries) { - - /** - * @private - */ - this.rbush_ = ol.ext.rbush(opt_maxEntries); - - /** - * A mapping between the objects added to this rbush wrapper - * and the objects that are actually added to the internal rbush. - * @private - * @type {Object.<number, ol.RBushEntry>} - */ - this.items_ = {}; - -}; - - -/** - * Insert a value into the RBush. - * @param {ol.Extent} extent Extent. - * @param {T} value Value. - */ -ol.structs.RBush.prototype.insert = function(extent, value) { - /** @type {ol.RBushEntry} */ - var item = { - minX: extent[0], - minY: extent[1], - maxX: extent[2], - maxY: extent[3], - value: value - }; - - this.rbush_.insert(item); - this.items_[ol.getUid(value)] = item; -}; - - -/** - * Bulk-insert values into the RBush. - * @param {Array.<ol.Extent>} extents Extents. - * @param {Array.<T>} values Values. - */ -ol.structs.RBush.prototype.load = function(extents, values) { - var items = new Array(values.length); - for (var i = 0, l = values.length; i < l; i++) { - var extent = extents[i]; - var value = values[i]; - - /** @type {ol.RBushEntry} */ - var item = { - minX: extent[0], - minY: extent[1], - maxX: extent[2], - maxY: extent[3], - value: value - }; - items[i] = item; - this.items_[ol.getUid(value)] = item; - } - this.rbush_.load(items); -}; - - -/** - * Remove a value from the RBush. - * @param {T} value Value. - * @return {boolean} Removed. - */ -ol.structs.RBush.prototype.remove = function(value) { - var uid = ol.getUid(value); - - // get the object in which the value was wrapped when adding to the - // internal rbush. then use that object to do the removal. - var item = this.items_[uid]; - delete this.items_[uid]; - return this.rbush_.remove(item) !== null; -}; - - -/** - * Update the extent of a value in the RBush. - * @param {ol.Extent} extent Extent. - * @param {T} value Value. - */ -ol.structs.RBush.prototype.update = function(extent, value) { - var item = this.items_[ol.getUid(value)]; - var bbox = [item.minX, item.minY, item.maxX, item.maxY]; - if (!ol.extent.equals(bbox, extent)) { - this.remove(value); - this.insert(extent, value); - } -}; - - -/** - * Return all values in the RBush. - * @return {Array.<T>} All. - */ -ol.structs.RBush.prototype.getAll = function() { - var items = this.rbush_.all(); - return items.map(function(item) { - return item.value; - }); -}; - - -/** - * Return all values in the given extent. - * @param {ol.Extent} extent Extent. - * @return {Array.<T>} All in extent. - */ -ol.structs.RBush.prototype.getInExtent = function(extent) { - /** @type {ol.RBushEntry} */ - var bbox = { - minX: extent[0], - minY: extent[1], - maxX: extent[2], - maxY: extent[3] - }; - var items = this.rbush_.search(bbox); - return items.map(function(item) { - return item.value; - }); -}; - - -/** - * Calls a callback function with each value in the tree. - * If the callback returns a truthy value, this value is returned without - * checking the rest of the tree. - * @param {function(this: S, T): *} callback Callback. - * @param {S=} opt_this The object to use as `this` in `callback`. - * @return {*} Callback return value. - * @template S - */ -ol.structs.RBush.prototype.forEach = function(callback, opt_this) { - return this.forEach_(this.getAll(), callback, opt_this); -}; - - -/** - * Calls a callback function with each value in the provided extent. - * @param {ol.Extent} extent Extent. - * @param {function(this: S, T): *} callback Callback. - * @param {S=} opt_this The object to use as `this` in `callback`. - * @return {*} Callback return value. - * @template S - */ -ol.structs.RBush.prototype.forEachInExtent = function(extent, callback, opt_this) { - return this.forEach_(this.getInExtent(extent), callback, opt_this); -}; - - -/** - * @param {Array.<T>} values Values. - * @param {function(this: S, T): *} callback Callback. - * @param {S=} opt_this The object to use as `this` in `callback`. - * @private - * @return {*} Callback return value. - * @template S - */ -ol.structs.RBush.prototype.forEach_ = function(values, callback, opt_this) { - var result; - for (var i = 0, l = values.length; i < l; i++) { - result = callback.call(opt_this, values[i]); - if (result) { - return result; - } - } - return result; -}; - - -/** - * @return {boolean} Is empty. - */ -ol.structs.RBush.prototype.isEmpty = function() { - return ol.obj.isEmpty(this.items_); -}; - - -/** - * Remove all values from the RBush. - */ -ol.structs.RBush.prototype.clear = function() { - this.rbush_.clear(); - this.items_ = {}; -}; - - -/** - * @param {ol.Extent=} opt_extent Extent. - * @return {ol.Extent} Extent. - */ -ol.structs.RBush.prototype.getExtent = function(opt_extent) { - // FIXME add getExtent() to rbush - var data = this.rbush_.data; - return ol.extent.createOrUpdate(data.minX, data.minY, data.maxX, data.maxY, opt_extent); -}; - - -/** - * @param {ol.structs.RBush} rbush R-Tree. - */ -ol.structs.RBush.prototype.concat = function(rbush) { - this.rbush_.load(rbush.rbush_.all()); - for (var i in rbush.items_) { - this.items_[i | 0] = rbush.items_[i | 0]; - } -}; - -// FIXME bulk feature upload - suppress events -// FIXME make change-detection more refined (notably, geometry hint) - -goog.provide('ol.source.Vector'); - -goog.require('ol'); -goog.require('ol.Collection'); -goog.require('ol.CollectionEventType'); -goog.require('ol.ObjectEventType'); -goog.require('ol.array'); -goog.require('ol.asserts'); -goog.require('ol.events'); -goog.require('ol.events.Event'); -goog.require('ol.events.EventType'); -goog.require('ol.extent'); -goog.require('ol.featureloader'); -goog.require('ol.functions'); -goog.require('ol.loadingstrategy'); -goog.require('ol.obj'); -goog.require('ol.source.Source'); -goog.require('ol.source.State'); -goog.require('ol.source.VectorEventType'); -goog.require('ol.structs.RBush'); - - -/** - * @classdesc - * Provides a source of features for vector layers. Vector features provided - * by this source are suitable for editing. See {@link ol.source.VectorTile} for - * vector data that is optimized for rendering. - * - * @constructor - * @extends {ol.source.Source} - * @fires ol.source.Vector.Event - * @param {olx.source.VectorOptions=} opt_options Vector source options. - * @api - */ -ol.source.Vector = function(opt_options) { - - var options = opt_options || {}; - - ol.source.Source.call(this, { - attributions: options.attributions, - logo: options.logo, - projection: undefined, - state: ol.source.State.READY, - wrapX: options.wrapX !== undefined ? options.wrapX : true - }); - - /** - * @private - * @type {ol.FeatureLoader} - */ - this.loader_ = ol.nullFunction; - - /** - * @private - * @type {ol.format.Feature|undefined} - */ - this.format_ = options.format; - - /** - * @private - * @type {boolean} - */ - this.overlaps_ = options.overlaps == undefined ? true : options.overlaps; - - /** - * @private - * @type {string|ol.FeatureUrlFunction|undefined} - */ - this.url_ = options.url; - - if (options.loader !== undefined) { - this.loader_ = options.loader; - } else if (this.url_ !== undefined) { - ol.asserts.assert(this.format_, 7); // `format` must be set when `url` is set - // create a XHR feature loader for "url" and "format" - this.loader_ = ol.featureloader.xhr(this.url_, /** @type {ol.format.Feature} */ (this.format_)); - } - - /** - * @private - * @type {ol.LoadingStrategy} - */ - this.strategy_ = options.strategy !== undefined ? options.strategy : - ol.loadingstrategy.all; - - var useSpatialIndex = - options.useSpatialIndex !== undefined ? options.useSpatialIndex : true; - - /** - * @private - * @type {ol.structs.RBush.<ol.Feature>} - */ - this.featuresRtree_ = useSpatialIndex ? new ol.structs.RBush() : null; - - /** - * @private - * @type {ol.structs.RBush.<{extent: ol.Extent}>} - */ - this.loadedExtentsRtree_ = new ol.structs.RBush(); - - /** - * @private - * @type {Object.<string, ol.Feature>} - */ - this.nullGeometryFeatures_ = {}; - - /** - * A lookup of features by id (the return from feature.getId()). - * @private - * @type {Object.<string, ol.Feature>} - */ - this.idIndex_ = {}; - - /** - * A lookup of features without id (keyed by ol.getUid(feature)). - * @private - * @type {Object.<string, ol.Feature>} - */ - this.undefIdIndex_ = {}; - - /** - * @private - * @type {Object.<string, Array.<ol.EventsKey>>} - */ - this.featureChangeKeys_ = {}; - - /** - * @private - * @type {ol.Collection.<ol.Feature>} - */ - this.featuresCollection_ = null; - - var collection, features; - if (options.features instanceof ol.Collection) { - collection = options.features; - features = collection.getArray(); - } else if (Array.isArray(options.features)) { - features = options.features; - } - if (!useSpatialIndex && collection === undefined) { - collection = new ol.Collection(features); - } - if (features !== undefined) { - this.addFeaturesInternal(features); - } - if (collection !== undefined) { - this.bindFeaturesCollection_(collection); - } - -}; -ol.inherits(ol.source.Vector, ol.source.Source); - - -/** - * Add a single feature to the source. If you want to add a batch of features - * at once, call {@link ol.source.Vector#addFeatures source.addFeatures()} - * instead. A feature will not be added to the source if feature with - * the same id is already there. The reason for this behavior is to avoid - * feature duplication when using bbox or tile loading strategies. - * @param {ol.Feature} feature Feature to add. - * @api - */ -ol.source.Vector.prototype.addFeature = function(feature) { - this.addFeatureInternal(feature); - this.changed(); -}; - - -/** - * Add a feature without firing a `change` event. - * @param {ol.Feature} feature Feature. - * @protected - */ -ol.source.Vector.prototype.addFeatureInternal = function(feature) { - var featureKey = ol.getUid(feature).toString(); - - if (!this.addToIndex_(featureKey, feature)) { - return; - } - - this.setupChangeEvents_(featureKey, feature); - - var geometry = feature.getGeometry(); - if (geometry) { - var extent = geometry.getExtent(); - if (this.featuresRtree_) { - this.featuresRtree_.insert(extent, feature); - } - } else { - this.nullGeometryFeatures_[featureKey] = feature; - } - - this.dispatchEvent( - new ol.source.Vector.Event(ol.source.VectorEventType.ADDFEATURE, feature)); -}; - - -/** - * @param {string} featureKey Unique identifier for the feature. - * @param {ol.Feature} feature The feature. - * @private - */ -ol.source.Vector.prototype.setupChangeEvents_ = function(featureKey, feature) { - this.featureChangeKeys_[featureKey] = [ - ol.events.listen(feature, ol.events.EventType.CHANGE, - this.handleFeatureChange_, this), - ol.events.listen(feature, ol.ObjectEventType.PROPERTYCHANGE, - this.handleFeatureChange_, this) - ]; -}; - - -/** - * @param {string} featureKey Unique identifier for the feature. - * @param {ol.Feature} feature The feature. - * @return {boolean} The feature is "valid", in the sense that it is also a - * candidate for insertion into the Rtree. - * @private - */ -ol.source.Vector.prototype.addToIndex_ = function(featureKey, feature) { - var valid = true; - var id = feature.getId(); - if (id !== undefined) { - if (!(id.toString() in this.idIndex_)) { - this.idIndex_[id.toString()] = feature; - } else { - valid = false; - } - } else { - ol.asserts.assert(!(featureKey in this.undefIdIndex_), - 30); // The passed `feature` was already added to the source - this.undefIdIndex_[featureKey] = feature; - } - return valid; -}; - - -/** - * Add a batch of features to the source. - * @param {Array.<ol.Feature>} features Features to add. - * @api - */ -ol.source.Vector.prototype.addFeatures = function(features) { - this.addFeaturesInternal(features); - this.changed(); -}; - - -/** - * Add features without firing a `change` event. - * @param {Array.<ol.Feature>} features Features. - * @protected - */ -ol.source.Vector.prototype.addFeaturesInternal = function(features) { - var featureKey, i, length, feature; - - var extents = []; - var newFeatures = []; - var geometryFeatures = []; - - for (i = 0, length = features.length; i < length; i++) { - feature = features[i]; - featureKey = ol.getUid(feature).toString(); - if (this.addToIndex_(featureKey, feature)) { - newFeatures.push(feature); - } - } - - for (i = 0, length = newFeatures.length; i < length; i++) { - feature = newFeatures[i]; - featureKey = ol.getUid(feature).toString(); - this.setupChangeEvents_(featureKey, feature); - - var geometry = feature.getGeometry(); - if (geometry) { - var extent = geometry.getExtent(); - extents.push(extent); - geometryFeatures.push(feature); - } else { - this.nullGeometryFeatures_[featureKey] = feature; - } - } - if (this.featuresRtree_) { - this.featuresRtree_.load(extents, geometryFeatures); - } - - for (i = 0, length = newFeatures.length; i < length; i++) { - this.dispatchEvent(new ol.source.Vector.Event( - ol.source.VectorEventType.ADDFEATURE, newFeatures[i])); - } -}; - - -/** - * @param {!ol.Collection.<ol.Feature>} collection Collection. - * @private - */ -ol.source.Vector.prototype.bindFeaturesCollection_ = function(collection) { - var modifyingCollection = false; - ol.events.listen(this, ol.source.VectorEventType.ADDFEATURE, - function(evt) { - if (!modifyingCollection) { - modifyingCollection = true; - collection.push(evt.feature); - modifyingCollection = false; - } - }); - ol.events.listen(this, ol.source.VectorEventType.REMOVEFEATURE, - function(evt) { - if (!modifyingCollection) { - modifyingCollection = true; - collection.remove(evt.feature); - modifyingCollection = false; - } - }); - ol.events.listen(collection, ol.CollectionEventType.ADD, - function(evt) { - if (!modifyingCollection) { - modifyingCollection = true; - this.addFeature(/** @type {ol.Feature} */ (evt.element)); - modifyingCollection = false; - } - }, this); - ol.events.listen(collection, ol.CollectionEventType.REMOVE, - function(evt) { - if (!modifyingCollection) { - modifyingCollection = true; - this.removeFeature(/** @type {ol.Feature} */ (evt.element)); - modifyingCollection = false; - } - }, this); - this.featuresCollection_ = collection; -}; - - -/** - * Remove all features from the source. - * @param {boolean=} opt_fast Skip dispatching of {@link removefeature} events. - * @api - */ -ol.source.Vector.prototype.clear = function(opt_fast) { - if (opt_fast) { - for (var featureId in this.featureChangeKeys_) { - var keys = this.featureChangeKeys_[featureId]; - keys.forEach(ol.events.unlistenByKey); - } - if (!this.featuresCollection_) { - this.featureChangeKeys_ = {}; - this.idIndex_ = {}; - this.undefIdIndex_ = {}; - } - } else { - if (this.featuresRtree_) { - this.featuresRtree_.forEach(this.removeFeatureInternal, this); - for (var id in this.nullGeometryFeatures_) { - this.removeFeatureInternal(this.nullGeometryFeatures_[id]); - } - } - } - if (this.featuresCollection_) { - this.featuresCollection_.clear(); - } - - if (this.featuresRtree_) { - this.featuresRtree_.clear(); - } - this.loadedExtentsRtree_.clear(); - this.nullGeometryFeatures_ = {}; - - var clearEvent = new ol.source.Vector.Event(ol.source.VectorEventType.CLEAR); - this.dispatchEvent(clearEvent); - this.changed(); -}; - - -/** - * Iterate through all features on the source, calling the provided callback - * with each one. If the callback returns any "truthy" value, iteration will - * stop and the function will return the same value. - * - * @param {function(this: T, ol.Feature): S} callback Called with each feature - * on the source. Return a truthy value to stop iteration. - * @param {T=} opt_this The object to use as `this` in the callback. - * @return {S|undefined} The return value from the last call to the callback. - * @template T,S - * @api - */ -ol.source.Vector.prototype.forEachFeature = function(callback, opt_this) { - if (this.featuresRtree_) { - return this.featuresRtree_.forEach(callback, opt_this); - } else if (this.featuresCollection_) { - return this.featuresCollection_.forEach(callback, opt_this); - } -}; - - -/** - * Iterate through all features whose geometries contain the provided - * coordinate, calling the callback with each feature. If the callback returns - * a "truthy" value, iteration will stop and the function will return the same - * value. - * - * @param {ol.Coordinate} coordinate Coordinate. - * @param {function(this: T, ol.Feature): S} callback Called with each feature - * whose goemetry contains the provided coordinate. - * @param {T=} opt_this The object to use as `this` in the callback. - * @return {S|undefined} The return value from the last call to the callback. - * @template T,S - */ -ol.source.Vector.prototype.forEachFeatureAtCoordinateDirect = function(coordinate, callback, opt_this) { - var extent = [coordinate[0], coordinate[1], coordinate[0], coordinate[1]]; - return this.forEachFeatureInExtent(extent, function(feature) { - var geometry = feature.getGeometry(); - if (geometry.intersectsCoordinate(coordinate)) { - return callback.call(opt_this, feature); - } else { - return undefined; - } - }); -}; - - -/** - * Iterate through all features whose bounding box intersects the provided - * extent (note that the feature's geometry may not intersect the extent), - * calling the callback with each feature. If the callback returns a "truthy" - * value, iteration will stop and the function will return the same value. - * - * If you are interested in features whose geometry intersects an extent, call - * the {@link ol.source.Vector#forEachFeatureIntersectingExtent - * source.forEachFeatureIntersectingExtent()} method instead. - * - * When `useSpatialIndex` is set to false, this method will loop through all - * features, equivalent to {@link ol.source.Vector#forEachFeature}. - * - * @param {ol.Extent} extent Extent. - * @param {function(this: T, ol.Feature): S} callback Called with each feature - * whose bounding box intersects the provided extent. - * @param {T=} opt_this The object to use as `this` in the callback. - * @return {S|undefined} The return value from the last call to the callback. - * @template T,S - * @api - */ -ol.source.Vector.prototype.forEachFeatureInExtent = function(extent, callback, opt_this) { - if (this.featuresRtree_) { - return this.featuresRtree_.forEachInExtent(extent, callback, opt_this); - } else if (this.featuresCollection_) { - return this.featuresCollection_.forEach(callback, opt_this); - } -}; - - -/** - * Iterate through all features whose geometry intersects the provided extent, - * calling the callback with each feature. If the callback returns a "truthy" - * value, iteration will stop and the function will return the same value. - * - * If you only want to test for bounding box intersection, call the - * {@link ol.source.Vector#forEachFeatureInExtent - * source.forEachFeatureInExtent()} method instead. - * - * @param {ol.Extent} extent Extent. - * @param {function(this: T, ol.Feature): S} callback Called with each feature - * whose geometry intersects the provided extent. - * @param {T=} opt_this The object to use as `this` in the callback. - * @return {S|undefined} The return value from the last call to the callback. - * @template T,S - * @api - */ -ol.source.Vector.prototype.forEachFeatureIntersectingExtent = function(extent, callback, opt_this) { - return this.forEachFeatureInExtent(extent, - /** - * @param {ol.Feature} feature Feature. - * @return {S|undefined} The return value from the last call to the callback. - * @template S - */ - function(feature) { - var geometry = feature.getGeometry(); - if (geometry.intersectsExtent(extent)) { - var result = callback.call(opt_this, feature); - if (result) { - return result; - } - } - }); -}; - - -/** - * Get the features collection associated with this source. Will be `null` - * unless the source was configured with `useSpatialIndex` set to `false`, or - * with an {@link ol.Collection} as `features`. - * @return {ol.Collection.<ol.Feature>} The collection of features. - * @api - */ -ol.source.Vector.prototype.getFeaturesCollection = function() { - return this.featuresCollection_; -}; - - -/** - * Get all features on the source in random order. - * @return {Array.<ol.Feature>} Features. - * @api - */ -ol.source.Vector.prototype.getFeatures = function() { - var features; - if (this.featuresCollection_) { - features = this.featuresCollection_.getArray(); - } else if (this.featuresRtree_) { - features = this.featuresRtree_.getAll(); - if (!ol.obj.isEmpty(this.nullGeometryFeatures_)) { - ol.array.extend( - features, ol.obj.getValues(this.nullGeometryFeatures_)); - } - } - return /** @type {Array.<ol.Feature>} */ (features); -}; - - -/** - * Get all features whose geometry intersects the provided coordinate. - * @param {ol.Coordinate} coordinate Coordinate. - * @return {Array.<ol.Feature>} Features. - * @api - */ -ol.source.Vector.prototype.getFeaturesAtCoordinate = function(coordinate) { - var features = []; - this.forEachFeatureAtCoordinateDirect(coordinate, function(feature) { - features.push(feature); - }); - return features; -}; - - -/** - * Get all features in the provided extent. Note that this returns an array of - * all features intersecting the given extent in random order (so it may include - * features whose geometries do not intersect the extent). - * - * This method is not available when the source is configured with - * `useSpatialIndex` set to `false`. - * @param {ol.Extent} extent Extent. - * @return {Array.<ol.Feature>} Features. - * @api - */ -ol.source.Vector.prototype.getFeaturesInExtent = function(extent) { - return this.featuresRtree_.getInExtent(extent); -}; - - -/** - * Get the closest feature to the provided coordinate. - * - * This method is not available when the source is configured with - * `useSpatialIndex` set to `false`. - * @param {ol.Coordinate} coordinate Coordinate. - * @param {function(ol.Feature):boolean=} opt_filter Feature filter function. - * The filter function will receive one argument, the {@link ol.Feature feature} - * and it should return a boolean value. By default, no filtering is made. - * @return {ol.Feature} Closest feature. - * @api - */ -ol.source.Vector.prototype.getClosestFeatureToCoordinate = function(coordinate, opt_filter) { - // Find the closest feature using branch and bound. We start searching an - // infinite extent, and find the distance from the first feature found. This - // becomes the closest feature. We then compute a smaller extent which any - // closer feature must intersect. We continue searching with this smaller - // extent, trying to find a closer feature. Every time we find a closer - // feature, we update the extent being searched so that any even closer - // feature must intersect it. We continue until we run out of features. - var x = coordinate[0]; - var y = coordinate[1]; - var closestFeature = null; - var closestPoint = [NaN, NaN]; - var minSquaredDistance = Infinity; - var extent = [-Infinity, -Infinity, Infinity, Infinity]; - var filter = opt_filter ? opt_filter : ol.functions.TRUE; - this.featuresRtree_.forEachInExtent(extent, - /** - * @param {ol.Feature} feature Feature. - */ - function(feature) { - if (filter(feature)) { - var geometry = feature.getGeometry(); - var previousMinSquaredDistance = minSquaredDistance; - minSquaredDistance = geometry.closestPointXY( - x, y, closestPoint, minSquaredDistance); - if (minSquaredDistance < previousMinSquaredDistance) { - closestFeature = feature; - // This is sneaky. Reduce the extent that it is currently being - // searched while the R-Tree traversal using this same extent object - // is still in progress. This is safe because the new extent is - // strictly contained by the old extent. - var minDistance = Math.sqrt(minSquaredDistance); - extent[0] = x - minDistance; - extent[1] = y - minDistance; - extent[2] = x + minDistance; - extent[3] = y + minDistance; - } - } - }); - return closestFeature; -}; - - -/** - * Get the extent of the features currently in the source. - * - * This method is not available when the source is configured with - * `useSpatialIndex` set to `false`. - * @param {ol.Extent=} opt_extent Destination extent. If provided, no new extent - * will be created. Instead, that extent's coordinates will be overwritten. - * @return {ol.Extent} Extent. - * @api - */ -ol.source.Vector.prototype.getExtent = function(opt_extent) { - return this.featuresRtree_.getExtent(opt_extent); -}; - - -/** - * Get a feature by its identifier (the value returned by feature.getId()). - * Note that the index treats string and numeric identifiers as the same. So - * `source.getFeatureById(2)` will return a feature with id `'2'` or `2`. - * - * @param {string|number} id Feature identifier. - * @return {ol.Feature} The feature (or `null` if not found). - * @api - */ -ol.source.Vector.prototype.getFeatureById = function(id) { - var feature = this.idIndex_[id.toString()]; - return feature !== undefined ? feature : null; -}; - - -/** - * Get the format associated with this source. - * - * @return {ol.format.Feature|undefined} The feature format. - * @api - */ -ol.source.Vector.prototype.getFormat = function() { - return this.format_; -}; - - -/** - * @return {boolean} The source can have overlapping geometries. - */ -ol.source.Vector.prototype.getOverlaps = function() { - return this.overlaps_; -}; - - -/** - * @override - */ -ol.source.Vector.prototype.getResolutions = function() {}; - - -/** - * Get the url associated with this source. - * - * @return {string|ol.FeatureUrlFunction|undefined} The url. - * @api - */ -ol.source.Vector.prototype.getUrl = function() { - return this.url_; -}; - - -/** - * @param {ol.events.Event} event Event. - * @private - */ -ol.source.Vector.prototype.handleFeatureChange_ = function(event) { - var feature = /** @type {ol.Feature} */ (event.target); - var featureKey = ol.getUid(feature).toString(); - var geometry = feature.getGeometry(); - if (!geometry) { - if (!(featureKey in this.nullGeometryFeatures_)) { - if (this.featuresRtree_) { - this.featuresRtree_.remove(feature); - } - this.nullGeometryFeatures_[featureKey] = feature; - } - } else { - var extent = geometry.getExtent(); - if (featureKey in this.nullGeometryFeatures_) { - delete this.nullGeometryFeatures_[featureKey]; - if (this.featuresRtree_) { - this.featuresRtree_.insert(extent, feature); - } - } else { - if (this.featuresRtree_) { - this.featuresRtree_.update(extent, feature); - } - } - } - var id = feature.getId(); - if (id !== undefined) { - var sid = id.toString(); - if (featureKey in this.undefIdIndex_) { - delete this.undefIdIndex_[featureKey]; - this.idIndex_[sid] = feature; - } else { - if (this.idIndex_[sid] !== feature) { - this.removeFromIdIndex_(feature); - this.idIndex_[sid] = feature; - } - } - } else { - if (!(featureKey in this.undefIdIndex_)) { - this.removeFromIdIndex_(feature); - this.undefIdIndex_[featureKey] = feature; - } - } - this.changed(); - this.dispatchEvent(new ol.source.Vector.Event( - ol.source.VectorEventType.CHANGEFEATURE, feature)); -}; - - -/** - * @return {boolean} Is empty. - */ -ol.source.Vector.prototype.isEmpty = function() { - return this.featuresRtree_.isEmpty() && - ol.obj.isEmpty(this.nullGeometryFeatures_); -}; - - -/** - * @param {ol.Extent} extent Extent. - * @param {number} resolution Resolution. - * @param {ol.proj.Projection} projection Projection. - */ -ol.source.Vector.prototype.loadFeatures = function( - extent, resolution, projection) { - var loadedExtentsRtree = this.loadedExtentsRtree_; - var extentsToLoad = this.strategy_(extent, resolution); - var i, ii; - for (i = 0, ii = extentsToLoad.length; i < ii; ++i) { - var extentToLoad = extentsToLoad[i]; - var alreadyLoaded = loadedExtentsRtree.forEachInExtent(extentToLoad, - /** - * @param {{extent: ol.Extent}} object Object. - * @return {boolean} Contains. - */ - function(object) { - return ol.extent.containsExtent(object.extent, extentToLoad); - }); - if (!alreadyLoaded) { - this.loader_.call(this, extentToLoad, resolution, projection); - loadedExtentsRtree.insert(extentToLoad, {extent: extentToLoad.slice()}); - } - } -}; - - -/** - * Remove a single feature from the source. If you want to remove all features - * at once, use the {@link ol.source.Vector#clear source.clear()} method - * instead. - * @param {ol.Feature} feature Feature to remove. - * @api - */ -ol.source.Vector.prototype.removeFeature = function(feature) { - var featureKey = ol.getUid(feature).toString(); - if (featureKey in this.nullGeometryFeatures_) { - delete this.nullGeometryFeatures_[featureKey]; - } else { - if (this.featuresRtree_) { - this.featuresRtree_.remove(feature); - } - } - this.removeFeatureInternal(feature); - this.changed(); -}; - - -/** - * Remove feature without firing a `change` event. - * @param {ol.Feature} feature Feature. - * @protected - */ -ol.source.Vector.prototype.removeFeatureInternal = function(feature) { - var featureKey = ol.getUid(feature).toString(); - this.featureChangeKeys_[featureKey].forEach(ol.events.unlistenByKey); - delete this.featureChangeKeys_[featureKey]; - var id = feature.getId(); - if (id !== undefined) { - delete this.idIndex_[id.toString()]; - } else { - delete this.undefIdIndex_[featureKey]; - } - this.dispatchEvent(new ol.source.Vector.Event( - ol.source.VectorEventType.REMOVEFEATURE, feature)); -}; - - -/** - * Remove a feature from the id index. Called internally when the feature id - * may have changed. - * @param {ol.Feature} feature The feature. - * @return {boolean} Removed the feature from the index. - * @private - */ -ol.source.Vector.prototype.removeFromIdIndex_ = function(feature) { - var removed = false; - for (var id in this.idIndex_) { - if (this.idIndex_[id] === feature) { - delete this.idIndex_[id]; - removed = true; - break; - } - } - return removed; -}; - - -/** - * Set the new loader of the source. The next loadFeatures call will use the - * new loader. - * @param {ol.FeatureLoader} loader The loader to set. - * @api - */ -ol.source.Vector.prototype.setLoader = function(loader) { - this.loader_ = loader; -}; - - -/** - * @classdesc - * Events emitted by {@link ol.source.Vector} instances are instances of this - * type. - * - * @constructor - * @extends {ol.events.Event} - * @implements {oli.source.Vector.Event} - * @param {string} type Type. - * @param {ol.Feature=} opt_feature Feature. - */ -ol.source.Vector.Event = function(type, opt_feature) { - - ol.events.Event.call(this, type); - - /** - * The feature being added or removed. - * @type {ol.Feature|undefined} - * @api - */ - this.feature = opt_feature; - -}; -ol.inherits(ol.source.Vector.Event, ol.events.Event); - -goog.provide('ol.interaction.Draw'); - -goog.require('ol'); -goog.require('ol.Feature'); -goog.require('ol.MapBrowserEventType'); -goog.require('ol.Object'); -goog.require('ol.coordinate'); -goog.require('ol.events'); -goog.require('ol.events.Event'); -goog.require('ol.events.condition'); -goog.require('ol.extent'); -goog.require('ol.functions'); -goog.require('ol.geom.Circle'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.LineString'); -goog.require('ol.geom.MultiLineString'); -goog.require('ol.geom.MultiPoint'); -goog.require('ol.geom.MultiPolygon'); -goog.require('ol.geom.Point'); -goog.require('ol.geom.Polygon'); -goog.require('ol.interaction.DrawEventType'); -goog.require('ol.interaction.Pointer'); -goog.require('ol.interaction.Property'); -goog.require('ol.layer.Vector'); -goog.require('ol.source.Vector'); -goog.require('ol.style.Style'); - - -/** - * @classdesc - * Interaction for drawing feature geometries. - * - * @constructor - * @extends {ol.interaction.Pointer} - * @fires ol.interaction.Draw.Event - * @param {olx.interaction.DrawOptions} options Options. - * @api - */ -ol.interaction.Draw = function(options) { - - ol.interaction.Pointer.call(this, { - handleDownEvent: ol.interaction.Draw.handleDownEvent_, - handleEvent: ol.interaction.Draw.handleEvent, - handleUpEvent: ol.interaction.Draw.handleUpEvent_ - }); - - /** - * @type {boolean} - * @private - */ - this.shouldHandle_ = false; - - /** - * @type {ol.Pixel} - * @private - */ - this.downPx_ = null; - - /** - * @type {boolean} - * @private - */ - this.freehand_ = false; - - /** - * Target source for drawn features. - * @type {ol.source.Vector} - * @private - */ - this.source_ = options.source ? options.source : null; - - /** - * Target collection for drawn features. - * @type {ol.Collection.<ol.Feature>} - * @private - */ - this.features_ = options.features ? options.features : null; - - /** - * Pixel distance for snapping. - * @type {number} - * @private - */ - this.snapTolerance_ = options.snapTolerance ? options.snapTolerance : 12; - - /** - * Geometry type. - * @type {ol.geom.GeometryType} - * @private - */ - this.type_ = options.type; - - /** - * Drawing mode (derived from geometry type. - * @type {ol.interaction.Draw.Mode_} - * @private - */ - this.mode_ = ol.interaction.Draw.getMode_(this.type_); - - /** - * The number of points that must be drawn before a polygon ring or line - * string can be finished. The default is 3 for polygon rings and 2 for - * line strings. - * @type {number} - * @private - */ - this.minPoints_ = options.minPoints ? - options.minPoints : - (this.mode_ === ol.interaction.Draw.Mode_.POLYGON ? 3 : 2); - - /** - * The number of points that can be drawn before a polygon ring or line string - * is finished. The default is no restriction. - * @type {number} - * @private - */ - this.maxPoints_ = options.maxPoints ? options.maxPoints : Infinity; - - /** - * A function to decide if a potential finish coordinate is permissible - * @private - * @type {ol.EventsConditionType} - */ - this.finishCondition_ = options.finishCondition ? options.finishCondition : ol.functions.TRUE; - - var geometryFunction = options.geometryFunction; - if (!geometryFunction) { - if (this.type_ === ol.geom.GeometryType.CIRCLE) { - /** - * @param {!Array.<ol.Coordinate>} coordinates - * The coordinates. - * @param {ol.geom.SimpleGeometry=} opt_geometry Optional geometry. - * @return {ol.geom.SimpleGeometry} A geometry. - */ - geometryFunction = function(coordinates, opt_geometry) { - var circle = opt_geometry ? /** @type {ol.geom.Circle} */ (opt_geometry) : - new ol.geom.Circle([NaN, NaN]); - var squaredLength = ol.coordinate.squaredDistance( - coordinates[0], coordinates[1]); - circle.setCenterAndRadius(coordinates[0], Math.sqrt(squaredLength)); - return circle; - }; - } else { - var Constructor; - var mode = this.mode_; - if (mode === ol.interaction.Draw.Mode_.POINT) { - Constructor = ol.geom.Point; - } else if (mode === ol.interaction.Draw.Mode_.LINE_STRING) { - Constructor = ol.geom.LineString; - } else if (mode === ol.interaction.Draw.Mode_.POLYGON) { - Constructor = ol.geom.Polygon; - } - /** - * @param {!Array.<ol.Coordinate>} coordinates - * The coordinates. - * @param {ol.geom.SimpleGeometry=} opt_geometry Optional geometry. - * @return {ol.geom.SimpleGeometry} A geometry. - */ - geometryFunction = function(coordinates, opt_geometry) { - var geometry = opt_geometry; - if (geometry) { - if (mode === ol.interaction.Draw.Mode_.POLYGON) { - geometry.setCoordinates([coordinates[0].concat([coordinates[0][0]])]); - } else { - geometry.setCoordinates(coordinates); - } - } else { - geometry = new Constructor(coordinates); - } - return geometry; - }; - } - } - - /** - * @type {ol.DrawGeometryFunctionType} - * @private - */ - this.geometryFunction_ = geometryFunction; - - /** - * Finish coordinate for the feature (first point for polygons, last point for - * linestrings). - * @type {ol.Coordinate} - * @private - */ - this.finishCoordinate_ = null; - - /** - * Sketch feature. - * @type {ol.Feature} - * @private - */ - this.sketchFeature_ = null; - - /** - * Sketch point. - * @type {ol.Feature} - * @private - */ - this.sketchPoint_ = null; - - /** - * Sketch coordinates. Used when drawing a line or polygon. - * @type {ol.Coordinate|Array.<ol.Coordinate>|Array.<Array.<ol.Coordinate>>} - * @private - */ - this.sketchCoords_ = null; - - /** - * Sketch line. Used when drawing polygon. - * @type {ol.Feature} - * @private - */ - this.sketchLine_ = null; - - /** - * Sketch line coordinates. Used when drawing a polygon or circle. - * @type {Array.<ol.Coordinate>} - * @private - */ - this.sketchLineCoords_ = null; - - /** - * Squared tolerance for handling up events. If the squared distance - * between a down and up event is greater than this tolerance, up events - * will not be handled. - * @type {number} - * @private - */ - this.squaredClickTolerance_ = options.clickTolerance ? - options.clickTolerance * options.clickTolerance : 36; - - /** - * Draw overlay where our sketch features are drawn. - * @type {ol.layer.Vector} - * @private - */ - this.overlay_ = new ol.layer.Vector({ - source: new ol.source.Vector({ - useSpatialIndex: false, - wrapX: options.wrapX ? options.wrapX : false - }), - style: options.style ? options.style : - ol.interaction.Draw.getDefaultStyleFunction() - }); - - /** - * Name of the geometry attribute for newly created features. - * @type {string|undefined} - * @private - */ - this.geometryName_ = options.geometryName; - - /** - * @private - * @type {ol.EventsConditionType} - */ - this.condition_ = options.condition ? - options.condition : ol.events.condition.noModifierKeys; - - /** - * @private - * @type {ol.EventsConditionType} - */ - this.freehandCondition_; - if (options.freehand) { - this.freehandCondition_ = ol.events.condition.always; - } else { - this.freehandCondition_ = options.freehandCondition ? - options.freehandCondition : ol.events.condition.shiftKeyOnly; - } - - ol.events.listen(this, - ol.Object.getChangeEventType(ol.interaction.Property.ACTIVE), - this.updateState_, this); - -}; -ol.inherits(ol.interaction.Draw, ol.interaction.Pointer); - - -/** - * @return {ol.StyleFunction} Styles. - */ -ol.interaction.Draw.getDefaultStyleFunction = function() { - var styles = ol.style.Style.createDefaultEditing(); - return function(feature, resolution) { - return styles[feature.getGeometry().getType()]; - }; -}; - - -/** - * @inheritDoc - */ -ol.interaction.Draw.prototype.setMap = function(map) { - ol.interaction.Pointer.prototype.setMap.call(this, map); - this.updateState_(); -}; - - -/** - * Handles the {@link ol.MapBrowserEvent map browser event} and may actually - * draw or finish the drawing. - * @param {ol.MapBrowserEvent} event Map browser event. - * @return {boolean} `false` to stop event propagation. - * @this {ol.interaction.Draw} - * @api - */ -ol.interaction.Draw.handleEvent = function(event) { - this.freehand_ = this.mode_ !== ol.interaction.Draw.Mode_.POINT && this.freehandCondition_(event); - var pass = true; - if (this.freehand_ && - event.type === ol.MapBrowserEventType.POINTERDRAG && - this.sketchFeature_ !== null) { - this.addToDrawing_(event); - pass = false; - } else if (this.freehand_ && - event.type === ol.MapBrowserEventType.POINTERDOWN) { - pass = false; - } else if (event.type === ol.MapBrowserEventType.POINTERMOVE) { - pass = this.handlePointerMove_(event); - } else if (event.type === ol.MapBrowserEventType.DBLCLICK) { - pass = false; - } - return ol.interaction.Pointer.handleEvent.call(this, event) && pass; -}; - - -/** - * @param {ol.MapBrowserPointerEvent} event Event. - * @return {boolean} Start drag sequence? - * @this {ol.interaction.Draw} - * @private - */ -ol.interaction.Draw.handleDownEvent_ = function(event) { - this.shouldHandle_ = !this.freehand_; - - if (this.freehand_) { - this.downPx_ = event.pixel; - if (!this.finishCoordinate_) { - this.startDrawing_(event); - } - return true; - } else if (this.condition_(event)) { - this.downPx_ = event.pixel; - return true; - } else { - return false; - } -}; - - -/** - * @param {ol.MapBrowserPointerEvent} event Event. - * @return {boolean} Stop drag sequence? - * @this {ol.interaction.Draw} - * @private - */ -ol.interaction.Draw.handleUpEvent_ = function(event) { - var pass = true; - - this.handlePointerMove_(event); - - var circleMode = this.mode_ === ol.interaction.Draw.Mode_.CIRCLE; - - if (this.shouldHandle_) { - if (!this.finishCoordinate_) { - this.startDrawing_(event); - if (this.mode_ === ol.interaction.Draw.Mode_.POINT) { - this.finishDrawing(); - } - } else if (this.freehand_ || circleMode) { - this.finishDrawing(); - } else if (this.atFinish_(event)) { - if (this.finishCondition_(event)) { - this.finishDrawing(); - } - } else { - this.addToDrawing_(event); - } - pass = false; - } else if (this.freehand_) { - this.finishCoordinate_ = null; - this.abortDrawing_(); - } - return pass; -}; - - -/** - * Handle move events. - * @param {ol.MapBrowserEvent} event A move event. - * @return {boolean} Pass the event to other interactions. - * @private - */ -ol.interaction.Draw.prototype.handlePointerMove_ = function(event) { - if (this.downPx_ && - ((!this.freehand_ && this.shouldHandle_) || - (this.freehand_ && !this.shouldHandle_))) { - var downPx = this.downPx_; - var clickPx = event.pixel; - var dx = downPx[0] - clickPx[0]; - var dy = downPx[1] - clickPx[1]; - var squaredDistance = dx * dx + dy * dy; - this.shouldHandle_ = this.freehand_ ? - squaredDistance > this.squaredClickTolerance_ : - squaredDistance <= this.squaredClickTolerance_; - } - - if (this.finishCoordinate_) { - this.modifyDrawing_(event); - } else { - this.createOrUpdateSketchPoint_(event); - } - return true; -}; - - -/** - * Determine if an event is within the snapping tolerance of the start coord. - * @param {ol.MapBrowserEvent} event Event. - * @return {boolean} The event is within the snapping tolerance of the start. - * @private - */ -ol.interaction.Draw.prototype.atFinish_ = function(event) { - var at = false; - if (this.sketchFeature_) { - var potentiallyDone = false; - var potentiallyFinishCoordinates = [this.finishCoordinate_]; - if (this.mode_ === ol.interaction.Draw.Mode_.LINE_STRING) { - potentiallyDone = this.sketchCoords_.length > this.minPoints_; - } else if (this.mode_ === ol.interaction.Draw.Mode_.POLYGON) { - potentiallyDone = this.sketchCoords_[0].length > - this.minPoints_; - potentiallyFinishCoordinates = [this.sketchCoords_[0][0], - this.sketchCoords_[0][this.sketchCoords_[0].length - 2]]; - } - if (potentiallyDone) { - var map = event.map; - for (var i = 0, ii = potentiallyFinishCoordinates.length; i < ii; i++) { - var finishCoordinate = potentiallyFinishCoordinates[i]; - var finishPixel = map.getPixelFromCoordinate(finishCoordinate); - var pixel = event.pixel; - var dx = pixel[0] - finishPixel[0]; - var dy = pixel[1] - finishPixel[1]; - var snapTolerance = this.freehand_ ? 1 : this.snapTolerance_; - at = Math.sqrt(dx * dx + dy * dy) <= snapTolerance; - if (at) { - this.finishCoordinate_ = finishCoordinate; - break; - } - } - } - } - return at; -}; - - -/** - * @param {ol.MapBrowserEvent} event Event. - * @private - */ -ol.interaction.Draw.prototype.createOrUpdateSketchPoint_ = function(event) { - var coordinates = event.coordinate.slice(); - if (!this.sketchPoint_) { - this.sketchPoint_ = new ol.Feature(new ol.geom.Point(coordinates)); - this.updateSketchFeatures_(); - } else { - var sketchPointGeom = /** @type {ol.geom.Point} */ (this.sketchPoint_.getGeometry()); - sketchPointGeom.setCoordinates(coordinates); - } -}; - - -/** - * Start the drawing. - * @param {ol.MapBrowserEvent} event Event. - * @private - */ -ol.interaction.Draw.prototype.startDrawing_ = function(event) { - var start = event.coordinate; - this.finishCoordinate_ = start; - if (this.mode_ === ol.interaction.Draw.Mode_.POINT) { - this.sketchCoords_ = start.slice(); - } else if (this.mode_ === ol.interaction.Draw.Mode_.POLYGON) { - this.sketchCoords_ = [[start.slice(), start.slice()]]; - this.sketchLineCoords_ = this.sketchCoords_[0]; - } else { - this.sketchCoords_ = [start.slice(), start.slice()]; - if (this.mode_ === ol.interaction.Draw.Mode_.CIRCLE) { - this.sketchLineCoords_ = this.sketchCoords_; - } - } - if (this.sketchLineCoords_) { - this.sketchLine_ = new ol.Feature( - new ol.geom.LineString(this.sketchLineCoords_)); - } - var geometry = this.geometryFunction_(this.sketchCoords_); - this.sketchFeature_ = new ol.Feature(); - if (this.geometryName_) { - this.sketchFeature_.setGeometryName(this.geometryName_); - } - this.sketchFeature_.setGeometry(geometry); - this.updateSketchFeatures_(); - this.dispatchEvent(new ol.interaction.Draw.Event( - ol.interaction.DrawEventType.DRAWSTART, this.sketchFeature_)); -}; - - -/** - * Modify the drawing. - * @param {ol.MapBrowserEvent} event Event. - * @private - */ -ol.interaction.Draw.prototype.modifyDrawing_ = function(event) { - var coordinate = event.coordinate; - var geometry = /** @type {ol.geom.SimpleGeometry} */ (this.sketchFeature_.getGeometry()); - var coordinates, last; - if (this.mode_ === ol.interaction.Draw.Mode_.POINT) { - last = this.sketchCoords_; - } else if (this.mode_ === ol.interaction.Draw.Mode_.POLYGON) { - coordinates = this.sketchCoords_[0]; - last = coordinates[coordinates.length - 1]; - if (this.atFinish_(event)) { - // snap to finish - coordinate = this.finishCoordinate_.slice(); - } - } else { - coordinates = this.sketchCoords_; - last = coordinates[coordinates.length - 1]; - } - last[0] = coordinate[0]; - last[1] = coordinate[1]; - this.geometryFunction_(/** @type {!Array.<ol.Coordinate>} */ (this.sketchCoords_), geometry); - if (this.sketchPoint_) { - var sketchPointGeom = /** @type {ol.geom.Point} */ (this.sketchPoint_.getGeometry()); - sketchPointGeom.setCoordinates(coordinate); - } - var sketchLineGeom; - if (geometry instanceof ol.geom.Polygon && - this.mode_ !== ol.interaction.Draw.Mode_.POLYGON) { - if (!this.sketchLine_) { - this.sketchLine_ = new ol.Feature(new ol.geom.LineString(null)); - } - var ring = geometry.getLinearRing(0); - sketchLineGeom = /** @type {ol.geom.LineString} */ (this.sketchLine_.getGeometry()); - sketchLineGeom.setFlatCoordinates( - ring.getLayout(), ring.getFlatCoordinates()); - } else if (this.sketchLineCoords_) { - sketchLineGeom = /** @type {ol.geom.LineString} */ (this.sketchLine_.getGeometry()); - sketchLineGeom.setCoordinates(this.sketchLineCoords_); - } - this.updateSketchFeatures_(); -}; - - -/** - * Add a new coordinate to the drawing. - * @param {ol.MapBrowserEvent} event Event. - * @private - */ -ol.interaction.Draw.prototype.addToDrawing_ = function(event) { - var coordinate = event.coordinate; - var geometry = /** @type {ol.geom.SimpleGeometry} */ (this.sketchFeature_.getGeometry()); - var done; - var coordinates; - if (this.mode_ === ol.interaction.Draw.Mode_.LINE_STRING) { - this.finishCoordinate_ = coordinate.slice(); - coordinates = this.sketchCoords_; - if (coordinates.length >= this.maxPoints_) { - if (this.freehand_) { - coordinates.pop(); - } else { - done = true; - } - } - coordinates.push(coordinate.slice()); - this.geometryFunction_(coordinates, geometry); - } else if (this.mode_ === ol.interaction.Draw.Mode_.POLYGON) { - coordinates = this.sketchCoords_[0]; - if (coordinates.length >= this.maxPoints_) { - if (this.freehand_) { - coordinates.pop(); - } else { - done = true; - } - } - coordinates.push(coordinate.slice()); - if (done) { - this.finishCoordinate_ = coordinates[0]; - } - this.geometryFunction_(this.sketchCoords_, geometry); - } - this.updateSketchFeatures_(); - if (done) { - this.finishDrawing(); - } -}; - - -/** - * Remove last point of the feature currently being drawn. - * @api - */ -ol.interaction.Draw.prototype.removeLastPoint = function() { - if (!this.sketchFeature_) { - return; - } - var geometry = /** @type {ol.geom.SimpleGeometry} */ (this.sketchFeature_.getGeometry()); - var coordinates, sketchLineGeom; - if (this.mode_ === ol.interaction.Draw.Mode_.LINE_STRING) { - coordinates = this.sketchCoords_; - coordinates.splice(-2, 1); - this.geometryFunction_(coordinates, geometry); - if (coordinates.length >= 2) { - this.finishCoordinate_ = coordinates[coordinates.length - 2].slice(); - } - } else if (this.mode_ === ol.interaction.Draw.Mode_.POLYGON) { - coordinates = this.sketchCoords_[0]; - coordinates.splice(-2, 1); - sketchLineGeom = /** @type {ol.geom.LineString} */ (this.sketchLine_.getGeometry()); - sketchLineGeom.setCoordinates(coordinates); - this.geometryFunction_(this.sketchCoords_, geometry); - } - - if (coordinates.length === 0) { - this.finishCoordinate_ = null; - } - - this.updateSketchFeatures_(); -}; - - -/** - * Stop drawing and add the sketch feature to the target layer. - * The {@link ol.interaction.DrawEventType.DRAWEND} event is dispatched before - * inserting the feature. - * @api - */ -ol.interaction.Draw.prototype.finishDrawing = function() { - var sketchFeature = this.abortDrawing_(); - var coordinates = this.sketchCoords_; - var geometry = /** @type {ol.geom.SimpleGeometry} */ (sketchFeature.getGeometry()); - if (this.mode_ === ol.interaction.Draw.Mode_.LINE_STRING) { - // remove the redundant last point - coordinates.pop(); - this.geometryFunction_(coordinates, geometry); - } else if (this.mode_ === ol.interaction.Draw.Mode_.POLYGON) { - // remove the redundant last point in ring - coordinates[0].pop(); - this.geometryFunction_(coordinates, geometry); - coordinates = geometry.getCoordinates(); - } - - // cast multi-part geometries - if (this.type_ === ol.geom.GeometryType.MULTI_POINT) { - sketchFeature.setGeometry(new ol.geom.MultiPoint([coordinates])); - } else if (this.type_ === ol.geom.GeometryType.MULTI_LINE_STRING) { - sketchFeature.setGeometry(new ol.geom.MultiLineString([coordinates])); - } else if (this.type_ === ol.geom.GeometryType.MULTI_POLYGON) { - sketchFeature.setGeometry(new ol.geom.MultiPolygon([coordinates])); - } - - // First dispatch event to allow full set up of feature - this.dispatchEvent(new ol.interaction.Draw.Event( - ol.interaction.DrawEventType.DRAWEND, sketchFeature)); - - // Then insert feature - if (this.features_) { - this.features_.push(sketchFeature); - } - if (this.source_) { - this.source_.addFeature(sketchFeature); - } -}; - - -/** - * Stop drawing without adding the sketch feature to the target layer. - * @return {ol.Feature} The sketch feature (or null if none). - * @private - */ -ol.interaction.Draw.prototype.abortDrawing_ = function() { - this.finishCoordinate_ = null; - var sketchFeature = this.sketchFeature_; - if (sketchFeature) { - this.sketchFeature_ = null; - this.sketchPoint_ = null; - this.sketchLine_ = null; - this.overlay_.getSource().clear(true); - } - return sketchFeature; -}; - - -/** - * Extend an existing geometry by adding additional points. This only works - * on features with `LineString` geometries, where the interaction will - * extend lines by adding points to the end of the coordinates array. - * @param {!ol.Feature} feature Feature to be extended. - * @api - */ -ol.interaction.Draw.prototype.extend = function(feature) { - var geometry = feature.getGeometry(); - var lineString = /** @type {ol.geom.LineString} */ (geometry); - this.sketchFeature_ = feature; - this.sketchCoords_ = lineString.getCoordinates(); - var last = this.sketchCoords_[this.sketchCoords_.length - 1]; - this.finishCoordinate_ = last.slice(); - this.sketchCoords_.push(last.slice()); - this.updateSketchFeatures_(); - this.dispatchEvent(new ol.interaction.Draw.Event( - ol.interaction.DrawEventType.DRAWSTART, this.sketchFeature_)); -}; - - -/** - * @inheritDoc - */ -ol.interaction.Draw.prototype.shouldStopEvent = ol.functions.FALSE; - - -/** - * Redraw the sketch features. - * @private - */ -ol.interaction.Draw.prototype.updateSketchFeatures_ = function() { - var sketchFeatures = []; - if (this.sketchFeature_) { - sketchFeatures.push(this.sketchFeature_); - } - if (this.sketchLine_) { - sketchFeatures.push(this.sketchLine_); - } - if (this.sketchPoint_) { - sketchFeatures.push(this.sketchPoint_); - } - var overlaySource = this.overlay_.getSource(); - overlaySource.clear(true); - overlaySource.addFeatures(sketchFeatures); -}; - - -/** - * @private - */ -ol.interaction.Draw.prototype.updateState_ = function() { - var map = this.getMap(); - var active = this.getActive(); - if (!map || !active) { - this.abortDrawing_(); - } - this.overlay_.setMap(active ? map : null); -}; - - -/** - * Create a `geometryFunction` for `type: 'Circle'` that will create a regular - * polygon with a user specified number of sides and start angle instead of an - * `ol.geom.Circle` geometry. - * @param {number=} opt_sides Number of sides of the regular polygon. Default is - * 32. - * @param {number=} opt_angle Angle of the first point in radians. 0 means East. - * Default is the angle defined by the heading from the center of the - * regular polygon to the current pointer position. - * @return {ol.DrawGeometryFunctionType} Function that draws a - * polygon. - * @api - */ -ol.interaction.Draw.createRegularPolygon = function(opt_sides, opt_angle) { - return ( - /** - * @param {ol.Coordinate|Array.<ol.Coordinate>|Array.<Array.<ol.Coordinate>>} coordinates - * @param {ol.geom.SimpleGeometry=} opt_geometry - * @return {ol.geom.SimpleGeometry} - */ - function(coordinates, opt_geometry) { - var center = coordinates[0]; - var end = coordinates[1]; - var radius = Math.sqrt( - ol.coordinate.squaredDistance(center, end)); - var geometry = opt_geometry ? /** @type {ol.geom.Polygon} */ (opt_geometry) : - ol.geom.Polygon.fromCircle(new ol.geom.Circle(center), opt_sides); - var angle = opt_angle ? opt_angle : - Math.atan((end[1] - center[1]) / (end[0] - center[0])); - ol.geom.Polygon.makeRegular(geometry, center, radius, angle); - return geometry; - } - ); -}; - - -/** - * Create a `geometryFunction` that will create a box-shaped polygon (aligned - * with the coordinate system axes). Use this with the draw interaction and - * `type: 'Circle'` to return a box instead of a circle geometry. - * @return {ol.DrawGeometryFunctionType} Function that draws a box-shaped polygon. - * @api - */ -ol.interaction.Draw.createBox = function() { - return ( - /** - * @param {Array.<ol.Coordinate>} coordinates - * @param {ol.geom.SimpleGeometry=} opt_geometry - * @return {ol.geom.SimpleGeometry} - */ - function(coordinates, opt_geometry) { - var extent = ol.extent.boundingExtent(coordinates); - var geometry = opt_geometry || new ol.geom.Polygon(null); - geometry.setCoordinates([[ - ol.extent.getBottomLeft(extent), - ol.extent.getBottomRight(extent), - ol.extent.getTopRight(extent), - ol.extent.getTopLeft(extent), - ol.extent.getBottomLeft(extent) - ]]); - return geometry; - } - ); -}; - - -/** - * Get the drawing mode. The mode for mult-part geometries is the same as for - * their single-part cousins. - * @param {ol.geom.GeometryType} type Geometry type. - * @return {ol.interaction.Draw.Mode_} Drawing mode. - * @private - */ -ol.interaction.Draw.getMode_ = function(type) { - var mode; - if (type === ol.geom.GeometryType.POINT || - type === ol.geom.GeometryType.MULTI_POINT) { - mode = ol.interaction.Draw.Mode_.POINT; - } else if (type === ol.geom.GeometryType.LINE_STRING || - type === ol.geom.GeometryType.MULTI_LINE_STRING) { - mode = ol.interaction.Draw.Mode_.LINE_STRING; - } else if (type === ol.geom.GeometryType.POLYGON || - type === ol.geom.GeometryType.MULTI_POLYGON) { - mode = ol.interaction.Draw.Mode_.POLYGON; - } else if (type === ol.geom.GeometryType.CIRCLE) { - mode = ol.interaction.Draw.Mode_.CIRCLE; - } - return /** @type {!ol.interaction.Draw.Mode_} */ (mode); -}; - - -/** - * Draw mode. This collapses multi-part geometry types with their single-part - * cousins. - * @enum {string} - * @private - */ -ol.interaction.Draw.Mode_ = { - POINT: 'Point', - LINE_STRING: 'LineString', - POLYGON: 'Polygon', - CIRCLE: 'Circle' -}; - -/** - * @classdesc - * Events emitted by {@link ol.interaction.Draw} instances are instances of - * this type. - * - * @constructor - * @extends {ol.events.Event} - * @implements {oli.DrawEvent} - * @param {ol.interaction.DrawEventType} type Type. - * @param {ol.Feature} feature The feature drawn. - */ -ol.interaction.Draw.Event = function(type, feature) { - - ol.events.Event.call(this, type); - - /** - * The feature being drawn. - * @type {ol.Feature} - * @api - */ - this.feature = feature; - -}; -ol.inherits(ol.interaction.Draw.Event, ol.events.Event); - -goog.provide('ol.interaction.ExtentEventType'); - - -/** - * @enum {string} - */ -ol.interaction.ExtentEventType = { - /** - * Triggered after the extent is changed - * @event ol.interaction.Extent.Event#extentchanged - * @api - */ - EXTENTCHANGED: 'extentchanged' -}; - -goog.provide('ol.interaction.Extent'); - -goog.require('ol'); -goog.require('ol.Feature'); -goog.require('ol.MapBrowserEventType'); -goog.require('ol.MapBrowserPointerEvent'); -goog.require('ol.coordinate'); -goog.require('ol.events.Event'); -goog.require('ol.extent'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.Point'); -goog.require('ol.geom.Polygon'); -goog.require('ol.interaction.ExtentEventType'); -goog.require('ol.interaction.Pointer'); -goog.require('ol.layer.Vector'); -goog.require('ol.source.Vector'); -goog.require('ol.style.Style'); - - -/** - * @classdesc - * Allows the user to draw a vector box by clicking and dragging on the map. - * Once drawn, the vector box can be modified by dragging its vertices or edges. - * This interaction is only supported for mouse devices. - * - * @constructor - * @extends {ol.interaction.Pointer} - * @fires ol.interaction.Extent.Event - * @param {olx.interaction.ExtentOptions=} opt_options Options. - * @api - */ -ol.interaction.Extent = function(opt_options) { - - /** - * Extent of the drawn box - * @type {ol.Extent} - * @private - */ - this.extent_ = null; - - /** - * Handler for pointer move events - * @type {function (ol.Coordinate): ol.Extent|null} - * @private - */ - this.pointerHandler_ = null; - - /** - * Pixel threshold to snap to extent - * @type {number} - * @private - */ - this.pixelTolerance_ = 10; - - /** - * Is the pointer snapped to an extent vertex - * @type {boolean} - * @private - */ - this.snappedToVertex_ = false; - - /** - * Feature for displaying the visible extent - * @type {ol.Feature} - * @private - */ - this.extentFeature_ = null; - - /** - * Feature for displaying the visible pointer - * @type {ol.Feature} - * @private - */ - this.vertexFeature_ = null; - - if (!opt_options) { - opt_options = {}; - } - - /* Inherit ol.interaction.Pointer */ - ol.interaction.Pointer.call(this, { - handleDownEvent: ol.interaction.Extent.handleDownEvent_, - handleDragEvent: ol.interaction.Extent.handleDragEvent_, - handleEvent: ol.interaction.Extent.handleEvent_, - handleUpEvent: ol.interaction.Extent.handleUpEvent_ - }); - - /** - * Layer for the extentFeature - * @type {ol.layer.Vector} - * @private - */ - this.extentOverlay_ = new ol.layer.Vector({ - source: new ol.source.Vector({ - useSpatialIndex: false, - wrapX: !!opt_options.wrapX - }), - style: opt_options.boxStyle ? opt_options.boxStyle : ol.interaction.Extent.getDefaultExtentStyleFunction_(), - updateWhileAnimating: true, - updateWhileInteracting: true - }); - - /** - * Layer for the vertexFeature - * @type {ol.layer.Vector} - * @private - */ - this.vertexOverlay_ = new ol.layer.Vector({ - source: new ol.source.Vector({ - useSpatialIndex: false, - wrapX: !!opt_options.wrapX - }), - style: opt_options.pointerStyle ? opt_options.pointerStyle : ol.interaction.Extent.getDefaultPointerStyleFunction_(), - updateWhileAnimating: true, - updateWhileInteracting: true - }); - - if (opt_options.extent) { - this.setExtent(opt_options.extent); - } -}; - -ol.inherits(ol.interaction.Extent, ol.interaction.Pointer); - -/** - * @param {ol.MapBrowserEvent} mapBrowserEvent Event. - * @return {boolean} Propagate event? - * @this {ol.interaction.Extent} - * @private - */ -ol.interaction.Extent.handleEvent_ = function(mapBrowserEvent) { - if (!(mapBrowserEvent instanceof ol.MapBrowserPointerEvent)) { - return true; - } - //display pointer (if not dragging) - if (mapBrowserEvent.type == ol.MapBrowserEventType.POINTERMOVE && !this.handlingDownUpSequence) { - this.handlePointerMove_(mapBrowserEvent); - } - //call pointer to determine up/down/drag - ol.interaction.Pointer.handleEvent.call(this, mapBrowserEvent); - //return false to stop propagation - return false; -}; - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Event handled? - * @this {ol.interaction.Extent} - * @private - */ -ol.interaction.Extent.handleDownEvent_ = function(mapBrowserEvent) { - var pixel = mapBrowserEvent.pixel; - var map = mapBrowserEvent.map; - - var extent = this.getExtent(); - var vertex = this.snapToVertex_(pixel, map); - - //find the extent corner opposite the passed corner - var getOpposingPoint = function(point) { - var x_ = null; - var y_ = null; - if (point[0] == extent[0]) { - x_ = extent[2]; - } else if (point[0] == extent[2]) { - x_ = extent[0]; - } - if (point[1] == extent[1]) { - y_ = extent[3]; - } else if (point[1] == extent[3]) { - y_ = extent[1]; - } - if (x_ !== null && y_ !== null) { - return [x_, y_]; - } - return null; - }; - if (vertex && extent) { - var x = (vertex[0] == extent[0] || vertex[0] == extent[2]) ? vertex[0] : null; - var y = (vertex[1] == extent[1] || vertex[1] == extent[3]) ? vertex[1] : null; - - //snap to point - if (x !== null && y !== null) { - this.pointerHandler_ = ol.interaction.Extent.getPointHandler_(getOpposingPoint(vertex)); - //snap to edge - } else if (x !== null) { - this.pointerHandler_ = ol.interaction.Extent.getEdgeHandler_( - getOpposingPoint([x, extent[1]]), - getOpposingPoint([x, extent[3]]) - ); - } else if (y !== null) { - this.pointerHandler_ = ol.interaction.Extent.getEdgeHandler_( - getOpposingPoint([extent[0], y]), - getOpposingPoint([extent[2], y]) - ); - } - //no snap - new bbox - } else { - vertex = map.getCoordinateFromPixel(pixel); - this.setExtent([vertex[0], vertex[1], vertex[0], vertex[1]]); - this.pointerHandler_ = ol.interaction.Extent.getPointHandler_(vertex); - } - return true; //event handled; start downup sequence -}; - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Event handled? - * @this {ol.interaction.Extent} - * @private - */ -ol.interaction.Extent.handleDragEvent_ = function(mapBrowserEvent) { - if (this.pointerHandler_) { - var pixelCoordinate = mapBrowserEvent.coordinate; - this.setExtent(this.pointerHandler_(pixelCoordinate)); - this.createOrUpdatePointerFeature_(pixelCoordinate); - } - return true; -}; - -/** - * @param {ol.MapBrowserPointerEvent} mapBrowserEvent Event. - * @return {boolean} Stop drag sequence? - * @this {ol.interaction.Extent} - * @private - */ -ol.interaction.Extent.handleUpEvent_ = function(mapBrowserEvent) { - this.pointerHandler_ = null; - //If bbox is zero area, set to null; - var extent = this.getExtent(); - if (!extent || ol.extent.getArea(extent) === 0) { - this.setExtent(null); - } - return false; //Stop handling downup sequence -}; - -/** - * Returns the default style for the drawn bbox - * - * @return {ol.StyleFunction} Default Extent style - * @private - */ -ol.interaction.Extent.getDefaultExtentStyleFunction_ = function() { - var style = ol.style.Style.createDefaultEditing(); - return function(feature, resolution) { - return style[ol.geom.GeometryType.POLYGON]; - }; -}; - -/** - * Returns the default style for the pointer - * - * @return {ol.StyleFunction} Default pointer style - * @private - */ -ol.interaction.Extent.getDefaultPointerStyleFunction_ = function() { - var style = ol.style.Style.createDefaultEditing(); - return function(feature, resolution) { - return style[ol.geom.GeometryType.POINT]; - }; -}; - -/** - * @param {ol.Coordinate} fixedPoint corner that will be unchanged in the new extent - * @returns {function (ol.Coordinate): ol.Extent} event handler - * @private - */ -ol.interaction.Extent.getPointHandler_ = function(fixedPoint) { - return function(point) { - return ol.extent.boundingExtent([fixedPoint, point]); - }; -}; - -/** - * @param {ol.Coordinate} fixedP1 first corner that will be unchanged in the new extent - * @param {ol.Coordinate} fixedP2 second corner that will be unchanged in the new extent - * @returns {function (ol.Coordinate): ol.Extent|null} event handler - * @private - */ -ol.interaction.Extent.getEdgeHandler_ = function(fixedP1, fixedP2) { - if (fixedP1[0] == fixedP2[0]) { - return function(point) { - return ol.extent.boundingExtent([fixedP1, [point[0], fixedP2[1]]]); - }; - } else if (fixedP1[1] == fixedP2[1]) { - return function(point) { - return ol.extent.boundingExtent([fixedP1, [fixedP2[0], point[1]]]); - }; - } else { - return null; - } -}; - -/** - * @param {ol.Extent} extent extent - * @returns {Array<Array<ol.Coordinate>>} extent line segments - * @private - */ -ol.interaction.Extent.getSegments_ = function(extent) { - return [ - [[extent[0], extent[1]], [extent[0], extent[3]]], - [[extent[0], extent[3]], [extent[2], extent[3]]], - [[extent[2], extent[3]], [extent[2], extent[1]]], - [[extent[2], extent[1]], [extent[0], extent[1]]] - ]; -}; - -/** - * @param {ol.Pixel} pixel cursor location - * @param {ol.PluggableMap} map map - * @returns {ol.Coordinate|null} snapped vertex on extent - * @private - */ -ol.interaction.Extent.prototype.snapToVertex_ = function(pixel, map) { - var pixelCoordinate = map.getCoordinateFromPixel(pixel); - var sortByDistance = function(a, b) { - return ol.coordinate.squaredDistanceToSegment(pixelCoordinate, a) - - ol.coordinate.squaredDistanceToSegment(pixelCoordinate, b); - }; - var extent = this.getExtent(); - if (extent) { - //convert extents to line segments and find the segment closest to pixelCoordinate - var segments = ol.interaction.Extent.getSegments_(extent); - segments.sort(sortByDistance); - var closestSegment = segments[0]; - - var vertex = (ol.coordinate.closestOnSegment(pixelCoordinate, - closestSegment)); - var vertexPixel = map.getPixelFromCoordinate(vertex); - - //if the distance is within tolerance, snap to the segment - if (ol.coordinate.distance(pixel, vertexPixel) <= this.pixelTolerance_) { - //test if we should further snap to a vertex - var pixel1 = map.getPixelFromCoordinate(closestSegment[0]); - var pixel2 = map.getPixelFromCoordinate(closestSegment[1]); - var squaredDist1 = ol.coordinate.squaredDistance(vertexPixel, pixel1); - var squaredDist2 = ol.coordinate.squaredDistance(vertexPixel, pixel2); - var dist = Math.sqrt(Math.min(squaredDist1, squaredDist2)); - this.snappedToVertex_ = dist <= this.pixelTolerance_; - if (this.snappedToVertex_) { - vertex = squaredDist1 > squaredDist2 ? - closestSegment[1] : closestSegment[0]; - } - return vertex; - } - } - return null; -}; - -/** - * @param {ol.MapBrowserEvent} mapBrowserEvent pointer move event - * @private - */ -ol.interaction.Extent.prototype.handlePointerMove_ = function(mapBrowserEvent) { - var pixel = mapBrowserEvent.pixel; - var map = mapBrowserEvent.map; - - var vertex = this.snapToVertex_(pixel, map); - if (!vertex) { - vertex = map.getCoordinateFromPixel(pixel); - } - this.createOrUpdatePointerFeature_(vertex); -}; - -/** - * @param {ol.Extent} extent extent - * @returns {ol.Feature} extent as featrue - * @private - */ -ol.interaction.Extent.prototype.createOrUpdateExtentFeature_ = function(extent) { - var extentFeature = this.extentFeature_; - - if (!extentFeature) { - if (!extent) { - extentFeature = new ol.Feature({}); - } else { - extentFeature = new ol.Feature(ol.geom.Polygon.fromExtent(extent)); - } - this.extentFeature_ = extentFeature; - this.extentOverlay_.getSource().addFeature(extentFeature); - } else { - if (!extent) { - extentFeature.setGeometry(undefined); - } else { - extentFeature.setGeometry(ol.geom.Polygon.fromExtent(extent)); - } - } - return extentFeature; -}; - - -/** - * @param {ol.Coordinate} vertex location of feature - * @returns {ol.Feature} vertex as feature - * @private - */ -ol.interaction.Extent.prototype.createOrUpdatePointerFeature_ = function(vertex) { - var vertexFeature = this.vertexFeature_; - if (!vertexFeature) { - vertexFeature = new ol.Feature(new ol.geom.Point(vertex)); - this.vertexFeature_ = vertexFeature; - this.vertexOverlay_.getSource().addFeature(vertexFeature); - } else { - var geometry = /** @type {ol.geom.Point} */ (vertexFeature.getGeometry()); - geometry.setCoordinates(vertex); - } - return vertexFeature; -}; - - -/** - * @inheritDoc - */ -ol.interaction.Extent.prototype.setMap = function(map) { - this.extentOverlay_.setMap(map); - this.vertexOverlay_.setMap(map); - ol.interaction.Pointer.prototype.setMap.call(this, map); -}; - -/** - * Returns the current drawn extent in the view projection - * - * @return {ol.Extent} Drawn extent in the view projection. - * @api - */ -ol.interaction.Extent.prototype.getExtent = function() { - return this.extent_; -}; - -/** - * Manually sets the drawn extent, using the view projection. - * - * @param {ol.Extent} extent Extent - * @api - */ -ol.interaction.Extent.prototype.setExtent = function(extent) { - //Null extent means no bbox - this.extent_ = extent ? extent : null; - this.createOrUpdateExtentFeature_(extent); - this.dispatchEvent(new ol.interaction.Extent.Event(this.extent_)); -}; - - -/** - * @classdesc - * Events emitted by {@link ol.interaction.Extent} instances are instances of - * this type. - * - * @constructor - * @implements {oli.ExtentEvent} - * @param {ol.Extent} extent the new extent - * @extends {ol.events.Event} - */ -ol.interaction.Extent.Event = function(extent) { - ol.events.Event.call(this, ol.interaction.ExtentEventType.EXTENTCHANGED); - - /** - * The current extent. - * @type {ol.Extent} - * @api - */ - this.extent = extent; - -}; -ol.inherits(ol.interaction.Extent.Event, ol.events.Event); - -goog.provide('ol.interaction.ModifyEventType'); - - -/** - * @enum {string} - */ -ol.interaction.ModifyEventType = { - /** - * Triggered upon feature modification start - * @event ol.interaction.Modify.Event#modifystart - * @api - */ - MODIFYSTART: 'modifystart', - /** - * Triggered upon feature modification end - * @event ol.interaction.Modify.Event#modifyend - * @api - */ - MODIFYEND: 'modifyend' -}; - -goog.provide('ol.interaction.Modify'); - -goog.require('ol'); -goog.require('ol.Collection'); -goog.require('ol.CollectionEventType'); -goog.require('ol.Feature'); -goog.require('ol.MapBrowserEventType'); -goog.require('ol.MapBrowserPointerEvent'); -goog.require('ol.ViewHint'); -goog.require('ol.array'); -goog.require('ol.coordinate'); -goog.require('ol.events'); -goog.require('ol.events.Event'); -goog.require('ol.events.EventType'); -goog.require('ol.events.condition'); -goog.require('ol.extent'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.Point'); -goog.require('ol.interaction.ModifyEventType'); -goog.require('ol.interaction.Pointer'); -goog.require('ol.layer.Vector'); -goog.require('ol.source.Vector'); -goog.require('ol.source.VectorEventType'); -goog.require('ol.structs.RBush'); -goog.require('ol.style.Style'); - -/** - * @classdesc - * Interaction for modifying feature geometries. To modify features that have - * been added to an existing source, construct the modify interaction with the - * `source` option. If you want to modify features in a collection (for example, - * the collection used by a select interaction), construct the interaction with - * the `features` option. The interaction must be constructed with either a - * `source` or `features` option. - * - * By default, the interaction will allow deletion of vertices when the `alt` - * key is pressed. To configure the interaction with a different condition - * for deletion, use the `deleteCondition` option. - * - * @constructor - * @extends {ol.interaction.Pointer} - * @param {olx.interaction.ModifyOptions} options Options. - * @fires ol.interaction.Modify.Event - * @api - */ -ol.interaction.Modify = function(options) { - - ol.interaction.Pointer.call(this, { - handleDownEvent: ol.interaction.Modify.handleDownEvent_, - handleDragEvent: ol.interaction.Modify.handleDragEvent_, - handleEvent: ol.interaction.Modify.handleEvent, - handleUpEvent: ol.interaction.Modify.handleUpEvent_ - }); - - /** - * @private - * @type {ol.EventsConditionType} - */ - this.condition_ = options.condition ? - options.condition : ol.events.condition.primaryAction; - - - /** - * @private - * @param {ol.MapBrowserEvent} mapBrowserEvent Browser event. - * @return {boolean} Combined condition result. - */ - this.defaultDeleteCondition_ = function(mapBrowserEvent) { - return ol.events.condition.altKeyOnly(mapBrowserEvent) && - ol.events.condition.singleClick(mapBrowserEvent); - }; - - /** - * @type {ol.EventsConditionType} - * @private - */ - this.deleteCondition_ = options.deleteCondition ? - options.deleteCondition : this.defaultDeleteCondition_; - - /** - * @type {ol.EventsConditionType} - * @private - */ - this.insertVertexCondition_ = options.insertVertexCondition ? - options.insertVertexCondition : ol.events.condition.always; - - /** - * Editing vertex. - * @type {ol.Feature} - * @private - */ - this.vertexFeature_ = null; - - /** - * Segments intersecting {@link this.vertexFeature_} by segment uid. - * @type {Object.<string, boolean>} - * @private - */ - this.vertexSegments_ = null; - - /** - * @type {ol.Pixel} - * @private - */ - this.lastPixel_ = [0, 0]; - - /** - * Tracks if the next `singleclick` event should be ignored to prevent - * accidental deletion right after vertex creation. - * @type {boolean} - * @private - */ - this.ignoreNextSingleClick_ = false; - - /** - * @type {boolean} - * @private - */ - this.modified_ = false; - - /** - * Segment RTree for each layer - * @type {ol.structs.RBush.<ol.ModifySegmentDataType>} - * @private - */ - this.rBush_ = new ol.structs.RBush(); - - /** - * @type {number} - * @private - */ - this.pixelTolerance_ = options.pixelTolerance !== undefined ? - options.pixelTolerance : 10; - - /** - * @type {boolean} - * @private - */ - this.snappedToVertex_ = false; - - /** - * Indicate whether the interaction is currently changing a feature's - * coordinates. - * @type {boolean} - * @private - */ - this.changingFeature_ = false; - - /** - * @type {Array} - * @private - */ - this.dragSegments_ = []; - - /** - * Draw overlay where sketch features are drawn. - * @type {ol.layer.Vector} - * @private - */ - this.overlay_ = new ol.layer.Vector({ - source: new ol.source.Vector({ - useSpatialIndex: false, - wrapX: !!options.wrapX - }), - style: options.style ? options.style : - ol.interaction.Modify.getDefaultStyleFunction(), - updateWhileAnimating: true, - updateWhileInteracting: true - }); - - /** - * @const - * @private - * @type {Object.<string, function(ol.Feature, ol.geom.Geometry)>} - */ - this.SEGMENT_WRITERS_ = { - 'Point': this.writePointGeometry_, - 'LineString': this.writeLineStringGeometry_, - 'LinearRing': this.writeLineStringGeometry_, - 'Polygon': this.writePolygonGeometry_, - 'MultiPoint': this.writeMultiPointGeometry_, - 'MultiLineString': this.writeMultiLineStringGeometry_, - 'MultiPolygon': this.writeMultiPolygonGeometry_, - 'Circle': this.writeCircleGeometry_, - 'GeometryCollection': this.writeGeometryCollectionGeometry_ - }; - - - /** - * @type {ol.source.Vector} - * @private - */ - this.source_ = null; - - var features; - if (options.source) { - this.source_ = options.source; - features = new ol.Collection(this.source_.getFeatures()); - ol.events.listen(this.source_, ol.source.VectorEventType.ADDFEATURE, - this.handleSourceAdd_, this); - ol.events.listen(this.source_, ol.source.VectorEventType.REMOVEFEATURE, - this.handleSourceRemove_, this); - } else { - features = options.features; - } - if (!features) { - throw new Error('The modify interaction requires features or a source'); - } - - /** - * @type {ol.Collection.<ol.Feature>} - * @private - */ - this.features_ = features; - - this.features_.forEach(this.addFeature_, this); - ol.events.listen(this.features_, ol.CollectionEventType.ADD, - this.handleFeatureAdd_, this); - ol.events.listen(this.features_, ol.CollectionEventType.REMOVE, - this.handleFeatureRemove_, this); - - /** - * @type {ol.MapBrowserPointerEvent} - * @private - */ - this.lastPointerEvent_ = null; - -}; -ol.inherits(ol.interaction.Modify, ol.interaction.Pointer); - - -/** - * @define {number} The segment index assigned to a circle's center when - * breaking up a cicrle into ModifySegmentDataType segments. - */ -ol.interaction.Modify.MODIFY_SEGMENT_CIRCLE_CENTER_INDEX = 0; - -/** - * @define {number} The segment index assigned to a circle's circumference when - * breaking up a circle into ModifySegmentDataType segments. - */ -ol.interaction.Modify.MODIFY_SEGMENT_CIRCLE_CIRCUMFERENCE_INDEX = 1; - - -/** - * @param {ol.Feature} feature Feature. - * @private - */ -ol.interaction.Modify.prototype.addFeature_ = function(feature) { - var geometry = feature.getGeometry(); - if (geometry && geometry.getType() in this.SEGMENT_WRITERS_) { - this.SEGMENT_WRITERS_[geometry.getType()].call(this, feature, geometry); - } - var map = this.getMap(); - if (map && map.isRendered() && this.getActive()) { - this.handlePointerAtPixel_(this.lastPixel_, map); - } - ol.events.listen(feature, ol.events.EventType.CHANGE, - this.handleFeatureChange_, this); -}; - - -/** - * @param {ol.MapBrowserPointerEvent} evt Map browser event - * @private - */ -ol.interaction.Modify.prototype.willModifyFeatures_ = function(evt) { - if (!this.modified_) { - this.modified_ = true; - this.dispatchEvent(new ol.interaction.Modify.Event( - ol.interaction.ModifyEventType.MODIFYSTART, this.features_, evt)); - } -}; - - -/** - * @param {ol.Feature} feature Feature. - * @private - */ -ol.interaction.Modify.prototype.removeFeature_ = function(feature) { - this.removeFeatureSegmentData_(feature); - // Remove the vertex feature if the collection of canditate features - // is empty. - if (this.vertexFeature_ && this.features_.getLength() === 0) { - this.overlay_.getSource().removeFeature(this.vertexFeature_); - this.vertexFeature_ = null; - } - ol.events.unlisten(feature, ol.events.EventType.CHANGE, - this.handleFeatureChange_, this); -}; - - -/** - * @param {ol.Feature} feature Feature. - * @private - */ -ol.interaction.Modify.prototype.removeFeatureSegmentData_ = function(feature) { - var rBush = this.rBush_; - var /** @type {Array.<ol.ModifySegmentDataType>} */ nodesToRemove = []; - rBush.forEach( - /** - * @param {ol.ModifySegmentDataType} node RTree node. - */ - function(node) { - if (feature === node.feature) { - nodesToRemove.push(node); - } - }); - for (var i = nodesToRemove.length - 1; i >= 0; --i) { - rBush.remove(nodesToRemove[i]); - } -}; - - -/** - * @inheritDoc - */ -ol.interaction.Modify.prototype.setActive = function(active) { - if (this.vertexFeature_ && !active) { - this.overlay_.getSource().removeFeature(this.vertexFeature_); - this.vertexFeature_ = null; - } - ol.interaction.Pointer.prototype.setActive.call(this, active); -}; - - -/** - * @inheritDoc - */ -ol.interaction.Modify.prototype.setMap = function(map) { - this.overlay_.setMap(map); - ol.interaction.Pointer.prototype.setMap.call(this, map); -}; - - -/** - * @param {ol.source.Vector.Event} event Event. - * @private - */ -ol.interaction.Modify.prototype.handleSourceAdd_ = function(event) { - if (event.feature) { - this.features_.push(event.feature); - } -}; - - -/** - * @param {ol.source.Vector.Event} event Event. - * @private - */ -ol.interaction.Modify.prototype.handleSourceRemove_ = function(event) { - if (event.feature) { - this.features_.remove(event.feature); - } -}; - - -/** - * @param {ol.Collection.Event} evt Event. - * @private - */ -ol.interaction.Modify.prototype.handleFeatureAdd_ = function(evt) { - this.addFeature_(/** @type {ol.Feature} */ (evt.element)); -}; - - -/** - * @param {ol.events.Event} evt Event. - * @private - */ -ol.interaction.Modify.prototype.handleFeatureChange_ = function(evt) { - if (!this.changingFeature_) { - var feature = /** @type {ol.Feature} */ (evt.target); - this.removeFeature_(feature); - this.addFeature_(feature); - } -}; - - -/** - * @param {ol.Collection.Event} evt Event. - * @private - */ -ol.interaction.Modify.prototype.handleFeatureRemove_ = function(evt) { - var feature = /** @type {ol.Feature} */ (evt.element); - this.removeFeature_(feature); -}; - - -/** - * @param {ol.Feature} feature Feature - * @param {ol.geom.Point} geometry Geometry. - * @private - */ -ol.interaction.Modify.prototype.writePointGeometry_ = function(feature, geometry) { - var coordinates = geometry.getCoordinates(); - var segmentData = /** @type {ol.ModifySegmentDataType} */ ({ - feature: feature, - geometry: geometry, - segment: [coordinates, coordinates] - }); - this.rBush_.insert(geometry.getExtent(), segmentData); -}; - - -/** - * @param {ol.Feature} feature Feature - * @param {ol.geom.MultiPoint} geometry Geometry. - * @private - */ -ol.interaction.Modify.prototype.writeMultiPointGeometry_ = function(feature, geometry) { - var points = geometry.getCoordinates(); - var coordinates, i, ii, segmentData; - for (i = 0, ii = points.length; i < ii; ++i) { - coordinates = points[i]; - segmentData = /** @type {ol.ModifySegmentDataType} */ ({ - feature: feature, - geometry: geometry, - depth: [i], - index: i, - segment: [coordinates, coordinates] - }); - this.rBush_.insert(geometry.getExtent(), segmentData); - } -}; - - -/** - * @param {ol.Feature} feature Feature - * @param {ol.geom.LineString} geometry Geometry. - * @private - */ -ol.interaction.Modify.prototype.writeLineStringGeometry_ = function(feature, geometry) { - var coordinates = geometry.getCoordinates(); - var i, ii, segment, segmentData; - for (i = 0, ii = coordinates.length - 1; i < ii; ++i) { - segment = coordinates.slice(i, i + 2); - segmentData = /** @type {ol.ModifySegmentDataType} */ ({ - feature: feature, - geometry: geometry, - index: i, - segment: segment - }); - this.rBush_.insert(ol.extent.boundingExtent(segment), segmentData); - } -}; - - -/** - * @param {ol.Feature} feature Feature - * @param {ol.geom.MultiLineString} geometry Geometry. - * @private - */ -ol.interaction.Modify.prototype.writeMultiLineStringGeometry_ = function(feature, geometry) { - var lines = geometry.getCoordinates(); - var coordinates, i, ii, j, jj, segment, segmentData; - for (j = 0, jj = lines.length; j < jj; ++j) { - coordinates = lines[j]; - for (i = 0, ii = coordinates.length - 1; i < ii; ++i) { - segment = coordinates.slice(i, i + 2); - segmentData = /** @type {ol.ModifySegmentDataType} */ ({ - feature: feature, - geometry: geometry, - depth: [j], - index: i, - segment: segment - }); - this.rBush_.insert(ol.extent.boundingExtent(segment), segmentData); - } - } -}; - - -/** - * @param {ol.Feature} feature Feature - * @param {ol.geom.Polygon} geometry Geometry. - * @private - */ -ol.interaction.Modify.prototype.writePolygonGeometry_ = function(feature, geometry) { - var rings = geometry.getCoordinates(); - var coordinates, i, ii, j, jj, segment, segmentData; - for (j = 0, jj = rings.length; j < jj; ++j) { - coordinates = rings[j]; - for (i = 0, ii = coordinates.length - 1; i < ii; ++i) { - segment = coordinates.slice(i, i + 2); - segmentData = /** @type {ol.ModifySegmentDataType} */ ({ - feature: feature, - geometry: geometry, - depth: [j], - index: i, - segment: segment - }); - this.rBush_.insert(ol.extent.boundingExtent(segment), segmentData); - } - } -}; - - -/** - * @param {ol.Feature} feature Feature - * @param {ol.geom.MultiPolygon} geometry Geometry. - * @private - */ -ol.interaction.Modify.prototype.writeMultiPolygonGeometry_ = function(feature, geometry) { - var polygons = geometry.getCoordinates(); - var coordinates, i, ii, j, jj, k, kk, rings, segment, segmentData; - for (k = 0, kk = polygons.length; k < kk; ++k) { - rings = polygons[k]; - for (j = 0, jj = rings.length; j < jj; ++j) { - coordinates = rings[j]; - for (i = 0, ii = coordinates.length - 1; i < ii; ++i) { - segment = coordinates.slice(i, i + 2); - segmentData = /** @type {ol.ModifySegmentDataType} */ ({ - feature: feature, - geometry: geometry, - depth: [j, k], - index: i, - segment: segment - }); - this.rBush_.insert(ol.extent.boundingExtent(segment), segmentData); - } - } - } -}; - - -/** - * We convert a circle into two segments. The segment at index - * {@link ol.interaction.Modify.MODIFY_SEGMENT_CIRCLE_CENTER_INDEX} is the - * circle's center (a point). The segment at index - * {@link ol.interaction.Modify.MODIFY_SEGMENT_CIRCLE_CIRCUMFERENCE_INDEX} is - * the circumference, and is not a line segment. - * - * @param {ol.Feature} feature Feature. - * @param {ol.geom.Circle} geometry Geometry. - * @private - */ -ol.interaction.Modify.prototype.writeCircleGeometry_ = function(feature, geometry) { - var coordinates = geometry.getCenter(); - var centerSegmentData = /** @type {ol.ModifySegmentDataType} */ ({ - feature: feature, - geometry: geometry, - index: ol.interaction.Modify.MODIFY_SEGMENT_CIRCLE_CENTER_INDEX, - segment: [coordinates, coordinates] - }); - var circumferenceSegmentData = /** @type {ol.ModifySegmentDataType} */ ({ - feature: feature, - geometry: geometry, - index: ol.interaction.Modify.MODIFY_SEGMENT_CIRCLE_CIRCUMFERENCE_INDEX, - segment: [coordinates, coordinates] - }); - var featureSegments = [centerSegmentData, circumferenceSegmentData]; - centerSegmentData.featureSegments = circumferenceSegmentData.featureSegments = featureSegments; - this.rBush_.insert(ol.extent.createOrUpdateFromCoordinate(coordinates), centerSegmentData); - this.rBush_.insert(geometry.getExtent(), circumferenceSegmentData); -}; - - -/** - * @param {ol.Feature} feature Feature - * @param {ol.geom.GeometryCollection} geometry Geometry. - * @private - */ -ol.interaction.Modify.prototype.writeGeometryCollectionGeometry_ = function(feature, geometry) { - var i, geometries = geometry.getGeometriesArray(); - for (i = 0; i < geometries.length; ++i) { - this.SEGMENT_WRITERS_[geometries[i].getType()].call( - this, feature, geometries[i]); - } -}; - - -/** - * @param {ol.Coordinate} coordinates Coordinates. - * @return {ol.Feature} Vertex feature. - * @private - */ -ol.interaction.Modify.prototype.createOrUpdateVertexFeature_ = function(coordinates) { - var vertexFeature = this.vertexFeature_; - if (!vertexFeature) { - vertexFeature = new ol.Feature(new ol.geom.Point(coordinates)); - this.vertexFeature_ = vertexFeature; - this.overlay_.getSource().addFeature(vertexFeature); - } else { - var geometry = /** @type {ol.geom.Point} */ (vertexFeature.getGeometry()); - geometry.setCoordinates(coordinates); - } - return vertexFeature; -}; - - -/** - * @param {ol.ModifySegmentDataType} a The first segment data. - * @param {ol.ModifySegmentDataType} b The second segment data. - * @return {number} The difference in indexes. - * @private - */ -ol.interaction.Modify.compareIndexes_ = function(a, b) { - return a.index - b.index; -}; - - -/** - * @param {ol.MapBrowserPointerEvent} evt Event. - * @return {boolean} Start drag sequence? - * @this {ol.interaction.Modify} - * @private - */ -ol.interaction.Modify.handleDownEvent_ = function(evt) { - if (!this.condition_(evt)) { - return false; - } - this.handlePointerAtPixel_(evt.pixel, evt.map); - var pixelCoordinate = evt.map.getCoordinateFromPixel(evt.pixel); - this.dragSegments_.length = 0; - this.modified_ = false; - var vertexFeature = this.vertexFeature_; - if (vertexFeature) { - var insertVertices = []; - var geometry = /** @type {ol.geom.Point} */ (vertexFeature.getGeometry()); - var vertex = geometry.getCoordinates(); - var vertexExtent = ol.extent.boundingExtent([vertex]); - var segmentDataMatches = this.rBush_.getInExtent(vertexExtent); - var componentSegments = {}; - segmentDataMatches.sort(ol.interaction.Modify.compareIndexes_); - for (var i = 0, ii = segmentDataMatches.length; i < ii; ++i) { - var segmentDataMatch = segmentDataMatches[i]; - var segment = segmentDataMatch.segment; - var uid = ol.getUid(segmentDataMatch.feature); - var depth = segmentDataMatch.depth; - if (depth) { - uid += '-' + depth.join('-'); // separate feature components - } - if (!componentSegments[uid]) { - componentSegments[uid] = new Array(2); - } - if (segmentDataMatch.geometry.getType() === ol.geom.GeometryType.CIRCLE && - segmentDataMatch.index === ol.interaction.Modify.MODIFY_SEGMENT_CIRCLE_CIRCUMFERENCE_INDEX) { - - var closestVertex = ol.interaction.Modify.closestOnSegmentData_(pixelCoordinate, segmentDataMatch); - if (ol.coordinate.equals(closestVertex, vertex) && !componentSegments[uid][0]) { - this.dragSegments_.push([segmentDataMatch, 0]); - componentSegments[uid][0] = segmentDataMatch; - } - } else if (ol.coordinate.equals(segment[0], vertex) && - !componentSegments[uid][0]) { - this.dragSegments_.push([segmentDataMatch, 0]); - componentSegments[uid][0] = segmentDataMatch; - } else if (ol.coordinate.equals(segment[1], vertex) && - !componentSegments[uid][1]) { - - // prevent dragging closed linestrings by the connecting node - if ((segmentDataMatch.geometry.getType() === - ol.geom.GeometryType.LINE_STRING || - segmentDataMatch.geometry.getType() === - ol.geom.GeometryType.MULTI_LINE_STRING) && - componentSegments[uid][0] && - componentSegments[uid][0].index === 0) { - continue; - } - - this.dragSegments_.push([segmentDataMatch, 1]); - componentSegments[uid][1] = segmentDataMatch; - } else if (this.insertVertexCondition_(evt) && ol.getUid(segment) in this.vertexSegments_ && - (!componentSegments[uid][0] && !componentSegments[uid][1])) { - insertVertices.push([segmentDataMatch, vertex]); - } - } - if (insertVertices.length) { - this.willModifyFeatures_(evt); - } - for (var j = insertVertices.length - 1; j >= 0; --j) { - this.insertVertex_.apply(this, insertVertices[j]); - } - } - return !!this.vertexFeature_; -}; - - -/** - * @param {ol.MapBrowserPointerEvent} evt Event. - * @this {ol.interaction.Modify} - * @private - */ -ol.interaction.Modify.handleDragEvent_ = function(evt) { - this.ignoreNextSingleClick_ = false; - this.willModifyFeatures_(evt); - - var vertex = evt.coordinate; - for (var i = 0, ii = this.dragSegments_.length; i < ii; ++i) { - var dragSegment = this.dragSegments_[i]; - var segmentData = dragSegment[0]; - var depth = segmentData.depth; - var geometry = segmentData.geometry; - var coordinates; - var segment = segmentData.segment; - var index = dragSegment[1]; - - while (vertex.length < geometry.getStride()) { - vertex.push(segment[index][vertex.length]); - } - - switch (geometry.getType()) { - case ol.geom.GeometryType.POINT: - coordinates = vertex; - segment[0] = segment[1] = vertex; - break; - case ol.geom.GeometryType.MULTI_POINT: - coordinates = geometry.getCoordinates(); - coordinates[segmentData.index] = vertex; - segment[0] = segment[1] = vertex; - break; - case ol.geom.GeometryType.LINE_STRING: - coordinates = geometry.getCoordinates(); - coordinates[segmentData.index + index] = vertex; - segment[index] = vertex; - break; - case ol.geom.GeometryType.MULTI_LINE_STRING: - coordinates = geometry.getCoordinates(); - coordinates[depth[0]][segmentData.index + index] = vertex; - segment[index] = vertex; - break; - case ol.geom.GeometryType.POLYGON: - coordinates = geometry.getCoordinates(); - coordinates[depth[0]][segmentData.index + index] = vertex; - segment[index] = vertex; - break; - case ol.geom.GeometryType.MULTI_POLYGON: - coordinates = geometry.getCoordinates(); - coordinates[depth[1]][depth[0]][segmentData.index + index] = vertex; - segment[index] = vertex; - break; - case ol.geom.GeometryType.CIRCLE: - segment[0] = segment[1] = vertex; - if (segmentData.index === ol.interaction.Modify.MODIFY_SEGMENT_CIRCLE_CENTER_INDEX) { - this.changingFeature_ = true; - geometry.setCenter(vertex); - this.changingFeature_ = false; - } else { // We're dragging the circle's circumference: - this.changingFeature_ = true; - geometry.setRadius(ol.coordinate.distance(geometry.getCenter(), vertex)); - this.changingFeature_ = false; - } - break; - default: - // pass - } - - if (coordinates) { - this.setGeometryCoordinates_(geometry, coordinates); - } - } - this.createOrUpdateVertexFeature_(vertex); -}; - - -/** - * @param {ol.MapBrowserPointerEvent} evt Event. - * @return {boolean} Stop drag sequence? - * @this {ol.interaction.Modify} - * @private - */ -ol.interaction.Modify.handleUpEvent_ = function(evt) { - var segmentData; - var geometry; - for (var i = this.dragSegments_.length - 1; i >= 0; --i) { - segmentData = this.dragSegments_[i][0]; - geometry = segmentData.geometry; - if (geometry.getType() === ol.geom.GeometryType.CIRCLE) { - // Update a circle object in the R* bush: - var coordinates = geometry.getCenter(); - var centerSegmentData = segmentData.featureSegments[0]; - var circumferenceSegmentData = segmentData.featureSegments[1]; - centerSegmentData.segment[0] = centerSegmentData.segment[1] = coordinates; - circumferenceSegmentData.segment[0] = circumferenceSegmentData.segment[1] = coordinates; - this.rBush_.update(ol.extent.createOrUpdateFromCoordinate(coordinates), centerSegmentData); - this.rBush_.update(geometry.getExtent(), circumferenceSegmentData); - } else { - this.rBush_.update(ol.extent.boundingExtent(segmentData.segment), - segmentData); - } - } - if (this.modified_) { - this.dispatchEvent(new ol.interaction.Modify.Event( - ol.interaction.ModifyEventType.MODIFYEND, this.features_, evt)); - this.modified_ = false; - } - return false; -}; - - -/** - * Handles the {@link ol.MapBrowserEvent map browser event} and may modify the - * geometry. - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} `false` to stop event propagation. - * @this {ol.interaction.Modify} - * @api - */ -ol.interaction.Modify.handleEvent = function(mapBrowserEvent) { - if (!(mapBrowserEvent instanceof ol.MapBrowserPointerEvent)) { - return true; - } - this.lastPointerEvent_ = mapBrowserEvent; - - var handled; - if (!mapBrowserEvent.map.getView().getHints()[ol.ViewHint.INTERACTING] && - mapBrowserEvent.type == ol.MapBrowserEventType.POINTERMOVE && - !this.handlingDownUpSequence) { - this.handlePointerMove_(mapBrowserEvent); - } - if (this.vertexFeature_ && this.deleteCondition_(mapBrowserEvent)) { - if (mapBrowserEvent.type != ol.MapBrowserEventType.SINGLECLICK || - !this.ignoreNextSingleClick_) { - handled = this.removePoint(); - } else { - handled = true; - } - } - - if (mapBrowserEvent.type == ol.MapBrowserEventType.SINGLECLICK) { - this.ignoreNextSingleClick_ = false; - } - - return ol.interaction.Pointer.handleEvent.call(this, mapBrowserEvent) && - !handled; -}; - - -/** - * @param {ol.MapBrowserEvent} evt Event. - * @private - */ -ol.interaction.Modify.prototype.handlePointerMove_ = function(evt) { - this.lastPixel_ = evt.pixel; - this.handlePointerAtPixel_(evt.pixel, evt.map); -}; - - -/** - * @param {ol.Pixel} pixel Pixel - * @param {ol.PluggableMap} map Map. - * @private - */ -ol.interaction.Modify.prototype.handlePointerAtPixel_ = function(pixel, map) { - var pixelCoordinate = map.getCoordinateFromPixel(pixel); - var sortByDistance = function(a, b) { - return ol.interaction.Modify.pointDistanceToSegmentDataSquared_(pixelCoordinate, a) - - ol.interaction.Modify.pointDistanceToSegmentDataSquared_(pixelCoordinate, b); - }; - - var box = ol.extent.buffer( - ol.extent.createOrUpdateFromCoordinate(pixelCoordinate), - map.getView().getResolution() * this.pixelTolerance_); - - var rBush = this.rBush_; - var nodes = rBush.getInExtent(box); - if (nodes.length > 0) { - nodes.sort(sortByDistance); - var node = nodes[0]; - var closestSegment = node.segment; - var vertex = ol.interaction.Modify.closestOnSegmentData_(pixelCoordinate, node); - var vertexPixel = map.getPixelFromCoordinate(vertex); - var dist = ol.coordinate.distance(pixel, vertexPixel); - if (dist <= this.pixelTolerance_) { - var vertexSegments = {}; - - if (node.geometry.getType() === ol.geom.GeometryType.CIRCLE && - node.index === ol.interaction.Modify.MODIFY_SEGMENT_CIRCLE_CIRCUMFERENCE_INDEX) { - - this.snappedToVertex_ = true; - this.createOrUpdateVertexFeature_(vertex); - } else { - var pixel1 = map.getPixelFromCoordinate(closestSegment[0]); - var pixel2 = map.getPixelFromCoordinate(closestSegment[1]); - var squaredDist1 = ol.coordinate.squaredDistance(vertexPixel, pixel1); - var squaredDist2 = ol.coordinate.squaredDistance(vertexPixel, pixel2); - dist = Math.sqrt(Math.min(squaredDist1, squaredDist2)); - this.snappedToVertex_ = dist <= this.pixelTolerance_; - if (this.snappedToVertex_) { - vertex = squaredDist1 > squaredDist2 ? - closestSegment[1] : closestSegment[0]; - } - this.createOrUpdateVertexFeature_(vertex); - var segment; - for (var i = 1, ii = nodes.length; i < ii; ++i) { - segment = nodes[i].segment; - if ((ol.coordinate.equals(closestSegment[0], segment[0]) && - ol.coordinate.equals(closestSegment[1], segment[1]) || - (ol.coordinate.equals(closestSegment[0], segment[1]) && - ol.coordinate.equals(closestSegment[1], segment[0])))) { - vertexSegments[ol.getUid(segment)] = true; - } else { - break; - } - } - } - - vertexSegments[ol.getUid(closestSegment)] = true; - this.vertexSegments_ = vertexSegments; - return; - } - } - if (this.vertexFeature_) { - this.overlay_.getSource().removeFeature(this.vertexFeature_); - this.vertexFeature_ = null; - } -}; - - -/** - * Returns the distance from a point to a line segment. - * - * @param {ol.Coordinate} pointCoordinates The coordinates of the point from - * which to calculate the distance. - * @param {ol.ModifySegmentDataType} segmentData The object describing the line - * segment we are calculating the distance to. - * @return {number} The square of the distance between a point and a line segment. - */ -ol.interaction.Modify.pointDistanceToSegmentDataSquared_ = function(pointCoordinates, segmentData) { - var geometry = segmentData.geometry; - - if (geometry.getType() === ol.geom.GeometryType.CIRCLE) { - var circleGeometry = /** @type {ol.geom.Circle} */ (geometry); - - if (segmentData.index === ol.interaction.Modify.MODIFY_SEGMENT_CIRCLE_CIRCUMFERENCE_INDEX) { - var distanceToCenterSquared = - ol.coordinate.squaredDistance(circleGeometry.getCenter(), pointCoordinates); - var distanceToCircumference = - Math.sqrt(distanceToCenterSquared) - circleGeometry.getRadius(); - return distanceToCircumference * distanceToCircumference; - } - } - return ol.coordinate.squaredDistanceToSegment(pointCoordinates, segmentData.segment); -}; - -/** - * Returns the point closest to a given line segment. - * - * @param {ol.Coordinate} pointCoordinates The point to which a closest point - * should be found. - * @param {ol.ModifySegmentDataType} segmentData The object describing the line - * segment which should contain the closest point. - * @return {ol.Coordinate} The point closest to the specified line segment. - */ -ol.interaction.Modify.closestOnSegmentData_ = function(pointCoordinates, segmentData) { - var geometry = segmentData.geometry; - - if (geometry.getType() === ol.geom.GeometryType.CIRCLE && - segmentData.index === ol.interaction.Modify.MODIFY_SEGMENT_CIRCLE_CIRCUMFERENCE_INDEX) { - return geometry.getClosestPoint(pointCoordinates); - } - return ol.coordinate.closestOnSegment(pointCoordinates, segmentData.segment); -}; - - -/** - * @param {ol.ModifySegmentDataType} segmentData Segment data. - * @param {ol.Coordinate} vertex Vertex. - * @private - */ -ol.interaction.Modify.prototype.insertVertex_ = function(segmentData, vertex) { - var segment = segmentData.segment; - var feature = segmentData.feature; - var geometry = segmentData.geometry; - var depth = segmentData.depth; - var index = /** @type {number} */ (segmentData.index); - var coordinates; - - while (vertex.length < geometry.getStride()) { - vertex.push(0); - } - - switch (geometry.getType()) { - case ol.geom.GeometryType.MULTI_LINE_STRING: - coordinates = geometry.getCoordinates(); - coordinates[depth[0]].splice(index + 1, 0, vertex); - break; - case ol.geom.GeometryType.POLYGON: - coordinates = geometry.getCoordinates(); - coordinates[depth[0]].splice(index + 1, 0, vertex); - break; - case ol.geom.GeometryType.MULTI_POLYGON: - coordinates = geometry.getCoordinates(); - coordinates[depth[1]][depth[0]].splice(index + 1, 0, vertex); - break; - case ol.geom.GeometryType.LINE_STRING: - coordinates = geometry.getCoordinates(); - coordinates.splice(index + 1, 0, vertex); - break; - default: - return; - } - - this.setGeometryCoordinates_(geometry, coordinates); - var rTree = this.rBush_; - rTree.remove(segmentData); - this.updateSegmentIndices_(geometry, index, depth, 1); - var newSegmentData = /** @type {ol.ModifySegmentDataType} */ ({ - segment: [segment[0], vertex], - feature: feature, - geometry: geometry, - depth: depth, - index: index - }); - rTree.insert(ol.extent.boundingExtent(newSegmentData.segment), - newSegmentData); - this.dragSegments_.push([newSegmentData, 1]); - - var newSegmentData2 = /** @type {ol.ModifySegmentDataType} */ ({ - segment: [vertex, segment[1]], - feature: feature, - geometry: geometry, - depth: depth, - index: index + 1 - }); - rTree.insert(ol.extent.boundingExtent(newSegmentData2.segment), - newSegmentData2); - this.dragSegments_.push([newSegmentData2, 0]); - this.ignoreNextSingleClick_ = true; -}; - -/** - * Removes the vertex currently being pointed. - * @return {boolean} True when a vertex was removed. - * @api - */ -ol.interaction.Modify.prototype.removePoint = function() { - if (this.lastPointerEvent_ && this.lastPointerEvent_.type != ol.MapBrowserEventType.POINTERDRAG) { - var evt = this.lastPointerEvent_; - this.willModifyFeatures_(evt); - this.removeVertex_(); - this.dispatchEvent(new ol.interaction.Modify.Event( - ol.interaction.ModifyEventType.MODIFYEND, this.features_, evt)); - this.modified_ = false; - return true; - } - return false; -}; - -/** - * Removes a vertex from all matching features. - * @return {boolean} True when a vertex was removed. - * @private - */ -ol.interaction.Modify.prototype.removeVertex_ = function() { - var dragSegments = this.dragSegments_; - var segmentsByFeature = {}; - var deleted = false; - var component, coordinates, dragSegment, geometry, i, index, left; - var newIndex, right, segmentData, uid; - for (i = dragSegments.length - 1; i >= 0; --i) { - dragSegment = dragSegments[i]; - segmentData = dragSegment[0]; - uid = ol.getUid(segmentData.feature); - if (segmentData.depth) { - // separate feature components - uid += '-' + segmentData.depth.join('-'); - } - if (!(uid in segmentsByFeature)) { - segmentsByFeature[uid] = {}; - } - if (dragSegment[1] === 0) { - segmentsByFeature[uid].right = segmentData; - segmentsByFeature[uid].index = segmentData.index; - } else if (dragSegment[1] == 1) { - segmentsByFeature[uid].left = segmentData; - segmentsByFeature[uid].index = segmentData.index + 1; - } - - } - for (uid in segmentsByFeature) { - right = segmentsByFeature[uid].right; - left = segmentsByFeature[uid].left; - index = segmentsByFeature[uid].index; - newIndex = index - 1; - if (left !== undefined) { - segmentData = left; - } else { - segmentData = right; - } - if (newIndex < 0) { - newIndex = 0; - } - geometry = segmentData.geometry; - coordinates = geometry.getCoordinates(); - component = coordinates; - deleted = false; - switch (geometry.getType()) { - case ol.geom.GeometryType.MULTI_LINE_STRING: - if (coordinates[segmentData.depth[0]].length > 2) { - coordinates[segmentData.depth[0]].splice(index, 1); - deleted = true; - } - break; - case ol.geom.GeometryType.LINE_STRING: - if (coordinates.length > 2) { - coordinates.splice(index, 1); - deleted = true; - } - break; - case ol.geom.GeometryType.MULTI_POLYGON: - component = component[segmentData.depth[1]]; - /* falls through */ - case ol.geom.GeometryType.POLYGON: - component = component[segmentData.depth[0]]; - if (component.length > 4) { - if (index == component.length - 1) { - index = 0; - } - component.splice(index, 1); - deleted = true; - if (index === 0) { - // close the ring again - component.pop(); - component.push(component[0]); - newIndex = component.length - 1; - } - } - break; - default: - // pass - } - - if (deleted) { - this.setGeometryCoordinates_(geometry, coordinates); - var segments = []; - if (left !== undefined) { - this.rBush_.remove(left); - segments.push(left.segment[0]); - } - if (right !== undefined) { - this.rBush_.remove(right); - segments.push(right.segment[1]); - } - if (left !== undefined && right !== undefined) { - var newSegmentData = /** @type {ol.ModifySegmentDataType} */ ({ - depth: segmentData.depth, - feature: segmentData.feature, - geometry: segmentData.geometry, - index: newIndex, - segment: segments - }); - this.rBush_.insert(ol.extent.boundingExtent(newSegmentData.segment), - newSegmentData); - } - this.updateSegmentIndices_(geometry, index, segmentData.depth, -1); - if (this.vertexFeature_) { - this.overlay_.getSource().removeFeature(this.vertexFeature_); - this.vertexFeature_ = null; - } - dragSegments.length = 0; - } - - } - return deleted; -}; - - -/** - * @param {ol.geom.SimpleGeometry} geometry Geometry. - * @param {Array} coordinates Coordinates. - * @private - */ -ol.interaction.Modify.prototype.setGeometryCoordinates_ = function(geometry, coordinates) { - this.changingFeature_ = true; - geometry.setCoordinates(coordinates); - this.changingFeature_ = false; -}; - - -/** - * @param {ol.geom.SimpleGeometry} geometry Geometry. - * @param {number} index Index. - * @param {Array.<number>|undefined} depth Depth. - * @param {number} delta Delta (1 or -1). - * @private - */ -ol.interaction.Modify.prototype.updateSegmentIndices_ = function( - geometry, index, depth, delta) { - this.rBush_.forEachInExtent(geometry.getExtent(), function(segmentDataMatch) { - if (segmentDataMatch.geometry === geometry && - (depth === undefined || segmentDataMatch.depth === undefined || - ol.array.equals(segmentDataMatch.depth, depth)) && - segmentDataMatch.index > index) { - segmentDataMatch.index += delta; - } - }); -}; - - -/** - * @return {ol.StyleFunction} Styles. - */ -ol.interaction.Modify.getDefaultStyleFunction = function() { - var style = ol.style.Style.createDefaultEditing(); - return function(feature, resolution) { - return style[ol.geom.GeometryType.POINT]; - }; -}; - - -/** - * @classdesc - * Events emitted by {@link ol.interaction.Modify} instances are instances of - * this type. - * - * @constructor - * @extends {ol.events.Event} - * @implements {oli.ModifyEvent} - * @param {ol.interaction.ModifyEventType} type Type. - * @param {ol.Collection.<ol.Feature>} features The features modified. - * @param {ol.MapBrowserPointerEvent} mapBrowserPointerEvent Associated - * {@link ol.MapBrowserPointerEvent}. - */ -ol.interaction.Modify.Event = function(type, features, mapBrowserPointerEvent) { - - ol.events.Event.call(this, type); - - /** - * The features being modified. - * @type {ol.Collection.<ol.Feature>} - * @api - */ - this.features = features; - - /** - * Associated {@link ol.MapBrowserEvent}. - * @type {ol.MapBrowserEvent} - * @api - */ - this.mapBrowserEvent = mapBrowserPointerEvent; -}; -ol.inherits(ol.interaction.Modify.Event, ol.events.Event); - -goog.provide('ol.interaction.Select'); - -goog.require('ol'); -goog.require('ol.CollectionEventType'); -goog.require('ol.array'); -goog.require('ol.events'); -goog.require('ol.events.Event'); -goog.require('ol.events.condition'); -goog.require('ol.functions'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.interaction.Interaction'); -goog.require('ol.layer.Vector'); -goog.require('ol.obj'); -goog.require('ol.source.Vector'); -goog.require('ol.style.Style'); - - -/** - * @classdesc - * Interaction for selecting vector features. By default, selected features are - * styled differently, so this interaction can be used for visual highlighting, - * as well as selecting features for other actions, such as modification or - * output. There are three ways of controlling which features are selected: - * using the browser event as defined by the `condition` and optionally the - * `toggle`, `add`/`remove`, and `multi` options; a `layers` filter; and a - * further feature filter using the `filter` option. - * - * Selected features are added to an internal unmanaged layer. - * - * @constructor - * @extends {ol.interaction.Interaction} - * @param {olx.interaction.SelectOptions=} opt_options Options. - * @fires ol.interaction.Select.Event - * @api - */ -ol.interaction.Select = function(opt_options) { - - ol.interaction.Interaction.call(this, { - handleEvent: ol.interaction.Select.handleEvent - }); - - var options = opt_options ? opt_options : {}; - - /** - * @private - * @type {ol.EventsConditionType} - */ - this.condition_ = options.condition ? - options.condition : ol.events.condition.singleClick; - - /** - * @private - * @type {ol.EventsConditionType} - */ - this.addCondition_ = options.addCondition ? - options.addCondition : ol.events.condition.never; - - /** - * @private - * @type {ol.EventsConditionType} - */ - this.removeCondition_ = options.removeCondition ? - options.removeCondition : ol.events.condition.never; - - /** - * @private - * @type {ol.EventsConditionType} - */ - this.toggleCondition_ = options.toggleCondition ? - options.toggleCondition : ol.events.condition.shiftKeyOnly; - - /** - * @private - * @type {boolean} - */ - this.multi_ = options.multi ? options.multi : false; - - /** - * @private - * @type {ol.SelectFilterFunction} - */ - this.filter_ = options.filter ? options.filter : - ol.functions.TRUE; - - /** - * @private - * @type {number} - */ - this.hitTolerance_ = options.hitTolerance ? options.hitTolerance : 0; - - var featureOverlay = new ol.layer.Vector({ - source: new ol.source.Vector({ - useSpatialIndex: false, - features: options.features, - wrapX: options.wrapX - }), - style: options.style ? options.style : - ol.interaction.Select.getDefaultStyleFunction(), - updateWhileAnimating: true, - updateWhileInteracting: true - }); - - /** - * @private - * @type {ol.layer.Vector} - */ - this.featureOverlay_ = featureOverlay; - - /** @type {function(ol.layer.Layer): boolean} */ - var layerFilter; - if (options.layers) { - if (typeof options.layers === 'function') { - layerFilter = options.layers; - } else { - var layers = options.layers; - layerFilter = function(layer) { - return ol.array.includes(layers, layer); - }; - } - } else { - layerFilter = ol.functions.TRUE; - } - - /** - * @private - * @type {function(ol.layer.Layer): boolean} - */ - this.layerFilter_ = layerFilter; - - /** - * An association between selected feature (key) - * and layer (value) - * @private - * @type {Object.<number, ol.layer.Layer>} - */ - this.featureLayerAssociation_ = {}; - - var features = this.featureOverlay_.getSource().getFeaturesCollection(); - ol.events.listen(features, ol.CollectionEventType.ADD, - this.addFeature_, this); - ol.events.listen(features, ol.CollectionEventType.REMOVE, - this.removeFeature_, this); - -}; -ol.inherits(ol.interaction.Select, ol.interaction.Interaction); - - -/** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @param {ol.layer.Layer} layer Layer. - * @private - */ -ol.interaction.Select.prototype.addFeatureLayerAssociation_ = function(feature, layer) { - var key = ol.getUid(feature); - this.featureLayerAssociation_[key] = layer; -}; - - -/** - * Get the selected features. - * @return {ol.Collection.<ol.Feature>} Features collection. - * @api - */ -ol.interaction.Select.prototype.getFeatures = function() { - return this.featureOverlay_.getSource().getFeaturesCollection(); -}; - - -/** - * Returns the Hit-detection tolerance. - * @returns {number} Hit tolerance in pixels. - * @api - */ -ol.interaction.Select.prototype.getHitTolerance = function() { - return this.hitTolerance_; -}; - - -/** - * Returns the associated {@link ol.layer.Vector vectorlayer} of - * the (last) selected feature. Note that this will not work with any - * programmatic method like pushing features to - * {@link ol.interaction.Select#getFeatures collection}. - * @param {ol.Feature|ol.render.Feature} feature Feature - * @return {ol.layer.Vector} Layer. - * @api - */ -ol.interaction.Select.prototype.getLayer = function(feature) { - var key = ol.getUid(feature); - return /** @type {ol.layer.Vector} */ (this.featureLayerAssociation_[key]); -}; - - -/** - * Handles the {@link ol.MapBrowserEvent map browser event} and may change the - * selected state of features. - * @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event. - * @return {boolean} `false` to stop event propagation. - * @this {ol.interaction.Select} - * @api - */ -ol.interaction.Select.handleEvent = function(mapBrowserEvent) { - if (!this.condition_(mapBrowserEvent)) { - return true; - } - var add = this.addCondition_(mapBrowserEvent); - var remove = this.removeCondition_(mapBrowserEvent); - var toggle = this.toggleCondition_(mapBrowserEvent); - var set = !add && !remove && !toggle; - var map = mapBrowserEvent.map; - var features = this.featureOverlay_.getSource().getFeaturesCollection(); - var deselected = []; - var selected = []; - if (set) { - // Replace the currently selected feature(s) with the feature(s) at the - // pixel, or clear the selected feature(s) if there is no feature at - // the pixel. - ol.obj.clear(this.featureLayerAssociation_); - map.forEachFeatureAtPixel(mapBrowserEvent.pixel, - ( - /** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @param {ol.layer.Layer} layer Layer. - * @return {boolean|undefined} Continue to iterate over the features. - */ - function(feature, layer) { - if (this.filter_(feature, layer)) { - selected.push(feature); - this.addFeatureLayerAssociation_(feature, layer); - return !this.multi_; - } - }).bind(this), { - layerFilter: this.layerFilter_, - hitTolerance: this.hitTolerance_ - }); - var i; - for (i = features.getLength() - 1; i >= 0; --i) { - var feature = features.item(i); - var index = selected.indexOf(feature); - if (index > -1) { - // feature is already selected - selected.splice(index, 1); - } else { - features.remove(feature); - deselected.push(feature); - } - } - if (selected.length !== 0) { - features.extend(selected); - } - } else { - // Modify the currently selected feature(s). - map.forEachFeatureAtPixel(mapBrowserEvent.pixel, - ( - /** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @param {ol.layer.Layer} layer Layer. - * @return {boolean|undefined} Continue to iterate over the features. - */ - function(feature, layer) { - if (this.filter_(feature, layer)) { - if ((add || toggle) && - !ol.array.includes(features.getArray(), feature)) { - selected.push(feature); - this.addFeatureLayerAssociation_(feature, layer); - } else if ((remove || toggle) && - ol.array.includes(features.getArray(), feature)) { - deselected.push(feature); - this.removeFeatureLayerAssociation_(feature); - } - return !this.multi_; - } - }).bind(this), { - layerFilter: this.layerFilter_, - hitTolerance: this.hitTolerance_ - }); - var j; - for (j = deselected.length - 1; j >= 0; --j) { - features.remove(deselected[j]); - } - features.extend(selected); - } - if (selected.length > 0 || deselected.length > 0) { - this.dispatchEvent( - new ol.interaction.Select.Event(ol.interaction.Select.EventType_.SELECT, - selected, deselected, mapBrowserEvent)); - } - return ol.events.condition.pointerMove(mapBrowserEvent); -}; - - -/** - * Hit-detection tolerance. Pixels inside the radius around the given position - * will be checked for features. This only works for the canvas renderer and - * not for WebGL. - * @param {number} hitTolerance Hit tolerance in pixels. - * @api - */ -ol.interaction.Select.prototype.setHitTolerance = function(hitTolerance) { - this.hitTolerance_ = hitTolerance; -}; - - -/** - * Remove the interaction from its current map, if any, and attach it to a new - * map, if any. Pass `null` to just remove the interaction from the current map. - * @param {ol.PluggableMap} map Map. - * @override - * @api - */ -ol.interaction.Select.prototype.setMap = function(map) { - var currentMap = this.getMap(); - var selectedFeatures = - this.featureOverlay_.getSource().getFeaturesCollection(); - if (currentMap) { - selectedFeatures.forEach(currentMap.unskipFeature, currentMap); - } - ol.interaction.Interaction.prototype.setMap.call(this, map); - this.featureOverlay_.setMap(map); - if (map) { - selectedFeatures.forEach(map.skipFeature, map); - } -}; - - -/** - * @return {ol.StyleFunction} Styles. - */ -ol.interaction.Select.getDefaultStyleFunction = function() { - var styles = ol.style.Style.createDefaultEditing(); - ol.array.extend(styles[ol.geom.GeometryType.POLYGON], - styles[ol.geom.GeometryType.LINE_STRING]); - ol.array.extend(styles[ol.geom.GeometryType.GEOMETRY_COLLECTION], - styles[ol.geom.GeometryType.LINE_STRING]); - - return function(feature, resolution) { - if (!feature.getGeometry()) { - return null; - } - return styles[feature.getGeometry().getType()]; - }; -}; - - -/** - * @param {ol.Collection.Event} evt Event. - * @private - */ -ol.interaction.Select.prototype.addFeature_ = function(evt) { - var map = this.getMap(); - if (map) { - map.skipFeature(/** @type {ol.Feature} */ (evt.element)); - } -}; - - -/** - * @param {ol.Collection.Event} evt Event. - * @private - */ -ol.interaction.Select.prototype.removeFeature_ = function(evt) { - var map = this.getMap(); - if (map) { - map.unskipFeature(/** @type {ol.Feature} */ (evt.element)); - } -}; - - -/** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @private - */ -ol.interaction.Select.prototype.removeFeatureLayerAssociation_ = function(feature) { - var key = ol.getUid(feature); - delete this.featureLayerAssociation_[key]; -}; - - -/** - * @classdesc - * Events emitted by {@link ol.interaction.Select} instances are instances of - * this type. - * - * @param {ol.interaction.Select.EventType_} type The event type. - * @param {Array.<ol.Feature>} selected Selected features. - * @param {Array.<ol.Feature>} deselected Deselected features. - * @param {ol.MapBrowserEvent} mapBrowserEvent Associated - * {@link ol.MapBrowserEvent}. - * @implements {oli.SelectEvent} - * @extends {ol.events.Event} - * @constructor - */ -ol.interaction.Select.Event = function(type, selected, deselected, mapBrowserEvent) { - ol.events.Event.call(this, type); - - /** - * Selected features array. - * @type {Array.<ol.Feature>} - * @api - */ - this.selected = selected; - - /** - * Deselected features array. - * @type {Array.<ol.Feature>} - * @api - */ - this.deselected = deselected; - - /** - * Associated {@link ol.MapBrowserEvent}. - * @type {ol.MapBrowserEvent} - * @api - */ - this.mapBrowserEvent = mapBrowserEvent; -}; -ol.inherits(ol.interaction.Select.Event, ol.events.Event); - - -/** - * @enum {string} - * @private - */ -ol.interaction.Select.EventType_ = { - /** - * Triggered when feature(s) has been (de)selected. - * @event ol.interaction.Select.Event#select - * @api - */ - SELECT: 'select' -}; - -goog.provide('ol.interaction.Snap'); - -goog.require('ol'); -goog.require('ol.Collection'); -goog.require('ol.CollectionEventType'); -goog.require('ol.coordinate'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.extent'); -goog.require('ol.functions'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.geom.Polygon'); -goog.require('ol.interaction.Pointer'); -goog.require('ol.obj'); -goog.require('ol.source.Vector'); -goog.require('ol.source.VectorEventType'); -goog.require('ol.structs.RBush'); - - -/** - * @classdesc - * Handles snapping of vector features while modifying or drawing them. The - * features can come from a {@link ol.source.Vector} or {@link ol.Collection} - * Any interaction object that allows the user to interact - * with the features using the mouse can benefit from the snapping, as long - * as it is added before. - * - * The snap interaction modifies map browser event `coordinate` and `pixel` - * properties to force the snap to occur to any interaction that them. - * - * Example: - * - * var snap = new ol.interaction.Snap({ - * source: source - * }); - * - * @constructor - * @extends {ol.interaction.Pointer} - * @param {olx.interaction.SnapOptions=} opt_options Options. - * @api - */ -ol.interaction.Snap = function(opt_options) { - - ol.interaction.Pointer.call(this, { - handleEvent: ol.interaction.Snap.handleEvent_, - handleDownEvent: ol.functions.TRUE, - handleUpEvent: ol.interaction.Snap.handleUpEvent_ - }); - - var options = opt_options ? opt_options : {}; - - /** - * @type {ol.source.Vector} - * @private - */ - this.source_ = options.source ? options.source : null; - - /** - * @private - * @type {boolean} - */ - this.vertex_ = options.vertex !== undefined ? options.vertex : true; - - /** - * @private - * @type {boolean} - */ - this.edge_ = options.edge !== undefined ? options.edge : true; - - /** - * @type {ol.Collection.<ol.Feature>} - * @private - */ - this.features_ = options.features ? options.features : null; - - /** - * @type {Array.<ol.EventsKey>} - * @private - */ - this.featuresListenerKeys_ = []; - - /** - * @type {Object.<number, ol.EventsKey>} - * @private - */ - this.featureChangeListenerKeys_ = {}; - - /** - * Extents are preserved so indexed segment can be quickly removed - * when its feature geometry changes - * @type {Object.<number, ol.Extent>} - * @private - */ - this.indexedFeaturesExtents_ = {}; - - /** - * If a feature geometry changes while a pointer drag|move event occurs, the - * feature doesn't get updated right away. It will be at the next 'pointerup' - * event fired. - * @type {Object.<number, ol.Feature>} - * @private - */ - this.pendingFeatures_ = {}; - - /** - * Used for distance sorting in sortByDistance_ - * @type {ol.Coordinate} - * @private - */ - this.pixelCoordinate_ = null; - - /** - * @type {number} - * @private - */ - this.pixelTolerance_ = options.pixelTolerance !== undefined ? - options.pixelTolerance : 10; - - /** - * @type {function(ol.SnapSegmentDataType, ol.SnapSegmentDataType): number} - * @private - */ - this.sortByDistance_ = ol.interaction.Snap.sortByDistance.bind(this); - - - /** - * Segment RTree for each layer - * @type {ol.structs.RBush.<ol.SnapSegmentDataType>} - * @private - */ - this.rBush_ = new ol.structs.RBush(); - - - /** - * @const - * @private - * @type {Object.<string, function(ol.Feature, ol.geom.Geometry)>} - */ - this.SEGMENT_WRITERS_ = { - 'Point': this.writePointGeometry_, - 'LineString': this.writeLineStringGeometry_, - 'LinearRing': this.writeLineStringGeometry_, - 'Polygon': this.writePolygonGeometry_, - 'MultiPoint': this.writeMultiPointGeometry_, - 'MultiLineString': this.writeMultiLineStringGeometry_, - 'MultiPolygon': this.writeMultiPolygonGeometry_, - 'GeometryCollection': this.writeGeometryCollectionGeometry_, - 'Circle': this.writeCircleGeometry_ - }; -}; -ol.inherits(ol.interaction.Snap, ol.interaction.Pointer); - - -/** - * Add a feature to the collection of features that we may snap to. - * @param {ol.Feature} feature Feature. - * @param {boolean=} opt_listen Whether to listen to the feature change or not - * Defaults to `true`. - * @api - */ -ol.interaction.Snap.prototype.addFeature = function(feature, opt_listen) { - var listen = opt_listen !== undefined ? opt_listen : true; - var feature_uid = ol.getUid(feature); - var geometry = feature.getGeometry(); - if (geometry) { - var segmentWriter = this.SEGMENT_WRITERS_[geometry.getType()]; - if (segmentWriter) { - this.indexedFeaturesExtents_[feature_uid] = geometry.getExtent( - ol.extent.createEmpty()); - segmentWriter.call(this, feature, geometry); - } - } - - if (listen) { - this.featureChangeListenerKeys_[feature_uid] = ol.events.listen( - feature, - ol.events.EventType.CHANGE, - this.handleFeatureChange_, this); - } -}; - - -/** - * @param {ol.Feature} feature Feature. - * @private - */ -ol.interaction.Snap.prototype.forEachFeatureAdd_ = function(feature) { - this.addFeature(feature); -}; - - -/** - * @param {ol.Feature} feature Feature. - * @private - */ -ol.interaction.Snap.prototype.forEachFeatureRemove_ = function(feature) { - this.removeFeature(feature); -}; - - -/** - * @return {ol.Collection.<ol.Feature>|Array.<ol.Feature>} Features. - * @private - */ -ol.interaction.Snap.prototype.getFeatures_ = function() { - var features; - if (this.features_) { - features = this.features_; - } else if (this.source_) { - features = this.source_.getFeatures(); - } - return /** @type {!Array.<ol.Feature>|!ol.Collection.<ol.Feature>} */ (features); -}; - - -/** - * @param {ol.source.Vector.Event|ol.Collection.Event} evt Event. - * @private - */ -ol.interaction.Snap.prototype.handleFeatureAdd_ = function(evt) { - var feature; - if (evt instanceof ol.source.Vector.Event) { - feature = evt.feature; - } else if (evt instanceof ol.Collection.Event) { - feature = evt.element; - } - this.addFeature(/** @type {ol.Feature} */ (feature)); -}; - - -/** - * @param {ol.source.Vector.Event|ol.Collection.Event} evt Event. - * @private - */ -ol.interaction.Snap.prototype.handleFeatureRemove_ = function(evt) { - var feature; - if (evt instanceof ol.source.Vector.Event) { - feature = evt.feature; - } else if (evt instanceof ol.Collection.Event) { - feature = evt.element; - } - this.removeFeature(/** @type {ol.Feature} */ (feature)); -}; - - -/** - * @param {ol.events.Event} evt Event. - * @private - */ -ol.interaction.Snap.prototype.handleFeatureChange_ = function(evt) { - var feature = /** @type {ol.Feature} */ (evt.target); - if (this.handlingDownUpSequence) { - var uid = ol.getUid(feature); - if (!(uid in this.pendingFeatures_)) { - this.pendingFeatures_[uid] = feature; - } - } else { - this.updateFeature_(feature); - } -}; - - -/** - * Remove a feature from the collection of features that we may snap to. - * @param {ol.Feature} feature Feature - * @param {boolean=} opt_unlisten Whether to unlisten to the feature change - * or not. Defaults to `true`. - * @api - */ -ol.interaction.Snap.prototype.removeFeature = function(feature, opt_unlisten) { - var unlisten = opt_unlisten !== undefined ? opt_unlisten : true; - var feature_uid = ol.getUid(feature); - var extent = this.indexedFeaturesExtents_[feature_uid]; - if (extent) { - var rBush = this.rBush_; - var i, nodesToRemove = []; - rBush.forEachInExtent(extent, function(node) { - if (feature === node.feature) { - nodesToRemove.push(node); - } - }); - for (i = nodesToRemove.length - 1; i >= 0; --i) { - rBush.remove(nodesToRemove[i]); - } - } - - if (unlisten) { - ol.events.unlistenByKey(this.featureChangeListenerKeys_[feature_uid]); - delete this.featureChangeListenerKeys_[feature_uid]; - } -}; - - -/** - * @inheritDoc - */ -ol.interaction.Snap.prototype.setMap = function(map) { - var currentMap = this.getMap(); - var keys = this.featuresListenerKeys_; - var features = this.getFeatures_(); - - if (currentMap) { - keys.forEach(ol.events.unlistenByKey); - keys.length = 0; - features.forEach(this.forEachFeatureRemove_, this); - } - ol.interaction.Pointer.prototype.setMap.call(this, map); - - if (map) { - if (this.features_) { - keys.push( - ol.events.listen(this.features_, ol.CollectionEventType.ADD, - this.handleFeatureAdd_, this), - ol.events.listen(this.features_, ol.CollectionEventType.REMOVE, - this.handleFeatureRemove_, this) - ); - } else if (this.source_) { - keys.push( - ol.events.listen(this.source_, ol.source.VectorEventType.ADDFEATURE, - this.handleFeatureAdd_, this), - ol.events.listen(this.source_, ol.source.VectorEventType.REMOVEFEATURE, - this.handleFeatureRemove_, this) - ); - } - features.forEach(this.forEachFeatureAdd_, this); - } -}; - - -/** - * @inheritDoc - */ -ol.interaction.Snap.prototype.shouldStopEvent = ol.functions.FALSE; - - -/** - * @param {ol.Pixel} pixel Pixel - * @param {ol.Coordinate} pixelCoordinate Coordinate - * @param {ol.PluggableMap} map Map. - * @return {ol.SnapResultType} Snap result - */ -ol.interaction.Snap.prototype.snapTo = function(pixel, pixelCoordinate, map) { - - var lowerLeft = map.getCoordinateFromPixel( - [pixel[0] - this.pixelTolerance_, pixel[1] + this.pixelTolerance_]); - var upperRight = map.getCoordinateFromPixel( - [pixel[0] + this.pixelTolerance_, pixel[1] - this.pixelTolerance_]); - var box = ol.extent.boundingExtent([lowerLeft, upperRight]); - - var segments = this.rBush_.getInExtent(box); - - // If snapping on vertices only, don't consider circles - if (this.vertex_ && !this.edge_) { - segments = segments.filter(function(segment) { - return segment.feature.getGeometry().getType() !== - ol.geom.GeometryType.CIRCLE; - }); - } - - var snappedToVertex = false; - var snapped = false; - var vertex = null; - var vertexPixel = null; - var dist, pixel1, pixel2, squaredDist1, squaredDist2; - if (segments.length > 0) { - this.pixelCoordinate_ = pixelCoordinate; - segments.sort(this.sortByDistance_); - var closestSegment = segments[0].segment; - var isCircle = segments[0].feature.getGeometry().getType() === - ol.geom.GeometryType.CIRCLE; - if (this.vertex_ && !this.edge_) { - pixel1 = map.getPixelFromCoordinate(closestSegment[0]); - pixel2 = map.getPixelFromCoordinate(closestSegment[1]); - squaredDist1 = ol.coordinate.squaredDistance(pixel, pixel1); - squaredDist2 = ol.coordinate.squaredDistance(pixel, pixel2); - dist = Math.sqrt(Math.min(squaredDist1, squaredDist2)); - snappedToVertex = dist <= this.pixelTolerance_; - if (snappedToVertex) { - snapped = true; - vertex = squaredDist1 > squaredDist2 ? - closestSegment[1] : closestSegment[0]; - vertexPixel = map.getPixelFromCoordinate(vertex); - } - } else if (this.edge_) { - if (isCircle) { - vertex = ol.coordinate.closestOnCircle(pixelCoordinate, - /** @type {ol.geom.Circle} */ (segments[0].feature.getGeometry())); - } else { - vertex = (ol.coordinate.closestOnSegment(pixelCoordinate, - closestSegment)); - } - vertexPixel = map.getPixelFromCoordinate(vertex); - if (ol.coordinate.distance(pixel, vertexPixel) <= this.pixelTolerance_) { - snapped = true; - if (this.vertex_ && !isCircle) { - pixel1 = map.getPixelFromCoordinate(closestSegment[0]); - pixel2 = map.getPixelFromCoordinate(closestSegment[1]); - squaredDist1 = ol.coordinate.squaredDistance(vertexPixel, pixel1); - squaredDist2 = ol.coordinate.squaredDistance(vertexPixel, pixel2); - dist = Math.sqrt(Math.min(squaredDist1, squaredDist2)); - snappedToVertex = dist <= this.pixelTolerance_; - if (snappedToVertex) { - vertex = squaredDist1 > squaredDist2 ? - closestSegment[1] : closestSegment[0]; - vertexPixel = map.getPixelFromCoordinate(vertex); - } - } - } - } - if (snapped) { - vertexPixel = [Math.round(vertexPixel[0]), Math.round(vertexPixel[1])]; - } - } - return /** @type {ol.SnapResultType} */ ({ - snapped: snapped, - vertex: vertex, - vertexPixel: vertexPixel - }); -}; - - -/** - * @param {ol.Feature} feature Feature - * @private - */ -ol.interaction.Snap.prototype.updateFeature_ = function(feature) { - this.removeFeature(feature, false); - this.addFeature(feature, false); -}; - - -/** - * @param {ol.Feature} feature Feature - * @param {ol.geom.Circle} geometry Geometry. - * @private - */ -ol.interaction.Snap.prototype.writeCircleGeometry_ = function(feature, geometry) { - var polygon = ol.geom.Polygon.fromCircle(geometry); - var coordinates = polygon.getCoordinates()[0]; - var i, ii, segment, segmentData; - for (i = 0, ii = coordinates.length - 1; i < ii; ++i) { - segment = coordinates.slice(i, i + 2); - segmentData = /** @type {ol.SnapSegmentDataType} */ ({ - feature: feature, - segment: segment - }); - this.rBush_.insert(ol.extent.boundingExtent(segment), segmentData); - } -}; - - -/** - * @param {ol.Feature} feature Feature - * @param {ol.geom.GeometryCollection} geometry Geometry. - * @private - */ -ol.interaction.Snap.prototype.writeGeometryCollectionGeometry_ = function(feature, geometry) { - var i, geometries = geometry.getGeometriesArray(); - for (i = 0; i < geometries.length; ++i) { - var segmentWriter = this.SEGMENT_WRITERS_[geometries[i].getType()]; - if (segmentWriter) { - segmentWriter.call(this, feature, geometries[i]); - } - } -}; - - -/** - * @param {ol.Feature} feature Feature - * @param {ol.geom.LineString} geometry Geometry. - * @private - */ -ol.interaction.Snap.prototype.writeLineStringGeometry_ = function(feature, geometry) { - var coordinates = geometry.getCoordinates(); - var i, ii, segment, segmentData; - for (i = 0, ii = coordinates.length - 1; i < ii; ++i) { - segment = coordinates.slice(i, i + 2); - segmentData = /** @type {ol.SnapSegmentDataType} */ ({ - feature: feature, - segment: segment - }); - this.rBush_.insert(ol.extent.boundingExtent(segment), segmentData); - } -}; - - -/** - * @param {ol.Feature} feature Feature - * @param {ol.geom.MultiLineString} geometry Geometry. - * @private - */ -ol.interaction.Snap.prototype.writeMultiLineStringGeometry_ = function(feature, geometry) { - var lines = geometry.getCoordinates(); - var coordinates, i, ii, j, jj, segment, segmentData; - for (j = 0, jj = lines.length; j < jj; ++j) { - coordinates = lines[j]; - for (i = 0, ii = coordinates.length - 1; i < ii; ++i) { - segment = coordinates.slice(i, i + 2); - segmentData = /** @type {ol.SnapSegmentDataType} */ ({ - feature: feature, - segment: segment - }); - this.rBush_.insert(ol.extent.boundingExtent(segment), segmentData); - } - } -}; - - -/** - * @param {ol.Feature} feature Feature - * @param {ol.geom.MultiPoint} geometry Geometry. - * @private - */ -ol.interaction.Snap.prototype.writeMultiPointGeometry_ = function(feature, geometry) { - var points = geometry.getCoordinates(); - var coordinates, i, ii, segmentData; - for (i = 0, ii = points.length; i < ii; ++i) { - coordinates = points[i]; - segmentData = /** @type {ol.SnapSegmentDataType} */ ({ - feature: feature, - segment: [coordinates, coordinates] - }); - this.rBush_.insert(geometry.getExtent(), segmentData); - } -}; - - -/** - * @param {ol.Feature} feature Feature - * @param {ol.geom.MultiPolygon} geometry Geometry. - * @private - */ -ol.interaction.Snap.prototype.writeMultiPolygonGeometry_ = function(feature, geometry) { - var polygons = geometry.getCoordinates(); - var coordinates, i, ii, j, jj, k, kk, rings, segment, segmentData; - for (k = 0, kk = polygons.length; k < kk; ++k) { - rings = polygons[k]; - for (j = 0, jj = rings.length; j < jj; ++j) { - coordinates = rings[j]; - for (i = 0, ii = coordinates.length - 1; i < ii; ++i) { - segment = coordinates.slice(i, i + 2); - segmentData = /** @type {ol.SnapSegmentDataType} */ ({ - feature: feature, - segment: segment - }); - this.rBush_.insert(ol.extent.boundingExtent(segment), segmentData); - } - } - } -}; - - -/** - * @param {ol.Feature} feature Feature - * @param {ol.geom.Point} geometry Geometry. - * @private - */ -ol.interaction.Snap.prototype.writePointGeometry_ = function(feature, geometry) { - var coordinates = geometry.getCoordinates(); - var segmentData = /** @type {ol.SnapSegmentDataType} */ ({ - feature: feature, - segment: [coordinates, coordinates] - }); - this.rBush_.insert(geometry.getExtent(), segmentData); -}; - - -/** - * @param {ol.Feature} feature Feature - * @param {ol.geom.Polygon} geometry Geometry. - * @private - */ -ol.interaction.Snap.prototype.writePolygonGeometry_ = function(feature, geometry) { - var rings = geometry.getCoordinates(); - var coordinates, i, ii, j, jj, segment, segmentData; - for (j = 0, jj = rings.length; j < jj; ++j) { - coordinates = rings[j]; - for (i = 0, ii = coordinates.length - 1; i < ii; ++i) { - segment = coordinates.slice(i, i + 2); - segmentData = /** @type {ol.SnapSegmentDataType} */ ({ - feature: feature, - segment: segment - }); - this.rBush_.insert(ol.extent.boundingExtent(segment), segmentData); - } - } -}; - - -/** - * Handle all pointer events events. - * @param {ol.MapBrowserEvent} evt A move event. - * @return {boolean} Pass the event to other interactions. - * @this {ol.interaction.Snap} - * @private - */ -ol.interaction.Snap.handleEvent_ = function(evt) { - var result = this.snapTo(evt.pixel, evt.coordinate, evt.map); - if (result.snapped) { - evt.coordinate = result.vertex.slice(0, 2); - evt.pixel = result.vertexPixel; - } - return ol.interaction.Pointer.handleEvent.call(this, evt); -}; - - -/** - * @param {ol.MapBrowserPointerEvent} evt Event. - * @return {boolean} Stop drag sequence? - * @this {ol.interaction.Snap} - * @private - */ -ol.interaction.Snap.handleUpEvent_ = function(evt) { - var featuresToUpdate = ol.obj.getValues(this.pendingFeatures_); - if (featuresToUpdate.length) { - featuresToUpdate.forEach(this.updateFeature_, this); - this.pendingFeatures_ = {}; - } - return false; -}; - - -/** - * Sort segments by distance, helper function - * @param {ol.SnapSegmentDataType} a The first segment data. - * @param {ol.SnapSegmentDataType} b The second segment data. - * @return {number} The difference in distance. - * @this {ol.interaction.Snap} - */ -ol.interaction.Snap.sortByDistance = function(a, b) { - return ol.coordinate.squaredDistanceToSegment( - this.pixelCoordinate_, a.segment) - - ol.coordinate.squaredDistanceToSegment( - this.pixelCoordinate_, b.segment); -}; - -goog.provide('ol.interaction.TranslateEventType'); - - -/** - * @enum {string} - */ -ol.interaction.TranslateEventType = { - /** - * Triggered upon feature translation start. - * @event ol.interaction.Translate.Event#translatestart - * @api - */ - TRANSLATESTART: 'translatestart', - /** - * Triggered upon feature translation. - * @event ol.interaction.Translate.Event#translating - * @api - */ - TRANSLATING: 'translating', - /** - * Triggered upon feature translation end. - * @event ol.interaction.Translate.Event#translateend - * @api - */ - TRANSLATEEND: 'translateend' -}; - -goog.provide('ol.interaction.Translate'); - -goog.require('ol'); -goog.require('ol.Collection'); -goog.require('ol.Object'); -goog.require('ol.events'); -goog.require('ol.events.Event'); -goog.require('ol.functions'); -goog.require('ol.array'); -goog.require('ol.interaction.Pointer'); -goog.require('ol.interaction.Property'); -goog.require('ol.interaction.TranslateEventType'); - - -/** - * @classdesc - * Interaction for translating (moving) features. - * - * @constructor - * @extends {ol.interaction.Pointer} - * @fires ol.interaction.Translate.Event - * @param {olx.interaction.TranslateOptions=} opt_options Options. - * @api - */ -ol.interaction.Translate = function(opt_options) { - ol.interaction.Pointer.call(this, { - handleDownEvent: ol.interaction.Translate.handleDownEvent_, - handleDragEvent: ol.interaction.Translate.handleDragEvent_, - handleMoveEvent: ol.interaction.Translate.handleMoveEvent_, - handleUpEvent: ol.interaction.Translate.handleUpEvent_ - }); - - var options = opt_options ? opt_options : {}; - - /** - * The last position we translated to. - * @type {ol.Coordinate} - * @private - */ - this.lastCoordinate_ = null; - - - /** - * @type {ol.Collection.<ol.Feature>} - * @private - */ - this.features_ = options.features !== undefined ? options.features : null; - - /** @type {function(ol.layer.Layer): boolean} */ - var layerFilter; - if (options.layers) { - if (typeof options.layers === 'function') { - layerFilter = options.layers; - } else { - var layers = options.layers; - layerFilter = function(layer) { - return ol.array.includes(layers, layer); - }; - } - } else { - layerFilter = ol.functions.TRUE; - } - - /** - * @private - * @type {function(ol.layer.Layer): boolean} - */ - this.layerFilter_ = layerFilter; - - /** - * @private - * @type {number} - */ - this.hitTolerance_ = options.hitTolerance ? options.hitTolerance : 0; - - /** - * @type {ol.Feature} - * @private - */ - this.lastFeature_ = null; - - ol.events.listen(this, - ol.Object.getChangeEventType(ol.interaction.Property.ACTIVE), - this.handleActiveChanged_, this); - -}; -ol.inherits(ol.interaction.Translate, ol.interaction.Pointer); - - -/** - * @param {ol.MapBrowserPointerEvent} event Event. - * @return {boolean} Start drag sequence? - * @this {ol.interaction.Translate} - * @private - */ -ol.interaction.Translate.handleDownEvent_ = function(event) { - this.lastFeature_ = this.featuresAtPixel_(event.pixel, event.map); - if (!this.lastCoordinate_ && this.lastFeature_) { - this.lastCoordinate_ = event.coordinate; - ol.interaction.Translate.handleMoveEvent_.call(this, event); - - var features = this.features_ || new ol.Collection([this.lastFeature_]); - - this.dispatchEvent( - new ol.interaction.Translate.Event( - ol.interaction.TranslateEventType.TRANSLATESTART, features, - event.coordinate)); - return true; - } - return false; -}; - - -/** - * @param {ol.MapBrowserPointerEvent} event Event. - * @return {boolean} Stop drag sequence? - * @this {ol.interaction.Translate} - * @private - */ -ol.interaction.Translate.handleUpEvent_ = function(event) { - if (this.lastCoordinate_) { - this.lastCoordinate_ = null; - ol.interaction.Translate.handleMoveEvent_.call(this, event); - - var features = this.features_ || new ol.Collection([this.lastFeature_]); - - this.dispatchEvent( - new ol.interaction.Translate.Event( - ol.interaction.TranslateEventType.TRANSLATEEND, features, - event.coordinate)); - return true; - } - return false; -}; - - -/** - * @param {ol.MapBrowserPointerEvent} event Event. - * @this {ol.interaction.Translate} - * @private - */ -ol.interaction.Translate.handleDragEvent_ = function(event) { - if (this.lastCoordinate_) { - var newCoordinate = event.coordinate; - var deltaX = newCoordinate[0] - this.lastCoordinate_[0]; - var deltaY = newCoordinate[1] - this.lastCoordinate_[1]; - - var features = this.features_ || new ol.Collection([this.lastFeature_]); - - features.forEach(function(feature) { - var geom = feature.getGeometry(); - geom.translate(deltaX, deltaY); - feature.setGeometry(geom); - }); - - this.lastCoordinate_ = newCoordinate; - this.dispatchEvent( - new ol.interaction.Translate.Event( - ol.interaction.TranslateEventType.TRANSLATING, features, - newCoordinate)); - } -}; - - -/** - * @param {ol.MapBrowserEvent} event Event. - * @this {ol.interaction.Translate} - * @private - */ -ol.interaction.Translate.handleMoveEvent_ = function(event) { - var elem = event.map.getViewport(); - - // Change the cursor to grab/grabbing if hovering any of the features managed - // by the interaction - if (this.featuresAtPixel_(event.pixel, event.map)) { - elem.classList.remove(this.lastCoordinate_ ? 'ol-grab' : 'ol-grabbing'); - elem.classList.add(this.lastCoordinate_ ? 'ol-grabbing' : 'ol-grab'); - } else { - elem.classList.remove('ol-grab', 'ol-grabbing'); - } -}; - - -/** - * Tests to see if the given coordinates intersects any of our selected - * features. - * @param {ol.Pixel} pixel Pixel coordinate to test for intersection. - * @param {ol.PluggableMap} map Map to test the intersection on. - * @return {ol.Feature} Returns the feature found at the specified pixel - * coordinates. - * @private - */ -ol.interaction.Translate.prototype.featuresAtPixel_ = function(pixel, map) { - return map.forEachFeatureAtPixel(pixel, - function(feature) { - if (!this.features_ || - ol.array.includes(this.features_.getArray(), feature)) { - return feature; - } - }.bind(this), { - layerFilter: this.layerFilter_, - hitTolerance: this.hitTolerance_ - }); -}; - - -/** - * Returns the Hit-detection tolerance. - * @returns {number} Hit tolerance in pixels. - * @api - */ -ol.interaction.Translate.prototype.getHitTolerance = function() { - return this.hitTolerance_; -}; - - -/** - * Hit-detection tolerance. Pixels inside the radius around the given position - * will be checked for features. This only works for the canvas renderer and - * not for WebGL. - * @param {number} hitTolerance Hit tolerance in pixels. - * @api - */ -ol.interaction.Translate.prototype.setHitTolerance = function(hitTolerance) { - this.hitTolerance_ = hitTolerance; -}; - - -/** - * @inheritDoc - */ -ol.interaction.Translate.prototype.setMap = function(map) { - var oldMap = this.getMap(); - ol.interaction.Pointer.prototype.setMap.call(this, map); - this.updateState_(oldMap); -}; - - -/** - * @private - */ -ol.interaction.Translate.prototype.handleActiveChanged_ = function() { - this.updateState_(null); -}; - - -/** - * @param {ol.PluggableMap} oldMap Old map. - * @private - */ -ol.interaction.Translate.prototype.updateState_ = function(oldMap) { - var map = this.getMap(); - var active = this.getActive(); - if (!map || !active) { - map = map || oldMap; - if (map) { - var elem = map.getViewport(); - elem.classList.remove('ol-grab', 'ol-grabbing'); - } - } -}; - - -/** - * @classdesc - * Events emitted by {@link ol.interaction.Translate} instances are instances of - * this type. - * - * @constructor - * @extends {ol.events.Event} - * @implements {oli.interaction.TranslateEvent} - * @param {ol.interaction.TranslateEventType} type Type. - * @param {ol.Collection.<ol.Feature>} features The features translated. - * @param {ol.Coordinate} coordinate The event coordinate. - */ -ol.interaction.Translate.Event = function(type, features, coordinate) { - - ol.events.Event.call(this, type); - - /** - * The features being translated. - * @type {ol.Collection.<ol.Feature>} - * @api - */ - this.features = features; - - /** - * The coordinate of the drag event. - * @const - * @type {ol.Coordinate} - * @api - */ - this.coordinate = coordinate; -}; -ol.inherits(ol.interaction.Translate.Event, ol.events.Event); - -goog.provide('ol.layer.Heatmap'); - -goog.require('ol.events'); -goog.require('ol'); -goog.require('ol.Object'); -goog.require('ol.dom'); -goog.require('ol.layer.Vector'); -goog.require('ol.math'); -goog.require('ol.obj'); -goog.require('ol.render.EventType'); -goog.require('ol.style.Icon'); -goog.require('ol.style.Style'); - - -/** - * @classdesc - * Layer for rendering vector data as a heatmap. - * Note that any property set in the options is set as a {@link ol.Object} - * property on the layer object; for example, setting `title: 'My Title'` in the - * options means that `title` is observable, and has get/set accessors. - * - * @constructor - * @extends {ol.layer.Vector} - * @fires ol.render.Event - * @param {olx.layer.HeatmapOptions=} opt_options Options. - * @api - */ -ol.layer.Heatmap = function(opt_options) { - var options = opt_options ? opt_options : {}; - - var baseOptions = ol.obj.assign({}, options); - - delete baseOptions.gradient; - delete baseOptions.radius; - delete baseOptions.blur; - delete baseOptions.shadow; - delete baseOptions.weight; - ol.layer.Vector.call(this, /** @type {olx.layer.VectorOptions} */ (baseOptions)); - - /** - * @private - * @type {Uint8ClampedArray} - */ - this.gradient_ = null; - - /** - * @private - * @type {number} - */ - this.shadow_ = options.shadow !== undefined ? options.shadow : 250; - - /** - * @private - * @type {string|undefined} - */ - this.circleImage_ = undefined; - - /** - * @private - * @type {Array.<Array.<ol.style.Style>>} - */ - this.styleCache_ = null; - - ol.events.listen(this, - ol.Object.getChangeEventType(ol.layer.Heatmap.Property_.GRADIENT), - this.handleGradientChanged_, this); - - this.setGradient(options.gradient ? - options.gradient : ol.layer.Heatmap.DEFAULT_GRADIENT); - - this.setBlur(options.blur !== undefined ? options.blur : 15); - - this.setRadius(options.radius !== undefined ? options.radius : 8); - - ol.events.listen(this, - ol.Object.getChangeEventType(ol.layer.Heatmap.Property_.BLUR), - this.handleStyleChanged_, this); - ol.events.listen(this, - ol.Object.getChangeEventType(ol.layer.Heatmap.Property_.RADIUS), - this.handleStyleChanged_, this); - - this.handleStyleChanged_(); - - var weight = options.weight ? options.weight : 'weight'; - var weightFunction; - if (typeof weight === 'string') { - weightFunction = function(feature) { - return feature.get(weight); - }; - } else { - weightFunction = weight; - } - - this.setStyle(function(feature, resolution) { - var weight = weightFunction(feature); - var opacity = weight !== undefined ? ol.math.clamp(weight, 0, 1) : 1; - // cast to 8 bits - var index = (255 * opacity) | 0; - var style = this.styleCache_[index]; - if (!style) { - style = [ - new ol.style.Style({ - image: new ol.style.Icon({ - opacity: opacity, - src: this.circleImage_ - }) - }) - ]; - this.styleCache_[index] = style; - } - return style; - }.bind(this)); - - // For performance reasons, don't sort the features before rendering. - // The render order is not relevant for a heatmap representation. - this.setRenderOrder(null); - - ol.events.listen(this, ol.render.EventType.RENDER, this.handleRender_, this); -}; -ol.inherits(ol.layer.Heatmap, ol.layer.Vector); - - -/** - * @const - * @type {Array.<string>} - */ -ol.layer.Heatmap.DEFAULT_GRADIENT = ['#00f', '#0ff', '#0f0', '#ff0', '#f00']; - - -/** - * @param {Array.<string>} colors A list of colored. - * @return {Uint8ClampedArray} An array. - * @private - */ -ol.layer.Heatmap.createGradient_ = function(colors) { - var width = 1; - var height = 256; - var context = ol.dom.createCanvasContext2D(width, height); - - var gradient = context.createLinearGradient(0, 0, width, height); - var step = 1 / (colors.length - 1); - for (var i = 0, ii = colors.length; i < ii; ++i) { - gradient.addColorStop(i * step, colors[i]); - } - - context.fillStyle = gradient; - context.fillRect(0, 0, width, height); - - return context.getImageData(0, 0, width, height).data; -}; - - -/** - * @return {string} Data URL for a circle. - * @private - */ -ol.layer.Heatmap.prototype.createCircle_ = function() { - var radius = this.getRadius(); - var blur = this.getBlur(); - var halfSize = radius + blur + 1; - var size = 2 * halfSize; - var context = ol.dom.createCanvasContext2D(size, size); - context.shadowOffsetX = context.shadowOffsetY = this.shadow_; - context.shadowBlur = blur; - context.shadowColor = '#000'; - context.beginPath(); - var center = halfSize - this.shadow_; - context.arc(center, center, radius, 0, Math.PI * 2, true); - context.fill(); - return context.canvas.toDataURL(); -}; - - -/** - * Return the blur size in pixels. - * @return {number} Blur size in pixels. - * @api - * @observable - */ -ol.layer.Heatmap.prototype.getBlur = function() { - return /** @type {number} */ (this.get(ol.layer.Heatmap.Property_.BLUR)); -}; - - -/** - * Return the gradient colors as array of strings. - * @return {Array.<string>} Colors. - * @api - * @observable - */ -ol.layer.Heatmap.prototype.getGradient = function() { - return /** @type {Array.<string>} */ ( - this.get(ol.layer.Heatmap.Property_.GRADIENT)); -}; - - -/** - * Return the size of the radius in pixels. - * @return {number} Radius size in pixel. - * @api - * @observable - */ -ol.layer.Heatmap.prototype.getRadius = function() { - return /** @type {number} */ (this.get(ol.layer.Heatmap.Property_.RADIUS)); -}; - - -/** - * @private - */ -ol.layer.Heatmap.prototype.handleGradientChanged_ = function() { - this.gradient_ = ol.layer.Heatmap.createGradient_(this.getGradient()); -}; - - -/** - * @private - */ -ol.layer.Heatmap.prototype.handleStyleChanged_ = function() { - this.circleImage_ = this.createCircle_(); - this.styleCache_ = new Array(256); - this.changed(); -}; - - -/** - * @param {ol.render.Event} event Post compose event - * @private - */ -ol.layer.Heatmap.prototype.handleRender_ = function(event) { - var context = event.context; - var canvas = context.canvas; - var image = context.getImageData(0, 0, canvas.width, canvas.height); - var view8 = image.data; - var i, ii, alpha; - for (i = 0, ii = view8.length; i < ii; i += 4) { - alpha = view8[i + 3] * 4; - if (alpha) { - view8[i] = this.gradient_[alpha]; - view8[i + 1] = this.gradient_[alpha + 1]; - view8[i + 2] = this.gradient_[alpha + 2]; - } - } - context.putImageData(image, 0, 0); -}; - - -/** - * Set the blur size in pixels. - * @param {number} blur Blur size in pixels. - * @api - * @observable - */ -ol.layer.Heatmap.prototype.setBlur = function(blur) { - this.set(ol.layer.Heatmap.Property_.BLUR, blur); -}; - - -/** - * Set the gradient colors as array of strings. - * @param {Array.<string>} colors Gradient. - * @api - * @observable - */ -ol.layer.Heatmap.prototype.setGradient = function(colors) { - this.set(ol.layer.Heatmap.Property_.GRADIENT, colors); -}; - - -/** - * Set the size of the radius in pixels. - * @param {number} radius Radius size in pixel. - * @api - * @observable - */ -ol.layer.Heatmap.prototype.setRadius = function(radius) { - this.set(ol.layer.Heatmap.Property_.RADIUS, radius); -}; - - -/** - * @enum {string} - * @private - */ -ol.layer.Heatmap.Property_ = { - BLUR: 'blur', - GRADIENT: 'gradient', - RADIUS: 'radius' -}; - -goog.provide('ol.layer.Image'); - -goog.require('ol'); -goog.require('ol.LayerType'); -goog.require('ol.layer.Layer'); - - -/** - * @classdesc - * Server-rendered images that are available for arbitrary extents and - * resolutions. - * Note that any property set in the options is set as a {@link ol.Object} - * property on the layer object; for example, setting `title: 'My Title'` in the - * options means that `title` is observable, and has get/set accessors. - * - * @constructor - * @extends {ol.layer.Layer} - * @fires ol.render.Event - * @param {olx.layer.ImageOptions=} opt_options Layer options. - * @api - */ -ol.layer.Image = function(opt_options) { - var options = opt_options ? opt_options : {}; - ol.layer.Layer.call(this, /** @type {olx.layer.LayerOptions} */ (options)); - - /** - * The layer type. - * @protected - * @type {ol.LayerType} - */ - this.type = ol.LayerType.IMAGE; - -}; -ol.inherits(ol.layer.Image, ol.layer.Layer); - - -/** - * Return the associated {@link ol.source.Image source} of the image layer. - * @function - * @return {ol.source.Image} Source. - * @api - */ -ol.layer.Image.prototype.getSource; - -goog.provide('ol.layer.TileProperty'); - -/** - * @enum {string} - */ -ol.layer.TileProperty = { - PRELOAD: 'preload', - USE_INTERIM_TILES_ON_ERROR: 'useInterimTilesOnError' -}; - -goog.provide('ol.layer.Tile'); - -goog.require('ol'); -goog.require('ol.LayerType'); -goog.require('ol.layer.Layer'); -goog.require('ol.layer.TileProperty'); -goog.require('ol.obj'); - - -/** - * @classdesc - * For layer sources that provide pre-rendered, tiled images in grids that are - * organized by zoom levels for specific resolutions. - * Note that any property set in the options is set as a {@link ol.Object} - * property on the layer object; for example, setting `title: 'My Title'` in the - * options means that `title` is observable, and has get/set accessors. - * - * @constructor - * @extends {ol.layer.Layer} - * @fires ol.render.Event - * @param {olx.layer.TileOptions=} opt_options Tile layer options. - * @api - */ -ol.layer.Tile = function(opt_options) { - var options = opt_options ? opt_options : {}; - - var baseOptions = ol.obj.assign({}, options); - - delete baseOptions.preload; - delete baseOptions.useInterimTilesOnError; - ol.layer.Layer.call(this, /** @type {olx.layer.LayerOptions} */ (baseOptions)); - - this.setPreload(options.preload !== undefined ? options.preload : 0); - this.setUseInterimTilesOnError(options.useInterimTilesOnError !== undefined ? - options.useInterimTilesOnError : true); - - /** - * The layer type. - * @protected - * @type {ol.LayerType} - */ - this.type = ol.LayerType.TILE; - -}; -ol.inherits(ol.layer.Tile, ol.layer.Layer); - - -/** - * Return the level as number to which we will preload tiles up to. - * @return {number} The level to preload tiles up to. - * @observable - * @api - */ -ol.layer.Tile.prototype.getPreload = function() { - return /** @type {number} */ (this.get(ol.layer.TileProperty.PRELOAD)); -}; - - -/** - * Return the associated {@link ol.source.Tile tilesource} of the layer. - * @function - * @return {ol.source.Tile} Source. - * @api - */ -ol.layer.Tile.prototype.getSource; - - -/** - * Set the level as number to which we will preload tiles up to. - * @param {number} preload The level to preload tiles up to. - * @observable - * @api - */ -ol.layer.Tile.prototype.setPreload = function(preload) { - this.set(ol.layer.TileProperty.PRELOAD, preload); -}; - - -/** - * Whether we use interim tiles on error. - * @return {boolean} Use interim tiles on error. - * @observable - * @api - */ -ol.layer.Tile.prototype.getUseInterimTilesOnError = function() { - return /** @type {boolean} */ ( - this.get(ol.layer.TileProperty.USE_INTERIM_TILES_ON_ERROR)); -}; - - -/** - * Set whether we use interim tiles on error. - * @param {boolean} useInterimTilesOnError Use interim tiles on error. - * @observable - * @api - */ -ol.layer.Tile.prototype.setUseInterimTilesOnError = function(useInterimTilesOnError) { - this.set( - ol.layer.TileProperty.USE_INTERIM_TILES_ON_ERROR, useInterimTilesOnError); -}; - -goog.provide('ol.layer.VectorTile'); - -goog.require('ol'); -goog.require('ol.LayerType'); -goog.require('ol.asserts'); -goog.require('ol.layer.TileProperty'); -goog.require('ol.layer.Vector'); -goog.require('ol.layer.VectorTileRenderType'); -goog.require('ol.obj'); - - -/** - * @classdesc - * Layer for vector tile data that is rendered client-side. - * Note that any property set in the options is set as a {@link ol.Object} - * property on the layer object; for example, setting `title: 'My Title'` in the - * options means that `title` is observable, and has get/set accessors. - * - * @constructor - * @extends {ol.layer.Vector} - * @param {olx.layer.VectorTileOptions=} opt_options Options. - * @api - */ -ol.layer.VectorTile = function(opt_options) { - var options = opt_options ? opt_options : {}; - - var baseOptions = ol.obj.assign({}, options); - - delete baseOptions.preload; - delete baseOptions.useInterimTilesOnError; - ol.layer.Vector.call(this, /** @type {olx.layer.VectorOptions} */ (baseOptions)); - - this.setPreload(options.preload ? options.preload : 0); - this.setUseInterimTilesOnError(options.useInterimTilesOnError ? - options.useInterimTilesOnError : true); - - ol.asserts.assert(options.renderMode == undefined || - options.renderMode == ol.layer.VectorTileRenderType.IMAGE || - options.renderMode == ol.layer.VectorTileRenderType.HYBRID || - options.renderMode == ol.layer.VectorTileRenderType.VECTOR, - 28); // `renderMode` must be `'image'`, `'hybrid'` or `'vector'` - - /** - * @private - * @type {ol.layer.VectorTileRenderType|string} - */ - this.renderMode_ = options.renderMode || ol.layer.VectorTileRenderType.HYBRID; - - /** - * The layer type. - * @protected - * @type {ol.LayerType} - */ - this.type = ol.LayerType.VECTOR_TILE; - -}; -ol.inherits(ol.layer.VectorTile, ol.layer.Vector); - - -/** - * Return the level as number to which we will preload tiles up to. - * @return {number} The level to preload tiles up to. - * @observable - * @api - */ -ol.layer.VectorTile.prototype.getPreload = function() { - return /** @type {number} */ (this.get(ol.layer.TileProperty.PRELOAD)); -}; - - -/** - * @return {ol.layer.VectorTileRenderType|string} The render mode. - */ -ol.layer.VectorTile.prototype.getRenderMode = function() { - return this.renderMode_; -}; - - -/** - * Whether we use interim tiles on error. - * @return {boolean} Use interim tiles on error. - * @observable - * @api - */ -ol.layer.VectorTile.prototype.getUseInterimTilesOnError = function() { - return /** @type {boolean} */ ( - this.get(ol.layer.TileProperty.USE_INTERIM_TILES_ON_ERROR)); -}; - - -/** - * Set the level as number to which we will preload tiles up to. - * @param {number} preload The level to preload tiles up to. - * @observable - * @api - */ -ol.layer.VectorTile.prototype.setPreload = function(preload) { - this.set(ol.layer.TileProperty.PRELOAD, preload); -}; - - -/** - * Set whether we use interim tiles on error. - * @param {boolean} useInterimTilesOnError Use interim tiles on error. - * @observable - * @api - */ -ol.layer.VectorTile.prototype.setUseInterimTilesOnError = function(useInterimTilesOnError) { - this.set( - ol.layer.TileProperty.USE_INTERIM_TILES_ON_ERROR, useInterimTilesOnError); -}; - - -/** - * Return the associated {@link ol.source.VectorTile vectortilesource} of the layer. - * @function - * @return {ol.source.VectorTile} Source. - * @api - */ -ol.layer.VectorTile.prototype.getSource; - -goog.provide('ol.webgl.Shader'); - -goog.require('ol.functions'); - - -/** - * @constructor - * @abstract - * @param {string} source Source. - * @struct - */ -ol.webgl.Shader = function(source) { - - /** - * @private - * @type {string} - */ - this.source_ = source; - -}; - - -/** - * @abstract - * @return {number} Type. - */ -ol.webgl.Shader.prototype.getType = function() {}; - - -/** - * @return {string} Source. - */ -ol.webgl.Shader.prototype.getSource = function() { - return this.source_; -}; - - -/** - * @return {boolean} Is animated? - */ -ol.webgl.Shader.prototype.isAnimated = ol.functions.FALSE; - -goog.provide('ol.webgl.Fragment'); - -goog.require('ol'); -goog.require('ol.webgl'); -goog.require('ol.webgl.Shader'); - - -/** - * @constructor - * @extends {ol.webgl.Shader} - * @param {string} source Source. - * @struct - */ -ol.webgl.Fragment = function(source) { - ol.webgl.Shader.call(this, source); -}; -ol.inherits(ol.webgl.Fragment, ol.webgl.Shader); - - -/** - * @inheritDoc - */ -ol.webgl.Fragment.prototype.getType = function() { - return ol.webgl.FRAGMENT_SHADER; -}; - -goog.provide('ol.webgl.Vertex'); - -goog.require('ol'); -goog.require('ol.webgl'); -goog.require('ol.webgl.Shader'); - - -/** - * @constructor - * @extends {ol.webgl.Shader} - * @param {string} source Source. - * @struct - */ -ol.webgl.Vertex = function(source) { - ol.webgl.Shader.call(this, source); -}; -ol.inherits(ol.webgl.Vertex, ol.webgl.Shader); - - -/** - * @inheritDoc - */ -ol.webgl.Vertex.prototype.getType = function() { - return ol.webgl.VERTEX_SHADER; -}; - -// This file is automatically generated, do not edit -goog.provide('ol.render.webgl.circlereplay.defaultshader'); - -goog.require('ol'); -goog.require('ol.webgl.Fragment'); -goog.require('ol.webgl.Vertex'); - - -ol.render.webgl.circlereplay.defaultshader.fragment = new ol.webgl.Fragment(ol.DEBUG_WEBGL ? - 'precision mediump float;\nvarying vec2 v_center;\nvarying vec2 v_offset;\nvarying float v_halfWidth;\nvarying float v_pixelRatio;\n\n\n\nuniform float u_opacity;\nuniform vec4 u_fillColor;\nuniform vec4 u_strokeColor;\nuniform vec2 u_size;\n\nvoid main(void) {\n vec2 windowCenter = vec2((v_center.x + 1.0) / 2.0 * u_size.x * v_pixelRatio,\n (v_center.y + 1.0) / 2.0 * u_size.y * v_pixelRatio);\n vec2 windowOffset = vec2((v_offset.x + 1.0) / 2.0 * u_size.x * v_pixelRatio,\n (v_offset.y + 1.0) / 2.0 * u_size.y * v_pixelRatio);\n float radius = length(windowCenter - windowOffset);\n float dist = length(windowCenter - gl_FragCoord.xy);\n if (dist > radius + v_halfWidth) {\n if (u_strokeColor.a == 0.0) {\n gl_FragColor = u_fillColor;\n } else {\n gl_FragColor = u_strokeColor;\n }\n gl_FragColor.a = gl_FragColor.a - (dist - (radius + v_halfWidth));\n } else if (u_fillColor.a == 0.0) {\n // Hooray, no fill, just stroke. We can use real antialiasing.\n gl_FragColor = u_strokeColor;\n if (dist < radius - v_halfWidth) {\n gl_FragColor.a = gl_FragColor.a - (radius - v_halfWidth - dist);\n }\n } else {\n gl_FragColor = u_fillColor;\n float strokeDist = radius - v_halfWidth;\n float antialias = 2.0 * v_pixelRatio;\n if (dist > strokeDist) {\n gl_FragColor = u_strokeColor;\n } else if (dist >= strokeDist - antialias) {\n float step = smoothstep(strokeDist - antialias, strokeDist, dist);\n gl_FragColor = mix(u_fillColor, u_strokeColor, step);\n }\n }\n gl_FragColor.a = gl_FragColor.a * u_opacity;\n if (gl_FragColor.a <= 0.0) {\n discard;\n }\n}\n' : - 'precision mediump float;varying vec2 a;varying vec2 b;varying float c;varying float d;uniform float m;uniform vec4 n;uniform vec4 o;uniform vec2 p;void main(void){vec2 windowCenter=vec2((a.x+1.0)/2.0*p.x*d,(a.y+1.0)/2.0*p.y*d);vec2 windowOffset=vec2((b.x+1.0)/2.0*p.x*d,(b.y+1.0)/2.0*p.y*d);float radius=length(windowCenter-windowOffset);float dist=length(windowCenter-gl_FragCoord.xy);if(dist>radius+c){if(o.a==0.0){gl_FragColor=n;}else{gl_FragColor=o;}gl_FragColor.a=gl_FragColor.a-(dist-(radius+c));}else if(n.a==0.0){gl_FragColor=o;if(dist<radius-c){gl_FragColor.a=gl_FragColor.a-(radius-c-dist);}} else{gl_FragColor=n;float strokeDist=radius-c;float antialias=2.0*d;if(dist>strokeDist){gl_FragColor=o;}else if(dist>=strokeDist-antialias){float step=smoothstep(strokeDist-antialias,strokeDist,dist);gl_FragColor=mix(n,o,step);}} gl_FragColor.a=gl_FragColor.a*m;if(gl_FragColor.a<=0.0){discard;}}'); - -ol.render.webgl.circlereplay.defaultshader.vertex = new ol.webgl.Vertex(ol.DEBUG_WEBGL ? - 'varying vec2 v_center;\nvarying vec2 v_offset;\nvarying float v_halfWidth;\nvarying float v_pixelRatio;\n\n\nattribute vec2 a_position;\nattribute float a_instruction;\nattribute float a_radius;\n\nuniform mat4 u_projectionMatrix;\nuniform mat4 u_offsetScaleMatrix;\nuniform mat4 u_offsetRotateMatrix;\nuniform float u_lineWidth;\nuniform float u_pixelRatio;\n\nvoid main(void) {\n mat4 offsetMatrix = u_offsetScaleMatrix * u_offsetRotateMatrix;\n v_center = vec4(u_projectionMatrix * vec4(a_position, 0.0, 1.0)).xy;\n v_pixelRatio = u_pixelRatio;\n float lineWidth = u_lineWidth * u_pixelRatio;\n v_halfWidth = lineWidth / 2.0;\n if (lineWidth == 0.0) {\n lineWidth = 2.0 * u_pixelRatio;\n }\n vec2 offset;\n // Radius with anitaliasing (roughly).\n float radius = a_radius + 3.0 * u_pixelRatio;\n // Until we get gl_VertexID in WebGL, we store an instruction.\n if (a_instruction == 0.0) {\n // Offsetting the edges of the triangle by lineWidth / 2 is necessary, however\n // we should also leave some space for the antialiasing, thus we offset by lineWidth.\n offset = vec2(-1.0, 1.0);\n } else if (a_instruction == 1.0) {\n offset = vec2(-1.0, -1.0);\n } else if (a_instruction == 2.0) {\n offset = vec2(1.0, -1.0);\n } else {\n offset = vec2(1.0, 1.0);\n }\n\n gl_Position = u_projectionMatrix * vec4(a_position + offset * radius, 0.0, 1.0) +\n offsetMatrix * vec4(offset * lineWidth, 0.0, 0.0);\n v_offset = vec4(u_projectionMatrix * vec4(a_position.x + a_radius, a_position.y,\n 0.0, 1.0)).xy;\n\n if (distance(v_center, v_offset) > 20000.0) {\n gl_Position = vec4(v_center, 0.0, 1.0);\n }\n}\n\n\n' : - 'varying vec2 a;varying vec2 b;varying float c;varying float d;attribute vec2 e;attribute float f;attribute float g;uniform mat4 h;uniform mat4 i;uniform mat4 j;uniform float k;uniform float l;void main(void){mat4 offsetMatrix=i*j;a=vec4(h*vec4(e,0.0,1.0)).xy;d=l;float lineWidth=k*l;c=lineWidth/2.0;if(lineWidth==0.0){lineWidth=2.0*l;}vec2 offset;float radius=g+3.0*l;//Until we get gl_VertexID in WebGL,we store an instruction.if(f==0.0){//Offsetting the edges of the triangle by lineWidth/2 is necessary,however//we should also leave some space for the antialiasing,thus we offset by lineWidth.offset=vec2(-1.0,1.0);}else if(f==1.0){offset=vec2(-1.0,-1.0);}else if(f==2.0){offset=vec2(1.0,-1.0);}else{offset=vec2(1.0,1.0);}gl_Position=h*vec4(e+offset*radius,0.0,1.0)+offsetMatrix*vec4(offset*lineWidth,0.0,0.0);b=vec4(h*vec4(e.x+g,e.y,0.0,1.0)).xy;if(distance(a,b)>20000.0){gl_Position=vec4(a,0.0,1.0);}}'); - -// This file is automatically generated, do not edit -goog.provide('ol.render.webgl.circlereplay.defaultshader.Locations'); - -goog.require('ol'); - - -/** - * @constructor - * @param {WebGLRenderingContext} gl GL. - * @param {WebGLProgram} program Program. - * @struct - */ -ol.render.webgl.circlereplay.defaultshader.Locations = function(gl, program) { - - /** - * @type {WebGLUniformLocation} - */ - this.u_projectionMatrix = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_projectionMatrix' : 'h'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_offsetScaleMatrix = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_offsetScaleMatrix' : 'i'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_offsetRotateMatrix = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_offsetRotateMatrix' : 'j'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_lineWidth = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_lineWidth' : 'k'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_pixelRatio = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_pixelRatio' : 'l'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_opacity = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_opacity' : 'm'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_fillColor = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_fillColor' : 'n'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_strokeColor = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_strokeColor' : 'o'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_size = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_size' : 'p'); - - /** - * @type {number} - */ - this.a_position = gl.getAttribLocation( - program, ol.DEBUG_WEBGL ? 'a_position' : 'e'); - - /** - * @type {number} - */ - this.a_instruction = gl.getAttribLocation( - program, ol.DEBUG_WEBGL ? 'a_instruction' : 'f'); - - /** - * @type {number} - */ - this.a_radius = gl.getAttribLocation( - program, ol.DEBUG_WEBGL ? 'a_radius' : 'g'); -}; - -goog.provide('ol.vec.Mat4'); - - -/** - * @return {Array.<number>} 4x4 matrix representing a 3D identity transform. - */ -ol.vec.Mat4.create = function() { - return [1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1]; -}; - - -/** - * @param {Array.<number>} mat4 Flattened 4x4 matrix receiving the result. - * @param {ol.Transform} transform Transformation matrix. - * @return {Array.<number>} 2D transformation matrix as flattened 4x4 matrix. - */ -ol.vec.Mat4.fromTransform = function(mat4, transform) { - mat4[0] = transform[0]; - mat4[1] = transform[1]; - mat4[4] = transform[2]; - mat4[5] = transform[3]; - mat4[12] = transform[4]; - mat4[13] = transform[5]; - return mat4; -}; - -goog.provide('ol.render.webgl.Replay'); - -goog.require('ol'); -goog.require('ol.extent'); -goog.require('ol.render.VectorContext'); -goog.require('ol.transform'); -goog.require('ol.vec.Mat4'); -goog.require('ol.webgl'); - - -/** - * @constructor - * @abstract - * @extends {ol.render.VectorContext} - * @param {number} tolerance Tolerance. - * @param {ol.Extent} maxExtent Max extent. - * @struct - */ -ol.render.webgl.Replay = function(tolerance, maxExtent) { - ol.render.VectorContext.call(this); - - /** - * @protected - * @type {number} - */ - this.tolerance = tolerance; - - /** - * @protected - * @const - * @type {ol.Extent} - */ - this.maxExtent = maxExtent; - - /** - * The origin of the coordinate system for the point coordinates sent to - * the GPU. To eliminate jitter caused by precision problems in the GPU - * we use the "Rendering Relative to Eye" technique described in the "3D - * Engine Design for Virtual Globes" book. - * @protected - * @type {ol.Coordinate} - */ - this.origin = ol.extent.getCenter(maxExtent); - - /** - * @private - * @type {ol.Transform} - */ - this.projectionMatrix_ = ol.transform.create(); - - /** - * @private - * @type {ol.Transform} - */ - this.offsetRotateMatrix_ = ol.transform.create(); - - /** - * @private - * @type {ol.Transform} - */ - this.offsetScaleMatrix_ = ol.transform.create(); - - /** - * @private - * @type {Array.<number>} - */ - this.tmpMat4_ = ol.vec.Mat4.create(); - - /** - * @protected - * @type {Array.<number>} - */ - this.indices = []; - - /** - * @protected - * @type {?ol.webgl.Buffer} - */ - this.indicesBuffer = null; - - /** - * Start index per feature (the index). - * @protected - * @type {Array.<number>} - */ - this.startIndices = []; - - /** - * Start index per feature (the feature). - * @protected - * @type {Array.<ol.Feature|ol.render.Feature>} - */ - this.startIndicesFeature = []; - - /** - * @protected - * @type {Array.<number>} - */ - this.vertices = []; - - /** - * @protected - * @type {?ol.webgl.Buffer} - */ - this.verticesBuffer = null; - - /** - * Optional parameter for PolygonReplay instances. - * @protected - * @type {ol.render.webgl.LineStringReplay|undefined} - */ - this.lineStringReplay = undefined; - -}; -ol.inherits(ol.render.webgl.Replay, ol.render.VectorContext); - - -/** - * @abstract - * @param {ol.webgl.Context} context WebGL context. - * @return {function()} Delete resources function. - */ -ol.render.webgl.Replay.prototype.getDeleteResourcesFunction = function(context) {}; - - -/** - * @abstract - * @param {ol.webgl.Context} context Context. - */ -ol.render.webgl.Replay.prototype.finish = function(context) {}; - - -/** - * @abstract - * @protected - * @param {WebGLRenderingContext} gl gl. - * @param {ol.webgl.Context} context Context. - * @param {ol.Size} size Size. - * @param {number} pixelRatio Pixel ratio. - * @return {ol.render.webgl.circlereplay.defaultshader.Locations| - ol.render.webgl.linestringreplay.defaultshader.Locations| - ol.render.webgl.polygonreplay.defaultshader.Locations| - ol.render.webgl.texturereplay.defaultshader.Locations} Locations. - */ -ol.render.webgl.Replay.prototype.setUpProgram = function(gl, context, size, pixelRatio) {}; - - -/** - * @abstract - * @protected - * @param {WebGLRenderingContext} gl gl. - * @param {ol.render.webgl.circlereplay.defaultshader.Locations| - ol.render.webgl.linestringreplay.defaultshader.Locations| - ol.render.webgl.polygonreplay.defaultshader.Locations| - ol.render.webgl.texturereplay.defaultshader.Locations} locations Locations. - */ -ol.render.webgl.Replay.prototype.shutDownProgram = function(gl, locations) {}; - - -/** - * @abstract - * @protected - * @param {WebGLRenderingContext} gl gl. - * @param {ol.webgl.Context} context Context. - * @param {Object.<string, boolean>} skippedFeaturesHash Ids of features - * to skip. - * @param {boolean} hitDetection Hit detection mode. - */ -ol.render.webgl.Replay.prototype.drawReplay = function(gl, context, skippedFeaturesHash, hitDetection) {}; - - -/** - * @abstract - * @protected - * @param {WebGLRenderingContext} gl gl. - * @param {ol.webgl.Context} context Context. - * @param {Object.<string, boolean>} skippedFeaturesHash Ids of features - * to skip. - * @param {function((ol.Feature|ol.render.Feature)): T|undefined} featureCallback Feature callback. - * @param {ol.Extent=} opt_hitExtent Hit extent: Only features intersecting - * this extent are checked. - * @return {T|undefined} Callback result. - * @template T - */ -ol.render.webgl.Replay.prototype.drawHitDetectionReplayOneByOne = function(gl, context, skippedFeaturesHash, featureCallback, opt_hitExtent) {}; - - -/** - * @protected - * @param {WebGLRenderingContext} gl gl. - * @param {ol.webgl.Context} context Context. - * @param {Object.<string, boolean>} skippedFeaturesHash Ids of features - * to skip. - * @param {function((ol.Feature|ol.render.Feature)): T|undefined} featureCallback Feature callback. - * @param {boolean} oneByOne Draw features one-by-one for the hit-detecion. - * @param {ol.Extent=} opt_hitExtent Hit extent: Only features intersecting - * this extent are checked. - * @return {T|undefined} Callback result. - * @template T - */ -ol.render.webgl.Replay.prototype.drawHitDetectionReplay = function(gl, context, skippedFeaturesHash, - featureCallback, oneByOne, opt_hitExtent) { - if (!oneByOne) { - // draw all hit-detection features in "once" (by texture group) - return this.drawHitDetectionReplayAll(gl, context, - skippedFeaturesHash, featureCallback); - } else { - // draw hit-detection features one by one - return this.drawHitDetectionReplayOneByOne(gl, context, - skippedFeaturesHash, featureCallback, opt_hitExtent); - } -}; - - -/** - * @protected - * @param {WebGLRenderingContext} gl gl. - * @param {ol.webgl.Context} context Context. - * @param {Object.<string, boolean>} skippedFeaturesHash Ids of features - * to skip. - * @param {function((ol.Feature|ol.render.Feature)): T|undefined} featureCallback Feature callback. - * @return {T|undefined} Callback result. - * @template T - */ -ol.render.webgl.Replay.prototype.drawHitDetectionReplayAll = function(gl, context, skippedFeaturesHash, - featureCallback) { - gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT); - this.drawReplay(gl, context, skippedFeaturesHash, true); - - var result = featureCallback(null); - if (result) { - return result; - } else { - return undefined; - } -}; - - -/** - * @param {ol.webgl.Context} context Context. - * @param {ol.Coordinate} center Center. - * @param {number} resolution Resolution. - * @param {number} rotation Rotation. - * @param {ol.Size} size Size. - * @param {number} pixelRatio Pixel ratio. - * @param {number} opacity Global opacity. - * @param {Object.<string, boolean>} skippedFeaturesHash Ids of features - * to skip. - * @param {function((ol.Feature|ol.render.Feature)): T|undefined} featureCallback Feature callback. - * @param {boolean} oneByOne Draw features one-by-one for the hit-detecion. - * @param {ol.Extent=} opt_hitExtent Hit extent: Only features intersecting - * this extent are checked. - * @return {T|undefined} Callback result. - * @template T - */ -ol.render.webgl.Replay.prototype.replay = function(context, - center, resolution, rotation, size, pixelRatio, - opacity, skippedFeaturesHash, - featureCallback, oneByOne, opt_hitExtent) { - var gl = context.getGL(); - var tmpStencil, tmpStencilFunc, tmpStencilMaskVal, tmpStencilRef, tmpStencilMask, - tmpStencilOpFail, tmpStencilOpPass, tmpStencilOpZFail; - - if (this.lineStringReplay) { - tmpStencil = gl.isEnabled(gl.STENCIL_TEST); - tmpStencilFunc = gl.getParameter(gl.STENCIL_FUNC); - tmpStencilMaskVal = gl.getParameter(gl.STENCIL_VALUE_MASK); - tmpStencilRef = gl.getParameter(gl.STENCIL_REF); - tmpStencilMask = gl.getParameter(gl.STENCIL_WRITEMASK); - tmpStencilOpFail = gl.getParameter(gl.STENCIL_FAIL); - tmpStencilOpPass = gl.getParameter(gl.STENCIL_PASS_DEPTH_PASS); - tmpStencilOpZFail = gl.getParameter(gl.STENCIL_PASS_DEPTH_FAIL); - - gl.enable(gl.STENCIL_TEST); - gl.clear(gl.STENCIL_BUFFER_BIT); - gl.stencilMask(255); - gl.stencilFunc(gl.ALWAYS, 1, 255); - gl.stencilOp(gl.KEEP, gl.KEEP, gl.REPLACE); - - this.lineStringReplay.replay(context, - center, resolution, rotation, size, pixelRatio, - opacity, skippedFeaturesHash, - featureCallback, oneByOne, opt_hitExtent); - - gl.stencilMask(0); - gl.stencilFunc(gl.NOTEQUAL, 1, 255); - } - - context.bindBuffer(ol.webgl.ARRAY_BUFFER, this.verticesBuffer); - - context.bindBuffer(ol.webgl.ELEMENT_ARRAY_BUFFER, this.indicesBuffer); - - var locations = this.setUpProgram(gl, context, size, pixelRatio); - - // set the "uniform" values - var projectionMatrix = ol.transform.reset(this.projectionMatrix_); - ol.transform.scale(projectionMatrix, 2 / (resolution * size[0]), 2 / (resolution * size[1])); - ol.transform.rotate(projectionMatrix, -rotation); - ol.transform.translate(projectionMatrix, -(center[0] - this.origin[0]), -(center[1] - this.origin[1])); - - var offsetScaleMatrix = ol.transform.reset(this.offsetScaleMatrix_); - ol.transform.scale(offsetScaleMatrix, 2 / size[0], 2 / size[1]); - - var offsetRotateMatrix = ol.transform.reset(this.offsetRotateMatrix_); - if (rotation !== 0) { - ol.transform.rotate(offsetRotateMatrix, -rotation); - } - - gl.uniformMatrix4fv(locations.u_projectionMatrix, false, - ol.vec.Mat4.fromTransform(this.tmpMat4_, projectionMatrix)); - gl.uniformMatrix4fv(locations.u_offsetScaleMatrix, false, - ol.vec.Mat4.fromTransform(this.tmpMat4_, offsetScaleMatrix)); - gl.uniformMatrix4fv(locations.u_offsetRotateMatrix, false, - ol.vec.Mat4.fromTransform(this.tmpMat4_, offsetRotateMatrix)); - gl.uniform1f(locations.u_opacity, opacity); - - // draw! - var result; - if (featureCallback === undefined) { - this.drawReplay(gl, context, skippedFeaturesHash, false); - } else { - // draw feature by feature for the hit-detection - result = this.drawHitDetectionReplay(gl, context, skippedFeaturesHash, - featureCallback, oneByOne, opt_hitExtent); - } - - // disable the vertex attrib arrays - this.shutDownProgram(gl, locations); - - if (this.lineStringReplay) { - if (!tmpStencil) { - gl.disable(gl.STENCIL_TEST); - } - gl.clear(gl.STENCIL_BUFFER_BIT); - gl.stencilFunc(/** @type {number} */ (tmpStencilFunc), - /** @type {number} */ (tmpStencilRef), /** @type {number} */ (tmpStencilMaskVal)); - gl.stencilMask(/** @type {number} */ (tmpStencilMask)); - gl.stencilOp(/** @type {number} */ (tmpStencilOpFail), - /** @type {number} */ (tmpStencilOpZFail), /** @type {number} */ (tmpStencilOpPass)); - } - - return result; -}; - -/** - * @protected - * @param {WebGLRenderingContext} gl gl. - * @param {ol.webgl.Context} context Context. - * @param {number} start Start index. - * @param {number} end End index. - */ -ol.render.webgl.Replay.prototype.drawElements = function( - gl, context, start, end) { - var elementType = context.hasOESElementIndexUint ? - ol.webgl.UNSIGNED_INT : ol.webgl.UNSIGNED_SHORT; - var elementSize = context.hasOESElementIndexUint ? 4 : 2; - - var numItems = end - start; - var offsetInBytes = start * elementSize; - gl.drawElements(ol.webgl.TRIANGLES, numItems, elementType, offsetInBytes); -}; - -goog.provide('ol.render.webgl'); - - -/** - * @const - * @type {string} - */ -ol.render.webgl.defaultFont = '10px sans-serif'; - - -/** - * @const - * @type {ol.Color} - */ -ol.render.webgl.defaultFillStyle = [0.0, 0.0, 0.0, 1.0]; - - -/** - * @const - * @type {string} - */ -ol.render.webgl.defaultLineCap = 'round'; - - -/** - * @const - * @type {Array.<number>} - */ -ol.render.webgl.defaultLineDash = []; - - -/** - * @const - * @type {number} - */ -ol.render.webgl.defaultLineDashOffset = 0; - - -/** - * @const - * @type {string} - */ -ol.render.webgl.defaultLineJoin = 'round'; - - -/** - * @const - * @type {number} - */ -ol.render.webgl.defaultMiterLimit = 10; - -/** - * @const - * @type {ol.Color} - */ -ol.render.webgl.defaultStrokeStyle = [0.0, 0.0, 0.0, 1.0]; - - -/** - * @const - * @type {number} - */ -ol.render.webgl.defaultTextAlign = 0.5; - - -/** - * @const - * @type {number} - */ -ol.render.webgl.defaultTextBaseline = 0.5; - - -/** - * @const - * @type {number} - */ -ol.render.webgl.defaultLineWidth = 1; - -/** - * Calculates the orientation of a triangle based on the determinant method. - * @param {number} x1 First X coordinate. - * @param {number} y1 First Y coordinate. - * @param {number} x2 Second X coordinate. - * @param {number} y2 Second Y coordinate. - * @param {number} x3 Third X coordinate. - * @param {number} y3 Third Y coordinate. - * @return {boolean|undefined} Triangle is clockwise. - */ -ol.render.webgl.triangleIsCounterClockwise = function(x1, y1, x2, y2, x3, y3) { - var area = (x2 - x1) * (y3 - y1) - (x3 - x1) * (y2 - y1); - return (area <= ol.render.webgl.EPSILON && area >= -ol.render.webgl.EPSILON) ? - undefined : area > 0; -}; - -/** - * @const - * @type {number} - */ -ol.render.webgl.EPSILON = Number.EPSILON || 2.220446049250313e-16; - -goog.provide('ol.webgl.Buffer'); - -goog.require('ol.webgl'); - - -/** - * @constructor - * @param {Array.<number>=} opt_arr Array. - * @param {number=} opt_usage Usage. - * @struct - */ -ol.webgl.Buffer = function(opt_arr, opt_usage) { - - /** - * @private - * @type {Array.<number>} - */ - this.arr_ = opt_arr !== undefined ? opt_arr : []; - - /** - * @private - * @type {number} - */ - this.usage_ = opt_usage !== undefined ? - opt_usage : ol.webgl.Buffer.Usage_.STATIC_DRAW; - -}; - - -/** - * @return {Array.<number>} Array. - */ -ol.webgl.Buffer.prototype.getArray = function() { - return this.arr_; -}; - - -/** - * @return {number} Usage. - */ -ol.webgl.Buffer.prototype.getUsage = function() { - return this.usage_; -}; - - -/** - * @enum {number} - * @private - */ -ol.webgl.Buffer.Usage_ = { - STATIC_DRAW: ol.webgl.STATIC_DRAW, - STREAM_DRAW: ol.webgl.STREAM_DRAW, - DYNAMIC_DRAW: ol.webgl.DYNAMIC_DRAW -}; - -goog.provide('ol.render.webgl.CircleReplay'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.color'); -goog.require('ol.extent'); -goog.require('ol.obj'); -goog.require('ol.geom.flat.transform'); -goog.require('ol.render.webgl.circlereplay.defaultshader'); -goog.require('ol.render.webgl.circlereplay.defaultshader.Locations'); -goog.require('ol.render.webgl.Replay'); -goog.require('ol.render.webgl'); -goog.require('ol.webgl'); -goog.require('ol.webgl.Buffer'); - - -/** - * @constructor - * @extends {ol.render.webgl.Replay} - * @param {number} tolerance Tolerance. - * @param {ol.Extent} maxExtent Max extent. - * @struct - */ -ol.render.webgl.CircleReplay = function(tolerance, maxExtent) { - ol.render.webgl.Replay.call(this, tolerance, maxExtent); - - /** - * @private - * @type {ol.render.webgl.circlereplay.defaultshader.Locations} - */ - this.defaultLocations_ = null; - - /** - * @private - * @type {Array.<Array.<Array.<number>|number>>} - */ - this.styles_ = []; - - /** - * @private - * @type {Array.<number>} - */ - this.styleIndices_ = []; - - /** - * @private - * @type {number} - */ - this.radius_ = 0; - - /** - * @private - * @type {{fillColor: (Array.<number>|null), - * strokeColor: (Array.<number>|null), - * lineDash: Array.<number>, - * lineDashOffset: (number|undefined), - * lineWidth: (number|undefined), - * changed: boolean}|null} - */ - this.state_ = { - fillColor: null, - strokeColor: null, - lineDash: null, - lineDashOffset: undefined, - lineWidth: undefined, - changed: false - }; - -}; -ol.inherits(ol.render.webgl.CircleReplay, ol.render.webgl.Replay); - - -/** - * @private - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - */ -ol.render.webgl.CircleReplay.prototype.drawCoordinates_ = function( - flatCoordinates, offset, end, stride) { - var numVertices = this.vertices.length; - var numIndices = this.indices.length; - var n = numVertices / 4; - var i, ii; - for (i = offset, ii = end; i < ii; i += stride) { - this.vertices[numVertices++] = flatCoordinates[i]; - this.vertices[numVertices++] = flatCoordinates[i + 1]; - this.vertices[numVertices++] = 0; - this.vertices[numVertices++] = this.radius_; - - this.vertices[numVertices++] = flatCoordinates[i]; - this.vertices[numVertices++] = flatCoordinates[i + 1]; - this.vertices[numVertices++] = 1; - this.vertices[numVertices++] = this.radius_; - - this.vertices[numVertices++] = flatCoordinates[i]; - this.vertices[numVertices++] = flatCoordinates[i + 1]; - this.vertices[numVertices++] = 2; - this.vertices[numVertices++] = this.radius_; - - this.vertices[numVertices++] = flatCoordinates[i]; - this.vertices[numVertices++] = flatCoordinates[i + 1]; - this.vertices[numVertices++] = 3; - this.vertices[numVertices++] = this.radius_; - - this.indices[numIndices++] = n; - this.indices[numIndices++] = n + 1; - this.indices[numIndices++] = n + 2; - - this.indices[numIndices++] = n + 2; - this.indices[numIndices++] = n + 3; - this.indices[numIndices++] = n; - - n += 4; - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.CircleReplay.prototype.drawCircle = function(circleGeometry, feature) { - var radius = circleGeometry.getRadius(); - var stride = circleGeometry.getStride(); - if (radius) { - this.startIndices.push(this.indices.length); - this.startIndicesFeature.push(feature); - if (this.state_.changed) { - this.styleIndices_.push(this.indices.length); - this.state_.changed = false; - } - - this.radius_ = radius; - var flatCoordinates = circleGeometry.getFlatCoordinates(); - flatCoordinates = ol.geom.flat.transform.translate(flatCoordinates, 0, 2, - stride, -this.origin[0], -this.origin[1]); - this.drawCoordinates_(flatCoordinates, 0, 2, stride); - } else { - if (this.state_.changed) { - this.styles_.pop(); - if (this.styles_.length) { - var lastState = this.styles_[this.styles_.length - 1]; - this.state_.fillColor = /** @type {Array.<number>} */ (lastState[0]); - this.state_.strokeColor = /** @type {Array.<number>} */ (lastState[1]); - this.state_.lineWidth = /** @type {number} */ (lastState[2]); - this.state_.changed = false; - } - } - } -}; - - -/** - * @inheritDoc - **/ -ol.render.webgl.CircleReplay.prototype.finish = function(context) { - // create, bind, and populate the vertices buffer - this.verticesBuffer = new ol.webgl.Buffer(this.vertices); - - // create, bind, and populate the indices buffer - this.indicesBuffer = new ol.webgl.Buffer(this.indices); - - this.startIndices.push(this.indices.length); - - //Clean up, if there is nothing to draw - if (this.styleIndices_.length === 0 && this.styles_.length > 0) { - this.styles_ = []; - } - - this.vertices = null; - this.indices = null; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.CircleReplay.prototype.getDeleteResourcesFunction = function(context) { - // We only delete our stuff here. The shaders and the program may - // be used by other CircleReplay instances (for other layers). And - // they will be deleted when disposing of the ol.webgl.Context - // object. - var verticesBuffer = this.verticesBuffer; - var indicesBuffer = this.indicesBuffer; - return function() { - context.deleteBuffer(verticesBuffer); - context.deleteBuffer(indicesBuffer); - }; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.CircleReplay.prototype.setUpProgram = function(gl, context, size, pixelRatio) { - // get the program - var fragmentShader, vertexShader; - fragmentShader = ol.render.webgl.circlereplay.defaultshader.fragment; - vertexShader = ol.render.webgl.circlereplay.defaultshader.vertex; - var program = context.getProgram(fragmentShader, vertexShader); - - // get the locations - var locations; - if (!this.defaultLocations_) { - locations = new ol.render.webgl.circlereplay.defaultshader.Locations(gl, program); - this.defaultLocations_ = locations; - } else { - locations = this.defaultLocations_; - } - - context.useProgram(program); - - // enable the vertex attrib arrays - gl.enableVertexAttribArray(locations.a_position); - gl.vertexAttribPointer(locations.a_position, 2, ol.webgl.FLOAT, - false, 16, 0); - - gl.enableVertexAttribArray(locations.a_instruction); - gl.vertexAttribPointer(locations.a_instruction, 1, ol.webgl.FLOAT, - false, 16, 8); - - gl.enableVertexAttribArray(locations.a_radius); - gl.vertexAttribPointer(locations.a_radius, 1, ol.webgl.FLOAT, - false, 16, 12); - - // Enable renderer specific uniforms. - gl.uniform2fv(locations.u_size, size); - gl.uniform1f(locations.u_pixelRatio, pixelRatio); - - return locations; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.CircleReplay.prototype.shutDownProgram = function(gl, locations) { - gl.disableVertexAttribArray(locations.a_position); - gl.disableVertexAttribArray(locations.a_instruction); - gl.disableVertexAttribArray(locations.a_radius); -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.CircleReplay.prototype.drawReplay = function(gl, context, skippedFeaturesHash, hitDetection) { - if (!ol.obj.isEmpty(skippedFeaturesHash)) { - this.drawReplaySkipping_(gl, context, skippedFeaturesHash); - } else { - //Draw by style groups to minimize drawElements() calls. - var i, start, end, nextStyle; - end = this.startIndices[this.startIndices.length - 1]; - for (i = this.styleIndices_.length - 1; i >= 0; --i) { - start = this.styleIndices_[i]; - nextStyle = this.styles_[i]; - this.setFillStyle_(gl, /** @type {Array.<number>} */ (nextStyle[0])); - this.setStrokeStyle_(gl, /** @type {Array.<number>} */ (nextStyle[1]), - /** @type {number} */ (nextStyle[2])); - this.drawElements(gl, context, start, end); - end = start; - } - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.CircleReplay.prototype.drawHitDetectionReplayOneByOne = function(gl, context, skippedFeaturesHash, - featureCallback, opt_hitExtent) { - var i, start, end, nextStyle, groupStart, feature, featureUid, featureIndex; - featureIndex = this.startIndices.length - 2; - end = this.startIndices[featureIndex + 1]; - for (i = this.styleIndices_.length - 1; i >= 0; --i) { - nextStyle = this.styles_[i]; - this.setFillStyle_(gl, /** @type {Array.<number>} */ (nextStyle[0])); - this.setStrokeStyle_(gl, /** @type {Array.<number>} */ (nextStyle[1]), - /** @type {number} */ (nextStyle[2])); - groupStart = this.styleIndices_[i]; - - while (featureIndex >= 0 && - this.startIndices[featureIndex] >= groupStart) { - start = this.startIndices[featureIndex]; - feature = this.startIndicesFeature[featureIndex]; - featureUid = ol.getUid(feature).toString(); - - if (skippedFeaturesHash[featureUid] === undefined && - feature.getGeometry() && - (opt_hitExtent === undefined || ol.extent.intersects( - /** @type {Array<number>} */ (opt_hitExtent), - feature.getGeometry().getExtent()))) { - gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT); - this.drawElements(gl, context, start, end); - - var result = featureCallback(feature); - - if (result) { - return result; - } - - } - featureIndex--; - end = start; - } - } - return undefined; -}; - - -/** - * @private - * @param {WebGLRenderingContext} gl gl. - * @param {ol.webgl.Context} context Context. - * @param {Object} skippedFeaturesHash Ids of features to skip. - */ -ol.render.webgl.CircleReplay.prototype.drawReplaySkipping_ = function(gl, context, skippedFeaturesHash) { - var i, start, end, nextStyle, groupStart, feature, featureUid, featureIndex, featureStart; - featureIndex = this.startIndices.length - 2; - end = start = this.startIndices[featureIndex + 1]; - for (i = this.styleIndices_.length - 1; i >= 0; --i) { - nextStyle = this.styles_[i]; - this.setFillStyle_(gl, /** @type {Array.<number>} */ (nextStyle[0])); - this.setStrokeStyle_(gl, /** @type {Array.<number>} */ (nextStyle[1]), - /** @type {number} */ (nextStyle[2])); - groupStart = this.styleIndices_[i]; - - while (featureIndex >= 0 && - this.startIndices[featureIndex] >= groupStart) { - featureStart = this.startIndices[featureIndex]; - feature = this.startIndicesFeature[featureIndex]; - featureUid = ol.getUid(feature).toString(); - - if (skippedFeaturesHash[featureUid]) { - if (start !== end) { - this.drawElements(gl, context, start, end); - } - end = featureStart; - } - featureIndex--; - start = featureStart; - } - if (start !== end) { - this.drawElements(gl, context, start, end); - } - start = end = groupStart; - } -}; - - -/** - * @private - * @param {WebGLRenderingContext} gl gl. - * @param {Array.<number>} color Color. - */ -ol.render.webgl.CircleReplay.prototype.setFillStyle_ = function(gl, color) { - gl.uniform4fv(this.defaultLocations_.u_fillColor, color); -}; - - -/** - * @private - * @param {WebGLRenderingContext} gl gl. - * @param {Array.<number>} color Color. - * @param {number} lineWidth Line width. - */ -ol.render.webgl.CircleReplay.prototype.setStrokeStyle_ = function(gl, color, lineWidth) { - gl.uniform4fv(this.defaultLocations_.u_strokeColor, color); - gl.uniform1f(this.defaultLocations_.u_lineWidth, lineWidth); -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.CircleReplay.prototype.setFillStrokeStyle = function(fillStyle, strokeStyle) { - var strokeStyleColor, strokeStyleWidth; - if (strokeStyle) { - var strokeStyleLineDash = strokeStyle.getLineDash(); - this.state_.lineDash = strokeStyleLineDash ? - strokeStyleLineDash : ol.render.webgl.defaultLineDash; - var strokeStyleLineDashOffset = strokeStyle.getLineDashOffset(); - this.state_.lineDashOffset = strokeStyleLineDashOffset ? - strokeStyleLineDashOffset : ol.render.webgl.defaultLineDashOffset; - strokeStyleColor = strokeStyle.getColor(); - if (!(strokeStyleColor instanceof CanvasGradient) && - !(strokeStyleColor instanceof CanvasPattern)) { - strokeStyleColor = ol.color.asArray(strokeStyleColor).map(function(c, i) { - return i != 3 ? c / 255 : c; - }) || ol.render.webgl.defaultStrokeStyle; - } else { - strokeStyleColor = ol.render.webgl.defaultStrokeStyle; - } - strokeStyleWidth = strokeStyle.getWidth(); - strokeStyleWidth = strokeStyleWidth !== undefined ? - strokeStyleWidth : ol.render.webgl.defaultLineWidth; - } else { - strokeStyleColor = [0, 0, 0, 0]; - strokeStyleWidth = 0; - } - var fillStyleColor = fillStyle ? fillStyle.getColor() : [0, 0, 0, 0]; - if (!(fillStyleColor instanceof CanvasGradient) && - !(fillStyleColor instanceof CanvasPattern)) { - fillStyleColor = ol.color.asArray(fillStyleColor).map(function(c, i) { - return i != 3 ? c / 255 : c; - }) || ol.render.webgl.defaultFillStyle; - } else { - fillStyleColor = ol.render.webgl.defaultFillStyle; - } - if (!this.state_.strokeColor || !ol.array.equals(this.state_.strokeColor, strokeStyleColor) || - !this.state_.fillColor || !ol.array.equals(this.state_.fillColor, fillStyleColor) || - this.state_.lineWidth !== strokeStyleWidth) { - this.state_.changed = true; - this.state_.fillColor = fillStyleColor; - this.state_.strokeColor = strokeStyleColor; - this.state_.lineWidth = strokeStyleWidth; - this.styles_.push([fillStyleColor, strokeStyleColor, strokeStyleWidth]); - } -}; - -// This file is automatically generated, do not edit -goog.provide('ol.render.webgl.texturereplay.defaultshader'); - -goog.require('ol'); -goog.require('ol.webgl.Fragment'); -goog.require('ol.webgl.Vertex'); - - -ol.render.webgl.texturereplay.defaultshader.fragment = new ol.webgl.Fragment(ol.DEBUG_WEBGL ? - 'precision mediump float;\nvarying vec2 v_texCoord;\nvarying float v_opacity;\n\nuniform float u_opacity;\nuniform sampler2D u_image;\n\nvoid main(void) {\n vec4 texColor = texture2D(u_image, v_texCoord);\n gl_FragColor.rgb = texColor.rgb;\n float alpha = texColor.a * v_opacity * u_opacity;\n if (alpha == 0.0) {\n discard;\n }\n gl_FragColor.a = alpha;\n}\n' : - 'precision mediump float;varying vec2 a;varying float b;uniform float k;uniform sampler2D l;void main(void){vec4 texColor=texture2D(l,a);gl_FragColor.rgb=texColor.rgb;float alpha=texColor.a*b*k;if(alpha==0.0){discard;}gl_FragColor.a=alpha;}'); - -ol.render.webgl.texturereplay.defaultshader.vertex = new ol.webgl.Vertex(ol.DEBUG_WEBGL ? - 'varying vec2 v_texCoord;\nvarying float v_opacity;\n\nattribute vec2 a_position;\nattribute vec2 a_texCoord;\nattribute vec2 a_offsets;\nattribute float a_opacity;\nattribute float a_rotateWithView;\n\nuniform mat4 u_projectionMatrix;\nuniform mat4 u_offsetScaleMatrix;\nuniform mat4 u_offsetRotateMatrix;\n\nvoid main(void) {\n mat4 offsetMatrix = u_offsetScaleMatrix;\n if (a_rotateWithView == 1.0) {\n offsetMatrix = u_offsetScaleMatrix * u_offsetRotateMatrix;\n }\n vec4 offsets = offsetMatrix * vec4(a_offsets, 0.0, 0.0);\n gl_Position = u_projectionMatrix * vec4(a_position, 0.0, 1.0) + offsets;\n v_texCoord = a_texCoord;\n v_opacity = a_opacity;\n}\n\n\n' : - 'varying vec2 a;varying float b;attribute vec2 c;attribute vec2 d;attribute vec2 e;attribute float f;attribute float g;uniform mat4 h;uniform mat4 i;uniform mat4 j;void main(void){mat4 offsetMatrix=i;if(g==1.0){offsetMatrix=i*j;}vec4 offsets=offsetMatrix*vec4(e,0.0,0.0);gl_Position=h*vec4(c,0.0,1.0)+offsets;a=d;b=f;}'); - -// This file is automatically generated, do not edit -goog.provide('ol.render.webgl.texturereplay.defaultshader.Locations'); - -goog.require('ol'); - - -/** - * @constructor - * @param {WebGLRenderingContext} gl GL. - * @param {WebGLProgram} program Program. - * @struct - */ -ol.render.webgl.texturereplay.defaultshader.Locations = function(gl, program) { - - /** - * @type {WebGLUniformLocation} - */ - this.u_projectionMatrix = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_projectionMatrix' : 'h'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_offsetScaleMatrix = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_offsetScaleMatrix' : 'i'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_offsetRotateMatrix = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_offsetRotateMatrix' : 'j'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_opacity = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_opacity' : 'k'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_image = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_image' : 'l'); - - /** - * @type {number} - */ - this.a_position = gl.getAttribLocation( - program, ol.DEBUG_WEBGL ? 'a_position' : 'c'); - - /** - * @type {number} - */ - this.a_texCoord = gl.getAttribLocation( - program, ol.DEBUG_WEBGL ? 'a_texCoord' : 'd'); - - /** - * @type {number} - */ - this.a_offsets = gl.getAttribLocation( - program, ol.DEBUG_WEBGL ? 'a_offsets' : 'e'); - - /** - * @type {number} - */ - this.a_opacity = gl.getAttribLocation( - program, ol.DEBUG_WEBGL ? 'a_opacity' : 'f'); - - /** - * @type {number} - */ - this.a_rotateWithView = gl.getAttribLocation( - program, ol.DEBUG_WEBGL ? 'a_rotateWithView' : 'g'); -}; - -goog.provide('ol.webgl.ContextEventType'); - - -/** - * @enum {string} - */ -ol.webgl.ContextEventType = { - LOST: 'webglcontextlost', - RESTORED: 'webglcontextrestored' -}; - -goog.provide('ol.webgl.Context'); - -goog.require('ol'); -goog.require('ol.Disposable'); -goog.require('ol.array'); -goog.require('ol.events'); -goog.require('ol.obj'); -goog.require('ol.webgl'); -goog.require('ol.webgl.ContextEventType'); - - -/** - * @classdesc - * A WebGL context for accessing low-level WebGL capabilities. - * - * @constructor - * @extends {ol.Disposable} - * @param {HTMLCanvasElement} canvas Canvas. - * @param {WebGLRenderingContext} gl GL. - */ -ol.webgl.Context = function(canvas, gl) { - - /** - * @private - * @type {HTMLCanvasElement} - */ - this.canvas_ = canvas; - - /** - * @private - * @type {WebGLRenderingContext} - */ - this.gl_ = gl; - - /** - * @private - * @type {Object.<string, ol.WebglBufferCacheEntry>} - */ - this.bufferCache_ = {}; - - /** - * @private - * @type {Object.<string, WebGLShader>} - */ - this.shaderCache_ = {}; - - /** - * @private - * @type {Object.<string, WebGLProgram>} - */ - this.programCache_ = {}; - - /** - * @private - * @type {WebGLProgram} - */ - this.currentProgram_ = null; - - /** - * @private - * @type {WebGLFramebuffer} - */ - this.hitDetectionFramebuffer_ = null; - - /** - * @private - * @type {WebGLTexture} - */ - this.hitDetectionTexture_ = null; - - /** - * @private - * @type {WebGLRenderbuffer} - */ - this.hitDetectionRenderbuffer_ = null; - - /** - * @type {boolean} - */ - this.hasOESElementIndexUint = ol.array.includes( - ol.WEBGL_EXTENSIONS, 'OES_element_index_uint'); - - // use the OES_element_index_uint extension if available - if (this.hasOESElementIndexUint) { - gl.getExtension('OES_element_index_uint'); - } - - ol.events.listen(this.canvas_, ol.webgl.ContextEventType.LOST, - this.handleWebGLContextLost, this); - ol.events.listen(this.canvas_, ol.webgl.ContextEventType.RESTORED, - this.handleWebGLContextRestored, this); - -}; -ol.inherits(ol.webgl.Context, ol.Disposable); - - -/** - * Just bind the buffer if it's in the cache. Otherwise create - * the WebGL buffer, bind it, populate it, and add an entry to - * the cache. - * @param {number} target Target. - * @param {ol.webgl.Buffer} buf Buffer. - */ -ol.webgl.Context.prototype.bindBuffer = function(target, buf) { - var gl = this.getGL(); - var arr = buf.getArray(); - var bufferKey = String(ol.getUid(buf)); - if (bufferKey in this.bufferCache_) { - var bufferCacheEntry = this.bufferCache_[bufferKey]; - gl.bindBuffer(target, bufferCacheEntry.buffer); - } else { - var buffer = gl.createBuffer(); - gl.bindBuffer(target, buffer); - var /** @type {ArrayBufferView} */ arrayBuffer; - if (target == ol.webgl.ARRAY_BUFFER) { - arrayBuffer = new Float32Array(arr); - } else if (target == ol.webgl.ELEMENT_ARRAY_BUFFER) { - arrayBuffer = this.hasOESElementIndexUint ? - new Uint32Array(arr) : new Uint16Array(arr); - } - gl.bufferData(target, arrayBuffer, buf.getUsage()); - this.bufferCache_[bufferKey] = { - buf: buf, - buffer: buffer - }; - } -}; - - -/** - * @param {ol.webgl.Buffer} buf Buffer. - */ -ol.webgl.Context.prototype.deleteBuffer = function(buf) { - var gl = this.getGL(); - var bufferKey = String(ol.getUid(buf)); - var bufferCacheEntry = this.bufferCache_[bufferKey]; - if (!gl.isContextLost()) { - gl.deleteBuffer(bufferCacheEntry.buffer); - } - delete this.bufferCache_[bufferKey]; -}; - - -/** - * @inheritDoc - */ -ol.webgl.Context.prototype.disposeInternal = function() { - ol.events.unlistenAll(this.canvas_); - var gl = this.getGL(); - if (!gl.isContextLost()) { - var key; - for (key in this.bufferCache_) { - gl.deleteBuffer(this.bufferCache_[key].buffer); - } - for (key in this.programCache_) { - gl.deleteProgram(this.programCache_[key]); - } - for (key in this.shaderCache_) { - gl.deleteShader(this.shaderCache_[key]); - } - // delete objects for hit-detection - gl.deleteFramebuffer(this.hitDetectionFramebuffer_); - gl.deleteRenderbuffer(this.hitDetectionRenderbuffer_); - gl.deleteTexture(this.hitDetectionTexture_); - } -}; - - -/** - * @return {HTMLCanvasElement} Canvas. - */ -ol.webgl.Context.prototype.getCanvas = function() { - return this.canvas_; -}; - - -/** - * Get the WebGL rendering context - * @return {WebGLRenderingContext} The rendering context. - * @api - */ -ol.webgl.Context.prototype.getGL = function() { - return this.gl_; -}; - - -/** - * Get the frame buffer for hit detection. - * @return {WebGLFramebuffer} The hit detection frame buffer. - */ -ol.webgl.Context.prototype.getHitDetectionFramebuffer = function() { - if (!this.hitDetectionFramebuffer_) { - this.initHitDetectionFramebuffer_(); - } - return this.hitDetectionFramebuffer_; -}; - - -/** - * Get shader from the cache if it's in the cache. Otherwise, create - * the WebGL shader, compile it, and add entry to cache. - * @param {ol.webgl.Shader} shaderObject Shader object. - * @return {WebGLShader} Shader. - */ -ol.webgl.Context.prototype.getShader = function(shaderObject) { - var shaderKey = String(ol.getUid(shaderObject)); - if (shaderKey in this.shaderCache_) { - return this.shaderCache_[shaderKey]; - } else { - var gl = this.getGL(); - var shader = gl.createShader(shaderObject.getType()); - gl.shaderSource(shader, shaderObject.getSource()); - gl.compileShader(shader); - this.shaderCache_[shaderKey] = shader; - return shader; - } -}; - - -/** - * Get the program from the cache if it's in the cache. Otherwise create - * the WebGL program, attach the shaders to it, and add an entry to the - * cache. - * @param {ol.webgl.Fragment} fragmentShaderObject Fragment shader. - * @param {ol.webgl.Vertex} vertexShaderObject Vertex shader. - * @return {WebGLProgram} Program. - */ -ol.webgl.Context.prototype.getProgram = function( - fragmentShaderObject, vertexShaderObject) { - var programKey = - ol.getUid(fragmentShaderObject) + '/' + ol.getUid(vertexShaderObject); - if (programKey in this.programCache_) { - return this.programCache_[programKey]; - } else { - var gl = this.getGL(); - var program = gl.createProgram(); - gl.attachShader(program, this.getShader(fragmentShaderObject)); - gl.attachShader(program, this.getShader(vertexShaderObject)); - gl.linkProgram(program); - this.programCache_[programKey] = program; - return program; - } -}; - - -/** - * FIXME empy description for jsdoc - */ -ol.webgl.Context.prototype.handleWebGLContextLost = function() { - ol.obj.clear(this.bufferCache_); - ol.obj.clear(this.shaderCache_); - ol.obj.clear(this.programCache_); - this.currentProgram_ = null; - this.hitDetectionFramebuffer_ = null; - this.hitDetectionTexture_ = null; - this.hitDetectionRenderbuffer_ = null; -}; - - -/** - * FIXME empy description for jsdoc - */ -ol.webgl.Context.prototype.handleWebGLContextRestored = function() { -}; - - -/** - * Creates a 1x1 pixel framebuffer for the hit-detection. - * @private - */ -ol.webgl.Context.prototype.initHitDetectionFramebuffer_ = function() { - var gl = this.gl_; - var framebuffer = gl.createFramebuffer(); - gl.bindFramebuffer(gl.FRAMEBUFFER, framebuffer); - - var texture = ol.webgl.Context.createEmptyTexture(gl, 1, 1); - var renderbuffer = gl.createRenderbuffer(); - gl.bindRenderbuffer(gl.RENDERBUFFER, renderbuffer); - gl.renderbufferStorage(gl.RENDERBUFFER, gl.DEPTH_COMPONENT16, 1, 1); - gl.framebufferTexture2D( - gl.FRAMEBUFFER, gl.COLOR_ATTACHMENT0, gl.TEXTURE_2D, texture, 0); - gl.framebufferRenderbuffer(gl.FRAMEBUFFER, gl.DEPTH_ATTACHMENT, - gl.RENDERBUFFER, renderbuffer); - - gl.bindTexture(gl.TEXTURE_2D, null); - gl.bindRenderbuffer(gl.RENDERBUFFER, null); - gl.bindFramebuffer(gl.FRAMEBUFFER, null); - - this.hitDetectionFramebuffer_ = framebuffer; - this.hitDetectionTexture_ = texture; - this.hitDetectionRenderbuffer_ = renderbuffer; -}; - - -/** - * Use a program. If the program is already in use, this will return `false`. - * @param {WebGLProgram} program Program. - * @return {boolean} Changed. - * @api - */ -ol.webgl.Context.prototype.useProgram = function(program) { - if (program == this.currentProgram_) { - return false; - } else { - var gl = this.getGL(); - gl.useProgram(program); - this.currentProgram_ = program; - return true; - } -}; - - -/** - * @param {WebGLRenderingContext} gl WebGL rendering context. - * @param {number=} opt_wrapS wrapS. - * @param {number=} opt_wrapT wrapT. - * @return {WebGLTexture} The texture. - * @private - */ -ol.webgl.Context.createTexture_ = function(gl, opt_wrapS, opt_wrapT) { - var texture = gl.createTexture(); - gl.bindTexture(gl.TEXTURE_2D, texture); - gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.LINEAR); - gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.LINEAR); - - if (opt_wrapS !== undefined) { - gl.texParameteri( - ol.webgl.TEXTURE_2D, ol.webgl.TEXTURE_WRAP_S, opt_wrapS); - } - if (opt_wrapT !== undefined) { - gl.texParameteri( - ol.webgl.TEXTURE_2D, ol.webgl.TEXTURE_WRAP_T, opt_wrapT); - } - - return texture; -}; - - -/** - * @param {WebGLRenderingContext} gl WebGL rendering context. - * @param {number} width Width. - * @param {number} height Height. - * @param {number=} opt_wrapS wrapS. - * @param {number=} opt_wrapT wrapT. - * @return {WebGLTexture} The texture. - */ -ol.webgl.Context.createEmptyTexture = function( - gl, width, height, opt_wrapS, opt_wrapT) { - var texture = ol.webgl.Context.createTexture_(gl, opt_wrapS, opt_wrapT); - gl.texImage2D( - gl.TEXTURE_2D, 0, gl.RGBA, width, height, 0, gl.RGBA, gl.UNSIGNED_BYTE, - null); - - return texture; -}; - - -/** - * @param {WebGLRenderingContext} gl WebGL rendering context. - * @param {HTMLCanvasElement|HTMLImageElement|HTMLVideoElement} image Image. - * @param {number=} opt_wrapS wrapS. - * @param {number=} opt_wrapT wrapT. - * @return {WebGLTexture} The texture. - */ -ol.webgl.Context.createTexture = function(gl, image, opt_wrapS, opt_wrapT) { - var texture = ol.webgl.Context.createTexture_(gl, opt_wrapS, opt_wrapT); - gl.texImage2D( - gl.TEXTURE_2D, 0, gl.RGBA, gl.RGBA, gl.UNSIGNED_BYTE, image); - - return texture; -}; - -goog.provide('ol.render.webgl.TextureReplay'); - -goog.require('ol'); -goog.require('ol.extent'); -goog.require('ol.obj'); -goog.require('ol.render.webgl.texturereplay.defaultshader'); -goog.require('ol.render.webgl.texturereplay.defaultshader.Locations'); -goog.require('ol.render.webgl.Replay'); -goog.require('ol.webgl'); -goog.require('ol.webgl.Context'); - -/** - * @constructor - * @abstract - * @extends {ol.render.webgl.Replay} - * @param {number} tolerance Tolerance. - * @param {ol.Extent} maxExtent Max extent. - * @struct - */ -ol.render.webgl.TextureReplay = function(tolerance, maxExtent) { - ol.render.webgl.Replay.call(this, tolerance, maxExtent); - - /** - * @type {number|undefined} - * @protected - */ - this.anchorX = undefined; - - /** - * @type {number|undefined} - * @protected - */ - this.anchorY = undefined; - - /** - * @type {Array.<number>} - * @protected - */ - this.groupIndices = []; - - /** - * @type {Array.<number>} - * @protected - */ - this.hitDetectionGroupIndices = []; - - /** - * @type {number|undefined} - * @protected - */ - this.height = undefined; - - /** - * @type {number|undefined} - * @protected - */ - this.imageHeight = undefined; - - /** - * @type {number|undefined} - * @protected - */ - this.imageWidth = undefined; - - /** - * @protected - * @type {ol.render.webgl.texturereplay.defaultshader.Locations} - */ - this.defaultLocations = null; - - /** - * @protected - * @type {number|undefined} - */ - this.opacity = undefined; - - /** - * @type {number|undefined} - * @protected - */ - this.originX = undefined; - - /** - * @type {number|undefined} - * @protected - */ - this.originY = undefined; - - /** - * @protected - * @type {boolean|undefined} - */ - this.rotateWithView = undefined; - - /** - * @protected - * @type {number|undefined} - */ - this.rotation = undefined; - - /** - * @protected - * @type {number|undefined} - */ - this.scale = undefined; - - /** - * @type {number|undefined} - * @protected - */ - this.width = undefined; -}; -ol.inherits(ol.render.webgl.TextureReplay, ol.render.webgl.Replay); - - -/** - * @inheritDoc - */ -ol.render.webgl.TextureReplay.prototype.getDeleteResourcesFunction = function(context) { - var verticesBuffer = this.verticesBuffer; - var indicesBuffer = this.indicesBuffer; - var textures = this.getTextures(true); - var gl = context.getGL(); - return function() { - if (!gl.isContextLost()) { - var i, ii; - for (i = 0, ii = textures.length; i < ii; ++i) { - gl.deleteTexture(textures[i]); - } - } - context.deleteBuffer(verticesBuffer); - context.deleteBuffer(indicesBuffer); - }; -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @return {number} My end. - * @protected - */ -ol.render.webgl.TextureReplay.prototype.drawCoordinates = function(flatCoordinates, offset, end, stride) { - var anchorX = /** @type {number} */ (this.anchorX); - var anchorY = /** @type {number} */ (this.anchorY); - var height = /** @type {number} */ (this.height); - var imageHeight = /** @type {number} */ (this.imageHeight); - var imageWidth = /** @type {number} */ (this.imageWidth); - var opacity = /** @type {number} */ (this.opacity); - var originX = /** @type {number} */ (this.originX); - var originY = /** @type {number} */ (this.originY); - var rotateWithView = this.rotateWithView ? 1.0 : 0.0; - // this.rotation_ is anti-clockwise, but rotation is clockwise - var rotation = /** @type {number} */ (-this.rotation); - var scale = /** @type {number} */ (this.scale); - var width = /** @type {number} */ (this.width); - var cos = Math.cos(rotation); - var sin = Math.sin(rotation); - var numIndices = this.indices.length; - var numVertices = this.vertices.length; - var i, n, offsetX, offsetY, x, y; - for (i = offset; i < end; i += stride) { - x = flatCoordinates[i] - this.origin[0]; - y = flatCoordinates[i + 1] - this.origin[1]; - - // There are 4 vertices per [x, y] point, one for each corner of the - // rectangle we're going to draw. We'd use 1 vertex per [x, y] point if - // WebGL supported Geometry Shaders (which can emit new vertices), but that - // is not currently the case. - // - // And each vertex includes 8 values: the x and y coordinates, the x and - // y offsets used to calculate the position of the corner, the u and - // v texture coordinates for the corner, the opacity, and whether the - // the image should be rotated with the view (rotateWithView). - - n = numVertices / 8; - - // bottom-left corner - offsetX = -scale * anchorX; - offsetY = -scale * (height - anchorY); - this.vertices[numVertices++] = x; - this.vertices[numVertices++] = y; - this.vertices[numVertices++] = offsetX * cos - offsetY * sin; - this.vertices[numVertices++] = offsetX * sin + offsetY * cos; - this.vertices[numVertices++] = originX / imageWidth; - this.vertices[numVertices++] = (originY + height) / imageHeight; - this.vertices[numVertices++] = opacity; - this.vertices[numVertices++] = rotateWithView; - - // bottom-right corner - offsetX = scale * (width - anchorX); - offsetY = -scale * (height - anchorY); - this.vertices[numVertices++] = x; - this.vertices[numVertices++] = y; - this.vertices[numVertices++] = offsetX * cos - offsetY * sin; - this.vertices[numVertices++] = offsetX * sin + offsetY * cos; - this.vertices[numVertices++] = (originX + width) / imageWidth; - this.vertices[numVertices++] = (originY + height) / imageHeight; - this.vertices[numVertices++] = opacity; - this.vertices[numVertices++] = rotateWithView; - - // top-right corner - offsetX = scale * (width - anchorX); - offsetY = scale * anchorY; - this.vertices[numVertices++] = x; - this.vertices[numVertices++] = y; - this.vertices[numVertices++] = offsetX * cos - offsetY * sin; - this.vertices[numVertices++] = offsetX * sin + offsetY * cos; - this.vertices[numVertices++] = (originX + width) / imageWidth; - this.vertices[numVertices++] = originY / imageHeight; - this.vertices[numVertices++] = opacity; - this.vertices[numVertices++] = rotateWithView; - - // top-left corner - offsetX = -scale * anchorX; - offsetY = scale * anchorY; - this.vertices[numVertices++] = x; - this.vertices[numVertices++] = y; - this.vertices[numVertices++] = offsetX * cos - offsetY * sin; - this.vertices[numVertices++] = offsetX * sin + offsetY * cos; - this.vertices[numVertices++] = originX / imageWidth; - this.vertices[numVertices++] = originY / imageHeight; - this.vertices[numVertices++] = opacity; - this.vertices[numVertices++] = rotateWithView; - - this.indices[numIndices++] = n; - this.indices[numIndices++] = n + 1; - this.indices[numIndices++] = n + 2; - this.indices[numIndices++] = n; - this.indices[numIndices++] = n + 2; - this.indices[numIndices++] = n + 3; - } - - return numVertices; -}; - - -/** - * @protected - * @param {Array.<WebGLTexture>} textures Textures. - * @param {Array.<HTMLCanvasElement|HTMLImageElement|HTMLVideoElement>} images - * Images. - * @param {Object.<string, WebGLTexture>} texturePerImage Texture cache. - * @param {WebGLRenderingContext} gl Gl. - */ -ol.render.webgl.TextureReplay.prototype.createTextures = function(textures, images, texturePerImage, gl) { - var texture, image, uid, i; - var ii = images.length; - for (i = 0; i < ii; ++i) { - image = images[i]; - - uid = ol.getUid(image).toString(); - if (uid in texturePerImage) { - texture = texturePerImage[uid]; - } else { - texture = ol.webgl.Context.createTexture( - gl, image, ol.webgl.CLAMP_TO_EDGE, ol.webgl.CLAMP_TO_EDGE); - texturePerImage[uid] = texture; - } - textures[i] = texture; - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.TextureReplay.prototype.setUpProgram = function(gl, context, size, pixelRatio) { - // get the program - var fragmentShader = ol.render.webgl.texturereplay.defaultshader.fragment; - var vertexShader = ol.render.webgl.texturereplay.defaultshader.vertex; - var program = context.getProgram(fragmentShader, vertexShader); - - // get the locations - var locations; - if (!this.defaultLocations) { - locations = new ol.render.webgl.texturereplay.defaultshader.Locations(gl, program); - this.defaultLocations = locations; - } else { - locations = this.defaultLocations; - } - - // use the program (FIXME: use the return value) - context.useProgram(program); - - // enable the vertex attrib arrays - gl.enableVertexAttribArray(locations.a_position); - gl.vertexAttribPointer(locations.a_position, 2, ol.webgl.FLOAT, - false, 32, 0); - - gl.enableVertexAttribArray(locations.a_offsets); - gl.vertexAttribPointer(locations.a_offsets, 2, ol.webgl.FLOAT, - false, 32, 8); - - gl.enableVertexAttribArray(locations.a_texCoord); - gl.vertexAttribPointer(locations.a_texCoord, 2, ol.webgl.FLOAT, - false, 32, 16); - - gl.enableVertexAttribArray(locations.a_opacity); - gl.vertexAttribPointer(locations.a_opacity, 1, ol.webgl.FLOAT, - false, 32, 24); - - gl.enableVertexAttribArray(locations.a_rotateWithView); - gl.vertexAttribPointer(locations.a_rotateWithView, 1, ol.webgl.FLOAT, - false, 32, 28); - - return locations; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.TextureReplay.prototype.shutDownProgram = function(gl, locations) { - gl.disableVertexAttribArray(locations.a_position); - gl.disableVertexAttribArray(locations.a_offsets); - gl.disableVertexAttribArray(locations.a_texCoord); - gl.disableVertexAttribArray(locations.a_opacity); - gl.disableVertexAttribArray(locations.a_rotateWithView); -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.TextureReplay.prototype.drawReplay = function(gl, context, skippedFeaturesHash, hitDetection) { - var textures = hitDetection ? this.getHitDetectionTextures() : this.getTextures(); - var groupIndices = hitDetection ? this.hitDetectionGroupIndices : this.groupIndices; - - if (!ol.obj.isEmpty(skippedFeaturesHash)) { - this.drawReplaySkipping( - gl, context, skippedFeaturesHash, textures, groupIndices); - } else { - var i, ii, start; - for (i = 0, ii = textures.length, start = 0; i < ii; ++i) { - gl.bindTexture(ol.webgl.TEXTURE_2D, textures[i]); - var end = groupIndices[i]; - this.drawElements(gl, context, start, end); - start = end; - } - } -}; - - -/** - * Draw the replay while paying attention to skipped features. - * - * This functions creates groups of features that can be drawn to together, - * so that the number of `drawElements` calls is minimized. - * - * For example given the following texture groups: - * - * Group 1: A B C - * Group 2: D [E] F G - * - * If feature E should be skipped, the following `drawElements` calls will be - * made: - * - * drawElements with feature A, B and C - * drawElements with feature D - * drawElements with feature F and G - * - * @protected - * @param {WebGLRenderingContext} gl gl. - * @param {ol.webgl.Context} context Context. - * @param {Object.<string, boolean>} skippedFeaturesHash Ids of features - * to skip. - * @param {Array.<WebGLTexture>} textures Textures. - * @param {Array.<number>} groupIndices Texture group indices. - */ -ol.render.webgl.TextureReplay.prototype.drawReplaySkipping = function(gl, context, skippedFeaturesHash, textures, - groupIndices) { - var featureIndex = 0; - - var i, ii; - for (i = 0, ii = textures.length; i < ii; ++i) { - gl.bindTexture(ol.webgl.TEXTURE_2D, textures[i]); - var groupStart = (i > 0) ? groupIndices[i - 1] : 0; - var groupEnd = groupIndices[i]; - - var start = groupStart; - var end = groupStart; - while (featureIndex < this.startIndices.length && - this.startIndices[featureIndex] <= groupEnd) { - var feature = this.startIndicesFeature[featureIndex]; - - var featureUid = ol.getUid(feature).toString(); - if (skippedFeaturesHash[featureUid] !== undefined) { - // feature should be skipped - if (start !== end) { - // draw the features so far - this.drawElements(gl, context, start, end); - } - // continue with the next feature - start = (featureIndex === this.startIndices.length - 1) ? - groupEnd : this.startIndices[featureIndex + 1]; - end = start; - } else { - // the feature is not skipped, augment the end index - end = (featureIndex === this.startIndices.length - 1) ? - groupEnd : this.startIndices[featureIndex + 1]; - } - featureIndex++; - } - - if (start !== end) { - // draw the remaining features (in case there was no skipped feature - // in this texture group, all features of a group are drawn together) - this.drawElements(gl, context, start, end); - } - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.TextureReplay.prototype.drawHitDetectionReplayOneByOne = function(gl, context, skippedFeaturesHash, - featureCallback, opt_hitExtent) { - var i, groupStart, start, end, feature, featureUid; - var featureIndex = this.startIndices.length - 1; - var hitDetectionTextures = this.getHitDetectionTextures(); - for (i = hitDetectionTextures.length - 1; i >= 0; --i) { - gl.bindTexture(ol.webgl.TEXTURE_2D, hitDetectionTextures[i]); - groupStart = (i > 0) ? this.hitDetectionGroupIndices[i - 1] : 0; - end = this.hitDetectionGroupIndices[i]; - - // draw all features for this texture group - while (featureIndex >= 0 && - this.startIndices[featureIndex] >= groupStart) { - start = this.startIndices[featureIndex]; - feature = this.startIndicesFeature[featureIndex]; - featureUid = ol.getUid(feature).toString(); - - if (skippedFeaturesHash[featureUid] === undefined && - feature.getGeometry() && - (opt_hitExtent === undefined || ol.extent.intersects( - /** @type {Array<number>} */ (opt_hitExtent), - feature.getGeometry().getExtent()))) { - gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT); - this.drawElements(gl, context, start, end); - - var result = featureCallback(feature); - if (result) { - return result; - } - } - - end = start; - featureIndex--; - } - } - return undefined; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.TextureReplay.prototype.finish = function(context) { - this.anchorX = undefined; - this.anchorY = undefined; - this.height = undefined; - this.imageHeight = undefined; - this.imageWidth = undefined; - this.indices = null; - this.opacity = undefined; - this.originX = undefined; - this.originY = undefined; - this.rotateWithView = undefined; - this.rotation = undefined; - this.scale = undefined; - this.vertices = null; - this.width = undefined; -}; - - -/** - * @abstract - * @protected - * @param {boolean=} opt_all Return hit detection textures with regular ones. - * @returns {Array.<WebGLTexture>} Textures. - */ -ol.render.webgl.TextureReplay.prototype.getTextures = function(opt_all) {}; - - -/** - * @abstract - * @protected - * @returns {Array.<WebGLTexture>} Textures. - */ -ol.render.webgl.TextureReplay.prototype.getHitDetectionTextures = function() {}; - -goog.provide('ol.render.webgl.ImageReplay'); - -goog.require('ol'); -goog.require('ol.render.webgl.TextureReplay'); -goog.require('ol.webgl.Buffer'); - - -/** - * @constructor - * @extends {ol.render.webgl.TextureReplay} - * @param {number} tolerance Tolerance. - * @param {ol.Extent} maxExtent Max extent. - * @struct - */ -ol.render.webgl.ImageReplay = function(tolerance, maxExtent) { - ol.render.webgl.TextureReplay.call(this, tolerance, maxExtent); - - /** - * @type {Array.<HTMLCanvasElement|HTMLImageElement|HTMLVideoElement>} - * @protected - */ - this.images_ = []; - - /** - * @type {Array.<HTMLCanvasElement|HTMLImageElement|HTMLVideoElement>} - * @protected - */ - this.hitDetectionImages_ = []; - - /** - * @type {Array.<WebGLTexture>} - * @private - */ - this.textures_ = []; - - /** - * @type {Array.<WebGLTexture>} - * @private - */ - this.hitDetectionTextures_ = []; - -}; -ol.inherits(ol.render.webgl.ImageReplay, ol.render.webgl.TextureReplay); - - -/** - * @inheritDoc - */ -ol.render.webgl.ImageReplay.prototype.drawMultiPoint = function(multiPointGeometry, feature) { - this.startIndices.push(this.indices.length); - this.startIndicesFeature.push(feature); - var flatCoordinates = multiPointGeometry.getFlatCoordinates(); - var stride = multiPointGeometry.getStride(); - this.drawCoordinates( - flatCoordinates, 0, flatCoordinates.length, stride); -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.ImageReplay.prototype.drawPoint = function(pointGeometry, feature) { - this.startIndices.push(this.indices.length); - this.startIndicesFeature.push(feature); - var flatCoordinates = pointGeometry.getFlatCoordinates(); - var stride = pointGeometry.getStride(); - this.drawCoordinates( - flatCoordinates, 0, flatCoordinates.length, stride); -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.ImageReplay.prototype.finish = function(context) { - var gl = context.getGL(); - - this.groupIndices.push(this.indices.length); - this.hitDetectionGroupIndices.push(this.indices.length); - - // create, bind, and populate the vertices buffer - this.verticesBuffer = new ol.webgl.Buffer(this.vertices); - - var indices = this.indices; - - // create, bind, and populate the indices buffer - this.indicesBuffer = new ol.webgl.Buffer(indices); - - // create textures - /** @type {Object.<string, WebGLTexture>} */ - var texturePerImage = {}; - - this.createTextures(this.textures_, this.images_, texturePerImage, gl); - - this.createTextures(this.hitDetectionTextures_, this.hitDetectionImages_, - texturePerImage, gl); - - this.images_ = null; - this.hitDetectionImages_ = null; - ol.render.webgl.TextureReplay.prototype.finish.call(this, context); -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.ImageReplay.prototype.setImageStyle = function(imageStyle) { - var anchor = imageStyle.getAnchor(); - var image = imageStyle.getImage(1); - var imageSize = imageStyle.getImageSize(); - var hitDetectionImage = imageStyle.getHitDetectionImage(1); - var opacity = imageStyle.getOpacity(); - var origin = imageStyle.getOrigin(); - var rotateWithView = imageStyle.getRotateWithView(); - var rotation = imageStyle.getRotation(); - var size = imageStyle.getSize(); - var scale = imageStyle.getScale(); - - var currentImage; - if (this.images_.length === 0) { - this.images_.push(image); - } else { - currentImage = this.images_[this.images_.length - 1]; - if (ol.getUid(currentImage) != ol.getUid(image)) { - this.groupIndices.push(this.indices.length); - this.images_.push(image); - } - } - - if (this.hitDetectionImages_.length === 0) { - this.hitDetectionImages_.push(hitDetectionImage); - } else { - currentImage = - this.hitDetectionImages_[this.hitDetectionImages_.length - 1]; - if (ol.getUid(currentImage) != ol.getUid(hitDetectionImage)) { - this.hitDetectionGroupIndices.push(this.indices.length); - this.hitDetectionImages_.push(hitDetectionImage); - } - } - - this.anchorX = anchor[0]; - this.anchorY = anchor[1]; - this.height = size[1]; - this.imageHeight = imageSize[1]; - this.imageWidth = imageSize[0]; - this.opacity = opacity; - this.originX = origin[0]; - this.originY = origin[1]; - this.rotation = rotation; - this.rotateWithView = rotateWithView; - this.scale = scale; - this.width = size[0]; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.ImageReplay.prototype.getTextures = function(opt_all) { - return opt_all ? this.textures_.concat(this.hitDetectionTextures_) : this.textures_; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.ImageReplay.prototype.getHitDetectionTextures = function() { - return this.hitDetectionTextures_; -}; - -// This file is automatically generated, do not edit -goog.provide('ol.render.webgl.linestringreplay.defaultshader'); - -goog.require('ol'); -goog.require('ol.webgl.Fragment'); -goog.require('ol.webgl.Vertex'); - - -ol.render.webgl.linestringreplay.defaultshader.fragment = new ol.webgl.Fragment(ol.DEBUG_WEBGL ? - 'precision mediump float;\nvarying float v_round;\nvarying vec2 v_roundVertex;\nvarying float v_halfWidth;\n\n\n\nuniform float u_opacity;\nuniform vec4 u_color;\nuniform vec2 u_size;\nuniform float u_pixelRatio;\n\nvoid main(void) {\n if (v_round > 0.0) {\n vec2 windowCoords = vec2((v_roundVertex.x + 1.0) / 2.0 * u_size.x * u_pixelRatio,\n (v_roundVertex.y + 1.0) / 2.0 * u_size.y * u_pixelRatio);\n if (length(windowCoords - gl_FragCoord.xy) > v_halfWidth * u_pixelRatio) {\n discard;\n }\n }\n gl_FragColor = u_color;\n float alpha = u_color.a * u_opacity;\n if (alpha == 0.0) {\n discard;\n }\n gl_FragColor.a = alpha;\n}\n' : - 'precision mediump float;varying float a;varying vec2 aVertex;varying float c;uniform float m;uniform vec4 n;uniform vec2 o;uniform float p;void main(void){if(a>0.0){vec2 windowCoords=vec2((aVertex.x+1.0)/2.0*o.x*p,(aVertex.y+1.0)/2.0*o.y*p);if(length(windowCoords-gl_FragCoord.xy)>c*p){discard;}} gl_FragColor=n;float alpha=n.a*m;if(alpha==0.0){discard;}gl_FragColor.a=alpha;}'); - -ol.render.webgl.linestringreplay.defaultshader.vertex = new ol.webgl.Vertex(ol.DEBUG_WEBGL ? - 'varying float v_round;\nvarying vec2 v_roundVertex;\nvarying float v_halfWidth;\n\n\nattribute vec2 a_lastPos;\nattribute vec2 a_position;\nattribute vec2 a_nextPos;\nattribute float a_direction;\n\nuniform mat4 u_projectionMatrix;\nuniform mat4 u_offsetScaleMatrix;\nuniform mat4 u_offsetRotateMatrix;\nuniform float u_lineWidth;\nuniform float u_miterLimit;\n\nbool nearlyEquals(in float value, in float ref) {\n float epsilon = 0.000000000001;\n return value >= ref - epsilon && value <= ref + epsilon;\n}\n\nvoid alongNormal(out vec2 offset, in vec2 nextP, in float turnDir, in float direction) {\n vec2 dirVect = nextP - a_position;\n vec2 normal = normalize(vec2(-turnDir * dirVect.y, turnDir * dirVect.x));\n offset = u_lineWidth / 2.0 * normal * direction;\n}\n\nvoid miterUp(out vec2 offset, out float round, in bool isRound, in float direction) {\n float halfWidth = u_lineWidth / 2.0;\n vec2 tangent = normalize(normalize(a_nextPos - a_position) + normalize(a_position - a_lastPos));\n vec2 normal = vec2(-tangent.y, tangent.x);\n vec2 dirVect = a_nextPos - a_position;\n vec2 tmpNormal = normalize(vec2(-dirVect.y, dirVect.x));\n float miterLength = abs(halfWidth / dot(normal, tmpNormal));\n offset = normal * direction * miterLength;\n round = 0.0;\n if (isRound) {\n round = 1.0;\n } else if (miterLength > u_miterLimit + u_lineWidth) {\n offset = halfWidth * tmpNormal * direction;\n }\n}\n\nbool miterDown(out vec2 offset, in vec4 projPos, in mat4 offsetMatrix, in float direction) {\n bool degenerate = false;\n vec2 tangent = normalize(normalize(a_nextPos - a_position) + normalize(a_position - a_lastPos));\n vec2 normal = vec2(-tangent.y, tangent.x);\n vec2 dirVect = a_lastPos - a_position;\n vec2 tmpNormal = normalize(vec2(-dirVect.y, dirVect.x));\n vec2 longOffset, shortOffset, longVertex;\n vec4 shortProjVertex;\n float halfWidth = u_lineWidth / 2.0;\n if (length(a_nextPos - a_position) > length(a_lastPos - a_position)) {\n longOffset = tmpNormal * direction * halfWidth;\n shortOffset = normalize(vec2(dirVect.y, -dirVect.x)) * direction * halfWidth;\n longVertex = a_nextPos;\n shortProjVertex = u_projectionMatrix * vec4(a_lastPos, 0.0, 1.0);\n } else {\n shortOffset = tmpNormal * direction * halfWidth;\n longOffset = normalize(vec2(dirVect.y, -dirVect.x)) * direction * halfWidth;\n longVertex = a_lastPos;\n shortProjVertex = u_projectionMatrix * vec4(a_nextPos, 0.0, 1.0);\n }\n //Intersection algorithm based on theory by Paul Bourke (http://paulbourke.net/geometry/pointlineplane/).\n vec4 p1 = u_projectionMatrix * vec4(longVertex, 0.0, 1.0) + offsetMatrix * vec4(longOffset, 0.0, 0.0);\n vec4 p2 = projPos + offsetMatrix * vec4(longOffset, 0.0, 0.0);\n vec4 p3 = shortProjVertex + offsetMatrix * vec4(-shortOffset, 0.0, 0.0);\n vec4 p4 = shortProjVertex + offsetMatrix * vec4(shortOffset, 0.0, 0.0);\n float denom = (p4.y - p3.y) * (p2.x - p1.x) - (p4.x - p3.x) * (p2.y - p1.y);\n float firstU = ((p4.x - p3.x) * (p1.y - p3.y) - (p4.y - p3.y) * (p1.x - p3.x)) / denom;\n float secondU = ((p2.x - p1.x) * (p1.y - p3.y) - (p2.y - p1.y) * (p1.x - p3.x)) / denom;\n float epsilon = 0.000000000001;\n if (firstU > epsilon && firstU < 1.0 - epsilon && secondU > epsilon && secondU < 1.0 - epsilon) {\n shortProjVertex.x = p1.x + firstU * (p2.x - p1.x);\n shortProjVertex.y = p1.y + firstU * (p2.y - p1.y);\n offset = shortProjVertex.xy;\n degenerate = true;\n } else {\n float miterLength = abs(halfWidth / dot(normal, tmpNormal));\n offset = normal * direction * miterLength;\n }\n return degenerate;\n}\n\nvoid squareCap(out vec2 offset, out float round, in bool isRound, in vec2 nextP,\n in float turnDir, in float direction) {\n round = 0.0;\n vec2 dirVect = a_position - nextP;\n vec2 firstNormal = normalize(dirVect);\n vec2 secondNormal = vec2(turnDir * firstNormal.y * direction, -turnDir * firstNormal.x * direction);\n vec2 hypotenuse = normalize(firstNormal - secondNormal);\n vec2 normal = vec2(turnDir * hypotenuse.y * direction, -turnDir * hypotenuse.x * direction);\n float length = sqrt(v_halfWidth * v_halfWidth * 2.0);\n offset = normal * length;\n if (isRound) {\n round = 1.0;\n }\n}\n\nvoid main(void) {\n bool degenerate = false;\n float direction = float(sign(a_direction));\n mat4 offsetMatrix = u_offsetScaleMatrix * u_offsetRotateMatrix;\n vec2 offset;\n vec4 projPos = u_projectionMatrix * vec4(a_position, 0.0, 1.0);\n bool round = nearlyEquals(mod(a_direction, 2.0), 0.0);\n\n v_round = 0.0;\n v_halfWidth = u_lineWidth / 2.0;\n v_roundVertex = projPos.xy;\n\n if (nearlyEquals(mod(a_direction, 3.0), 0.0) || nearlyEquals(mod(a_direction, 17.0), 0.0)) {\n alongNormal(offset, a_nextPos, 1.0, direction);\n } else if (nearlyEquals(mod(a_direction, 5.0), 0.0) || nearlyEquals(mod(a_direction, 13.0), 0.0)) {\n alongNormal(offset, a_lastPos, -1.0, direction);\n } else if (nearlyEquals(mod(a_direction, 23.0), 0.0)) {\n miterUp(offset, v_round, round, direction);\n } else if (nearlyEquals(mod(a_direction, 19.0), 0.0)) {\n degenerate = miterDown(offset, projPos, offsetMatrix, direction);\n } else if (nearlyEquals(mod(a_direction, 7.0), 0.0)) {\n squareCap(offset, v_round, round, a_nextPos, 1.0, direction);\n } else if (nearlyEquals(mod(a_direction, 11.0), 0.0)) {\n squareCap(offset, v_round, round, a_lastPos, -1.0, direction);\n }\n if (!degenerate) {\n vec4 offsets = offsetMatrix * vec4(offset, 0.0, 0.0);\n gl_Position = projPos + offsets;\n } else {\n gl_Position = vec4(offset, 0.0, 1.0);\n }\n}\n\n\n' : - 'varying float a;varying vec2 aVertex;varying float c;attribute vec2 d;attribute vec2 e;attribute vec2 f;attribute float g;uniform mat4 h;uniform mat4 i;uniform mat4 j;uniform float k;uniform float l;bool nearlyEquals(in float value,in float ref){float epsilon=0.000000000001;return value>=ref-epsilon&&value<=ref+epsilon;}void alongNormal(out vec2 offset,in vec2 nextP,in float turnDir,in float direction){vec2 dirVect=nextP-e;vec2 normal=normalize(vec2(-turnDir*dirVect.y,turnDir*dirVect.x));offset=k/2.0*normal*direction;}void miterUp(out vec2 offset,out float round,in bool isRound,in float direction){float halfWidth=k/2.0;vec2 tangent=normalize(normalize(f-e)+normalize(e-d));vec2 normal=vec2(-tangent.y,tangent.x);vec2 dirVect=f-e;vec2 tmpNormal=normalize(vec2(-dirVect.y,dirVect.x));float miterLength=abs(halfWidth/dot(normal,tmpNormal));offset=normal*direction*miterLength;round=0.0;if(isRound){round=1.0;}else if(miterLength>l+k){offset=halfWidth*tmpNormal*direction;}} bool miterDown(out vec2 offset,in vec4 projPos,in mat4 offsetMatrix,in float direction){bool degenerate=false;vec2 tangent=normalize(normalize(f-e)+normalize(e-d));vec2 normal=vec2(-tangent.y,tangent.x);vec2 dirVect=d-e;vec2 tmpNormal=normalize(vec2(-dirVect.y,dirVect.x));vec2 longOffset,shortOffset,longVertex;vec4 shortProjVertex;float halfWidth=k/2.0;if(length(f-e)>length(d-e)){longOffset=tmpNormal*direction*halfWidth;shortOffset=normalize(vec2(dirVect.y,-dirVect.x))*direction*halfWidth;longVertex=f;shortProjVertex=h*vec4(d,0.0,1.0);}else{shortOffset=tmpNormal*direction*halfWidth;longOffset=normalize(vec2(dirVect.y,-dirVect.x))*direction*halfWidth;longVertex=d;shortProjVertex=h*vec4(f,0.0,1.0);}vec4 p1=h*vec4(longVertex,0.0,1.0)+offsetMatrix*vec4(longOffset,0.0,0.0);vec4 p2=projPos+offsetMatrix*vec4(longOffset,0.0,0.0);vec4 p3=shortProjVertex+offsetMatrix*vec4(-shortOffset,0.0,0.0);vec4 p4=shortProjVertex+offsetMatrix*vec4(shortOffset,0.0,0.0);float denom=(p4.y-p3.y)*(p2.x-p1.x)-(p4.x-p3.x)*(p2.y-p1.y);float firstU=((p4.x-p3.x)*(p1.y-p3.y)-(p4.y-p3.y)*(p1.x-p3.x))/denom;float secondU=((p2.x-p1.x)*(p1.y-p3.y)-(p2.y-p1.y)*(p1.x-p3.x))/denom;float epsilon=0.000000000001;if(firstU>epsilon&&firstU<1.0-epsilon&&secondU>epsilon&&secondU<1.0-epsilon){shortProjVertex.x=p1.x+firstU*(p2.x-p1.x);shortProjVertex.y=p1.y+firstU*(p2.y-p1.y);offset=shortProjVertex.xy;degenerate=true;}else{float miterLength=abs(halfWidth/dot(normal,tmpNormal));offset=normal*direction*miterLength;}return degenerate;}void squareCap(out vec2 offset,out float round,in bool isRound,in vec2 nextP,in float turnDir,in float direction){round=0.0;vec2 dirVect=e-nextP;vec2 firstNormal=normalize(dirVect);vec2 secondNormal=vec2(turnDir*firstNormal.y*direction,-turnDir*firstNormal.x*direction);vec2 hypotenuse=normalize(firstNormal-secondNormal);vec2 normal=vec2(turnDir*hypotenuse.y*direction,-turnDir*hypotenuse.x*direction);float length=sqrt(c*c*2.0);offset=normal*length;if(isRound){round=1.0;}} void main(void){bool degenerate=false;float direction=float(sign(g));mat4 offsetMatrix=i*j;vec2 offset;vec4 projPos=h*vec4(e,0.0,1.0);bool round=nearlyEquals(mod(g,2.0),0.0);a=0.0;c=k/2.0;aVertex=projPos.xy;if(nearlyEquals(mod(g,3.0),0.0)||nearlyEquals(mod(g,17.0),0.0)){alongNormal(offset,f,1.0,direction);}else if(nearlyEquals(mod(g,5.0),0.0)||nearlyEquals(mod(g,13.0),0.0)){alongNormal(offset,d,-1.0,direction);}else if(nearlyEquals(mod(g,23.0),0.0)){miterUp(offset,a,round,direction);}else if(nearlyEquals(mod(g,19.0),0.0)){degenerate=miterDown(offset,projPos,offsetMatrix,direction);}else if(nearlyEquals(mod(g,7.0),0.0)){squareCap(offset,a,round,f,1.0,direction);}else if(nearlyEquals(mod(g,11.0),0.0)){squareCap(offset,a,round,d,-1.0,direction);}if(!degenerate){vec4 offsets=offsetMatrix*vec4(offset,0.0,0.0);gl_Position=projPos+offsets;}else{gl_Position=vec4(offset,0.0,1.0);}}'); - -// This file is automatically generated, do not edit -goog.provide('ol.render.webgl.linestringreplay.defaultshader.Locations'); - -goog.require('ol'); - - -/** - * @constructor - * @param {WebGLRenderingContext} gl GL. - * @param {WebGLProgram} program Program. - * @struct - */ -ol.render.webgl.linestringreplay.defaultshader.Locations = function(gl, program) { - - /** - * @type {WebGLUniformLocation} - */ - this.u_projectionMatrix = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_projectionMatrix' : 'h'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_offsetScaleMatrix = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_offsetScaleMatrix' : 'i'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_offsetRotateMatrix = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_offsetRotateMatrix' : 'j'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_lineWidth = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_lineWidth' : 'k'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_miterLimit = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_miterLimit' : 'l'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_opacity = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_opacity' : 'm'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_color = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_color' : 'n'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_size = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_size' : 'o'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_pixelRatio = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_pixelRatio' : 'p'); - - /** - * @type {number} - */ - this.a_lastPos = gl.getAttribLocation( - program, ol.DEBUG_WEBGL ? 'a_lastPos' : 'd'); - - /** - * @type {number} - */ - this.a_position = gl.getAttribLocation( - program, ol.DEBUG_WEBGL ? 'a_position' : 'e'); - - /** - * @type {number} - */ - this.a_nextPos = gl.getAttribLocation( - program, ol.DEBUG_WEBGL ? 'a_nextPos' : 'f'); - - /** - * @type {number} - */ - this.a_direction = gl.getAttribLocation( - program, ol.DEBUG_WEBGL ? 'a_direction' : 'g'); -}; - -goog.provide('ol.render.webgl.LineStringReplay'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.color'); -goog.require('ol.extent'); -goog.require('ol.geom.flat.orient'); -goog.require('ol.geom.flat.transform'); -goog.require('ol.geom.flat.topology'); -goog.require('ol.obj'); -goog.require('ol.render.webgl'); -goog.require('ol.render.webgl.Replay'); -goog.require('ol.render.webgl.linestringreplay.defaultshader'); -goog.require('ol.render.webgl.linestringreplay.defaultshader.Locations'); -goog.require('ol.webgl'); -goog.require('ol.webgl.Buffer'); - - -/** - * @constructor - * @extends {ol.render.webgl.Replay} - * @param {number} tolerance Tolerance. - * @param {ol.Extent} maxExtent Max extent. - * @struct - */ -ol.render.webgl.LineStringReplay = function(tolerance, maxExtent) { - ol.render.webgl.Replay.call(this, tolerance, maxExtent); - - /** - * @private - * @type {ol.render.webgl.linestringreplay.defaultshader.Locations} - */ - this.defaultLocations_ = null; - - /** - * @private - * @type {Array.<Array.<?>>} - */ - this.styles_ = []; - - /** - * @private - * @type {Array.<number>} - */ - this.styleIndices_ = []; - - /** - * @private - * @type {{strokeColor: (Array.<number>|null), - * lineCap: (string|undefined), - * lineDash: Array.<number>, - * lineDashOffset: (number|undefined), - * lineJoin: (string|undefined), - * lineWidth: (number|undefined), - * miterLimit: (number|undefined), - * changed: boolean}|null} - */ - this.state_ = { - strokeColor: null, - lineCap: undefined, - lineDash: null, - lineDashOffset: undefined, - lineJoin: undefined, - lineWidth: undefined, - miterLimit: undefined, - changed: false - }; - -}; -ol.inherits(ol.render.webgl.LineStringReplay, ol.render.webgl.Replay); - - -/** - * Draw one segment. - * @private - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - */ -ol.render.webgl.LineStringReplay.prototype.drawCoordinates_ = function(flatCoordinates, offset, end, stride) { - - var i, ii; - var numVertices = this.vertices.length; - var numIndices = this.indices.length; - //To save a vertex, the direction of a point is a product of the sign (1 or -1), a prime from - //ol.render.webgl.LineStringReplay.Instruction_, and a rounding factor (1 or 2). If the product is even, - //we round it. If it is odd, we don't. - var lineJoin = this.state_.lineJoin === 'bevel' ? 0 : - this.state_.lineJoin === 'miter' ? 1 : 2; - var lineCap = this.state_.lineCap === 'butt' ? 0 : - this.state_.lineCap === 'square' ? 1 : 2; - var closed = ol.geom.flat.topology.lineStringIsClosed(flatCoordinates, offset, end, stride); - var startCoords, sign, n; - var lastIndex = numIndices; - var lastSign = 1; - //We need the adjacent vertices to define normals in joins. p0 = last, p1 = current, p2 = next. - var p0, p1, p2; - - for (i = offset, ii = end; i < ii; i += stride) { - - n = numVertices / 7; - - p0 = p1; - p1 = p2 || [flatCoordinates[i], flatCoordinates[i + 1]]; - //First vertex. - if (i === offset) { - p2 = [flatCoordinates[i + stride], flatCoordinates[i + stride + 1]]; - if (end - offset === stride * 2 && ol.array.equals(p1, p2)) { - break; - } - if (closed) { - //A closed line! Complete the circle. - p0 = [flatCoordinates[end - stride * 2], - flatCoordinates[end - stride * 2 + 1]]; - - startCoords = p2; - } else { - //Add the first two/four vertices. - - if (lineCap) { - numVertices = this.addVertices_([0, 0], p1, p2, - lastSign * ol.render.webgl.LineStringReplay.Instruction_.BEGIN_LINE_CAP * lineCap, numVertices); - - numVertices = this.addVertices_([0, 0], p1, p2, - -lastSign * ol.render.webgl.LineStringReplay.Instruction_.BEGIN_LINE_CAP * lineCap, numVertices); - - this.indices[numIndices++] = n + 2; - this.indices[numIndices++] = n; - this.indices[numIndices++] = n + 1; - - this.indices[numIndices++] = n + 1; - this.indices[numIndices++] = n + 3; - this.indices[numIndices++] = n + 2; - - } - - numVertices = this.addVertices_([0, 0], p1, p2, - lastSign * ol.render.webgl.LineStringReplay.Instruction_.BEGIN_LINE * (lineCap || 1), numVertices); - - numVertices = this.addVertices_([0, 0], p1, p2, - -lastSign * ol.render.webgl.LineStringReplay.Instruction_.BEGIN_LINE * (lineCap || 1), numVertices); - - lastIndex = numVertices / 7 - 1; - - continue; - } - } else if (i === end - stride) { - //Last vertex. - if (closed) { - //Same as the first vertex. - p2 = startCoords; - break; - } else { - p0 = p0 || [0, 0]; - - numVertices = this.addVertices_(p0, p1, [0, 0], - lastSign * ol.render.webgl.LineStringReplay.Instruction_.END_LINE * (lineCap || 1), numVertices); - - numVertices = this.addVertices_(p0, p1, [0, 0], - -lastSign * ol.render.webgl.LineStringReplay.Instruction_.END_LINE * (lineCap || 1), numVertices); - - this.indices[numIndices++] = n; - this.indices[numIndices++] = lastIndex - 1; - this.indices[numIndices++] = lastIndex; - - this.indices[numIndices++] = lastIndex; - this.indices[numIndices++] = n + 1; - this.indices[numIndices++] = n; - - if (lineCap) { - numVertices = this.addVertices_(p0, p1, [0, 0], - lastSign * ol.render.webgl.LineStringReplay.Instruction_.END_LINE_CAP * lineCap, numVertices); - - numVertices = this.addVertices_(p0, p1, [0, 0], - -lastSign * ol.render.webgl.LineStringReplay.Instruction_.END_LINE_CAP * lineCap, numVertices); - - this.indices[numIndices++] = n + 2; - this.indices[numIndices++] = n; - this.indices[numIndices++] = n + 1; - - this.indices[numIndices++] = n + 1; - this.indices[numIndices++] = n + 3; - this.indices[numIndices++] = n + 2; - - } - - break; - } - } else { - p2 = [flatCoordinates[i + stride], flatCoordinates[i + stride + 1]]; - } - - // We group CW and straight lines, thus the not so inituitive CCW checking function. - sign = ol.render.webgl.triangleIsCounterClockwise(p0[0], p0[1], p1[0], p1[1], p2[0], p2[1]) - ? -1 : 1; - - numVertices = this.addVertices_(p0, p1, p2, - sign * ol.render.webgl.LineStringReplay.Instruction_.BEVEL_FIRST * (lineJoin || 1), numVertices); - - numVertices = this.addVertices_(p0, p1, p2, - sign * ol.render.webgl.LineStringReplay.Instruction_.BEVEL_SECOND * (lineJoin || 1), numVertices); - - numVertices = this.addVertices_(p0, p1, p2, - -sign * ol.render.webgl.LineStringReplay.Instruction_.MITER_BOTTOM * (lineJoin || 1), numVertices); - - if (i > offset) { - this.indices[numIndices++] = n; - this.indices[numIndices++] = lastIndex - 1; - this.indices[numIndices++] = lastIndex; - - this.indices[numIndices++] = n + 2; - this.indices[numIndices++] = n; - this.indices[numIndices++] = lastSign * sign > 0 ? lastIndex : lastIndex - 1; - } - - this.indices[numIndices++] = n; - this.indices[numIndices++] = n + 2; - this.indices[numIndices++] = n + 1; - - lastIndex = n + 2; - lastSign = sign; - - //Add miter - if (lineJoin) { - numVertices = this.addVertices_(p0, p1, p2, - sign * ol.render.webgl.LineStringReplay.Instruction_.MITER_TOP * lineJoin, numVertices); - - this.indices[numIndices++] = n + 1; - this.indices[numIndices++] = n + 3; - this.indices[numIndices++] = n; - } - } - - if (closed) { - n = n || numVertices / 7; - sign = ol.geom.flat.orient.linearRingIsClockwise([p0[0], p0[1], p1[0], p1[1], p2[0], p2[1]], 0, 6, 2) - ? 1 : -1; - - numVertices = this.addVertices_(p0, p1, p2, - sign * ol.render.webgl.LineStringReplay.Instruction_.BEVEL_FIRST * (lineJoin || 1), numVertices); - - numVertices = this.addVertices_(p0, p1, p2, - -sign * ol.render.webgl.LineStringReplay.Instruction_.MITER_BOTTOM * (lineJoin || 1), numVertices); - - this.indices[numIndices++] = n; - this.indices[numIndices++] = lastIndex - 1; - this.indices[numIndices++] = lastIndex; - - this.indices[numIndices++] = n + 1; - this.indices[numIndices++] = n; - this.indices[numIndices++] = lastSign * sign > 0 ? lastIndex : lastIndex - 1; - } -}; - -/** - * @param {Array.<number>} p0 Last coordinates. - * @param {Array.<number>} p1 Current coordinates. - * @param {Array.<number>} p2 Next coordinates. - * @param {number} product Sign, instruction, and rounding product. - * @param {number} numVertices Vertex counter. - * @return {number} Vertex counter. - * @private - */ -ol.render.webgl.LineStringReplay.prototype.addVertices_ = function(p0, p1, p2, product, numVertices) { - this.vertices[numVertices++] = p0[0]; - this.vertices[numVertices++] = p0[1]; - this.vertices[numVertices++] = p1[0]; - this.vertices[numVertices++] = p1[1]; - this.vertices[numVertices++] = p2[0]; - this.vertices[numVertices++] = p2[1]; - this.vertices[numVertices++] = product; - - return numVertices; -}; - -/** - * Check if the linestring can be drawn (i. e. valid). - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - * @return {boolean} The linestring can be drawn. - * @private - */ -ol.render.webgl.LineStringReplay.prototype.isValid_ = function(flatCoordinates, offset, end, stride) { - var range = end - offset; - if (range < stride * 2) { - return false; - } else if (range === stride * 2) { - var firstP = [flatCoordinates[offset], flatCoordinates[offset + 1]]; - var lastP = [flatCoordinates[offset + stride], flatCoordinates[offset + stride + 1]]; - return !ol.array.equals(firstP, lastP); - } - - return true; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.LineStringReplay.prototype.drawLineString = function(lineStringGeometry, feature) { - var flatCoordinates = lineStringGeometry.getFlatCoordinates(); - var stride = lineStringGeometry.getStride(); - if (this.isValid_(flatCoordinates, 0, flatCoordinates.length, stride)) { - flatCoordinates = ol.geom.flat.transform.translate(flatCoordinates, 0, flatCoordinates.length, - stride, -this.origin[0], -this.origin[1]); - if (this.state_.changed) { - this.styleIndices_.push(this.indices.length); - this.state_.changed = false; - } - this.startIndices.push(this.indices.length); - this.startIndicesFeature.push(feature); - this.drawCoordinates_( - flatCoordinates, 0, flatCoordinates.length, stride); - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.LineStringReplay.prototype.drawMultiLineString = function(multiLineStringGeometry, feature) { - var indexCount = this.indices.length; - var ends = multiLineStringGeometry.getEnds(); - ends.unshift(0); - var flatCoordinates = multiLineStringGeometry.getFlatCoordinates(); - var stride = multiLineStringGeometry.getStride(); - var i, ii; - if (ends.length > 1) { - for (i = 1, ii = ends.length; i < ii; ++i) { - if (this.isValid_(flatCoordinates, ends[i - 1], ends[i], stride)) { - var lineString = ol.geom.flat.transform.translate(flatCoordinates, ends[i - 1], ends[i], - stride, -this.origin[0], -this.origin[1]); - this.drawCoordinates_( - lineString, 0, lineString.length, stride); - } - } - } - if (this.indices.length > indexCount) { - this.startIndices.push(indexCount); - this.startIndicesFeature.push(feature); - if (this.state_.changed) { - this.styleIndices_.push(indexCount); - this.state_.changed = false; - } - } -}; - - -/** - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {Array.<Array.<number>>} holeFlatCoordinates Hole flat coordinates. - * @param {number} stride Stride. - */ -ol.render.webgl.LineStringReplay.prototype.drawPolygonCoordinates = function( - flatCoordinates, holeFlatCoordinates, stride) { - if (!ol.geom.flat.topology.lineStringIsClosed(flatCoordinates, 0, - flatCoordinates.length, stride)) { - flatCoordinates.push(flatCoordinates[0]); - flatCoordinates.push(flatCoordinates[1]); - } - this.drawCoordinates_(flatCoordinates, 0, flatCoordinates.length, stride); - if (holeFlatCoordinates.length) { - var i, ii; - for (i = 0, ii = holeFlatCoordinates.length; i < ii; ++i) { - if (!ol.geom.flat.topology.lineStringIsClosed(holeFlatCoordinates[i], 0, - holeFlatCoordinates[i].length, stride)) { - holeFlatCoordinates[i].push(holeFlatCoordinates[i][0]); - holeFlatCoordinates[i].push(holeFlatCoordinates[i][1]); - } - this.drawCoordinates_(holeFlatCoordinates[i], 0, - holeFlatCoordinates[i].length, stride); - } - } -}; - - -/** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @param {number=} opt_index Index count. - */ -ol.render.webgl.LineStringReplay.prototype.setPolygonStyle = function(feature, opt_index) { - var index = opt_index === undefined ? this.indices.length : opt_index; - this.startIndices.push(index); - this.startIndicesFeature.push(feature); - if (this.state_.changed) { - this.styleIndices_.push(index); - this.state_.changed = false; - } -}; - - -/** - * @return {number} Current index. - */ -ol.render.webgl.LineStringReplay.prototype.getCurrentIndex = function() { - return this.indices.length; -}; - - -/** - * @inheritDoc - **/ -ol.render.webgl.LineStringReplay.prototype.finish = function(context) { - // create, bind, and populate the vertices buffer - this.verticesBuffer = new ol.webgl.Buffer(this.vertices); - - // create, bind, and populate the indices buffer - this.indicesBuffer = new ol.webgl.Buffer(this.indices); - - this.startIndices.push(this.indices.length); - - //Clean up, if there is nothing to draw - if (this.styleIndices_.length === 0 && this.styles_.length > 0) { - this.styles_ = []; - } - - this.vertices = null; - this.indices = null; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.LineStringReplay.prototype.getDeleteResourcesFunction = function(context) { - var verticesBuffer = this.verticesBuffer; - var indicesBuffer = this.indicesBuffer; - return function() { - context.deleteBuffer(verticesBuffer); - context.deleteBuffer(indicesBuffer); - }; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.LineStringReplay.prototype.setUpProgram = function(gl, context, size, pixelRatio) { - // get the program - var fragmentShader, vertexShader; - fragmentShader = ol.render.webgl.linestringreplay.defaultshader.fragment; - vertexShader = ol.render.webgl.linestringreplay.defaultshader.vertex; - var program = context.getProgram(fragmentShader, vertexShader); - - // get the locations - var locations; - if (!this.defaultLocations_) { - locations = new ol.render.webgl.linestringreplay.defaultshader.Locations(gl, program); - this.defaultLocations_ = locations; - } else { - locations = this.defaultLocations_; - } - - context.useProgram(program); - - // enable the vertex attrib arrays - gl.enableVertexAttribArray(locations.a_lastPos); - gl.vertexAttribPointer(locations.a_lastPos, 2, ol.webgl.FLOAT, - false, 28, 0); - - gl.enableVertexAttribArray(locations.a_position); - gl.vertexAttribPointer(locations.a_position, 2, ol.webgl.FLOAT, - false, 28, 8); - - gl.enableVertexAttribArray(locations.a_nextPos); - gl.vertexAttribPointer(locations.a_nextPos, 2, ol.webgl.FLOAT, - false, 28, 16); - - gl.enableVertexAttribArray(locations.a_direction); - gl.vertexAttribPointer(locations.a_direction, 1, ol.webgl.FLOAT, - false, 28, 24); - - // Enable renderer specific uniforms. - gl.uniform2fv(locations.u_size, size); - gl.uniform1f(locations.u_pixelRatio, pixelRatio); - - return locations; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.LineStringReplay.prototype.shutDownProgram = function(gl, locations) { - gl.disableVertexAttribArray(locations.a_lastPos); - gl.disableVertexAttribArray(locations.a_position); - gl.disableVertexAttribArray(locations.a_nextPos); - gl.disableVertexAttribArray(locations.a_direction); -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.LineStringReplay.prototype.drawReplay = function(gl, context, skippedFeaturesHash, hitDetection) { - //Save GL parameters. - var tmpDepthFunc = /** @type {number} */ (gl.getParameter(gl.DEPTH_FUNC)); - var tmpDepthMask = /** @type {boolean} */ (gl.getParameter(gl.DEPTH_WRITEMASK)); - - if (!hitDetection) { - gl.enable(gl.DEPTH_TEST); - gl.depthMask(true); - gl.depthFunc(gl.NOTEQUAL); - } - - if (!ol.obj.isEmpty(skippedFeaturesHash)) { - this.drawReplaySkipping_(gl, context, skippedFeaturesHash); - } else { - //Draw by style groups to minimize drawElements() calls. - var i, start, end, nextStyle; - end = this.startIndices[this.startIndices.length - 1]; - for (i = this.styleIndices_.length - 1; i >= 0; --i) { - start = this.styleIndices_[i]; - nextStyle = this.styles_[i]; - this.setStrokeStyle_(gl, nextStyle[0], nextStyle[1], nextStyle[2]); - this.drawElements(gl, context, start, end); - gl.clear(gl.DEPTH_BUFFER_BIT); - end = start; - } - } - if (!hitDetection) { - gl.disable(gl.DEPTH_TEST); - gl.clear(gl.DEPTH_BUFFER_BIT); - //Restore GL parameters. - gl.depthMask(tmpDepthMask); - gl.depthFunc(tmpDepthFunc); - } -}; - - -/** - * @private - * @param {WebGLRenderingContext} gl gl. - * @param {ol.webgl.Context} context Context. - * @param {Object} skippedFeaturesHash Ids of features to skip. - */ -ol.render.webgl.LineStringReplay.prototype.drawReplaySkipping_ = function(gl, context, skippedFeaturesHash) { - var i, start, end, nextStyle, groupStart, feature, featureUid, featureIndex, featureStart; - featureIndex = this.startIndices.length - 2; - end = start = this.startIndices[featureIndex + 1]; - for (i = this.styleIndices_.length - 1; i >= 0; --i) { - nextStyle = this.styles_[i]; - this.setStrokeStyle_(gl, nextStyle[0], nextStyle[1], nextStyle[2]); - groupStart = this.styleIndices_[i]; - - while (featureIndex >= 0 && - this.startIndices[featureIndex] >= groupStart) { - featureStart = this.startIndices[featureIndex]; - feature = this.startIndicesFeature[featureIndex]; - featureUid = ol.getUid(feature).toString(); - - if (skippedFeaturesHash[featureUid]) { - if (start !== end) { - this.drawElements(gl, context, start, end); - gl.clear(gl.DEPTH_BUFFER_BIT); - } - end = featureStart; - } - featureIndex--; - start = featureStart; - } - if (start !== end) { - this.drawElements(gl, context, start, end); - gl.clear(gl.DEPTH_BUFFER_BIT); - } - start = end = groupStart; - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.LineStringReplay.prototype.drawHitDetectionReplayOneByOne = function(gl, context, skippedFeaturesHash, - featureCallback, opt_hitExtent) { - var i, start, end, nextStyle, groupStart, feature, featureUid, featureIndex; - featureIndex = this.startIndices.length - 2; - end = this.startIndices[featureIndex + 1]; - for (i = this.styleIndices_.length - 1; i >= 0; --i) { - nextStyle = this.styles_[i]; - this.setStrokeStyle_(gl, nextStyle[0], nextStyle[1], nextStyle[2]); - groupStart = this.styleIndices_[i]; - - while (featureIndex >= 0 && - this.startIndices[featureIndex] >= groupStart) { - start = this.startIndices[featureIndex]; - feature = this.startIndicesFeature[featureIndex]; - featureUid = ol.getUid(feature).toString(); - - if (skippedFeaturesHash[featureUid] === undefined && - feature.getGeometry() && - (opt_hitExtent === undefined || ol.extent.intersects( - /** @type {Array<number>} */ (opt_hitExtent), - feature.getGeometry().getExtent()))) { - gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT); - this.drawElements(gl, context, start, end); - - var result = featureCallback(feature); - - if (result) { - return result; - } - - } - featureIndex--; - end = start; - } - } - return undefined; -}; - - -/** - * @private - * @param {WebGLRenderingContext} gl gl. - * @param {Array.<number>} color Color. - * @param {number} lineWidth Line width. - * @param {number} miterLimit Miter limit. - */ -ol.render.webgl.LineStringReplay.prototype.setStrokeStyle_ = function(gl, color, lineWidth, miterLimit) { - gl.uniform4fv(this.defaultLocations_.u_color, color); - gl.uniform1f(this.defaultLocations_.u_lineWidth, lineWidth); - gl.uniform1f(this.defaultLocations_.u_miterLimit, miterLimit); -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.LineStringReplay.prototype.setFillStrokeStyle = function(fillStyle, strokeStyle) { - var strokeStyleLineCap = strokeStyle.getLineCap(); - this.state_.lineCap = strokeStyleLineCap !== undefined ? - strokeStyleLineCap : ol.render.webgl.defaultLineCap; - var strokeStyleLineDash = strokeStyle.getLineDash(); - this.state_.lineDash = strokeStyleLineDash ? - strokeStyleLineDash : ol.render.webgl.defaultLineDash; - var strokeStyleLineDashOffset = strokeStyle.getLineDashOffset(); - this.state_.lineDashOffset = strokeStyleLineDashOffset ? - strokeStyleLineDashOffset : ol.render.webgl.defaultLineDashOffset; - var strokeStyleLineJoin = strokeStyle.getLineJoin(); - this.state_.lineJoin = strokeStyleLineJoin !== undefined ? - strokeStyleLineJoin : ol.render.webgl.defaultLineJoin; - var strokeStyleColor = strokeStyle.getColor(); - if (!(strokeStyleColor instanceof CanvasGradient) && - !(strokeStyleColor instanceof CanvasPattern)) { - strokeStyleColor = ol.color.asArray(strokeStyleColor).map(function(c, i) { - return i != 3 ? c / 255 : c; - }) || ol.render.webgl.defaultStrokeStyle; - } else { - strokeStyleColor = ol.render.webgl.defaultStrokeStyle; - } - var strokeStyleWidth = strokeStyle.getWidth(); - strokeStyleWidth = strokeStyleWidth !== undefined ? - strokeStyleWidth : ol.render.webgl.defaultLineWidth; - var strokeStyleMiterLimit = strokeStyle.getMiterLimit(); - strokeStyleMiterLimit = strokeStyleMiterLimit !== undefined ? - strokeStyleMiterLimit : ol.render.webgl.defaultMiterLimit; - if (!this.state_.strokeColor || !ol.array.equals(this.state_.strokeColor, strokeStyleColor) || - this.state_.lineWidth !== strokeStyleWidth || this.state_.miterLimit !== strokeStyleMiterLimit) { - this.state_.changed = true; - this.state_.strokeColor = strokeStyleColor; - this.state_.lineWidth = strokeStyleWidth; - this.state_.miterLimit = strokeStyleMiterLimit; - this.styles_.push([strokeStyleColor, strokeStyleWidth, strokeStyleMiterLimit]); - } -}; - -/** - * @enum {number} - * @private - */ -ol.render.webgl.LineStringReplay.Instruction_ = { - ROUND: 2, - BEGIN_LINE: 3, - END_LINE: 5, - BEGIN_LINE_CAP: 7, - END_LINE_CAP: 11, - BEVEL_FIRST: 13, - BEVEL_SECOND: 17, - MITER_BOTTOM: 19, - MITER_TOP: 23 -}; - -// This file is automatically generated, do not edit -goog.provide('ol.render.webgl.polygonreplay.defaultshader'); - -goog.require('ol'); -goog.require('ol.webgl.Fragment'); -goog.require('ol.webgl.Vertex'); - - -ol.render.webgl.polygonreplay.defaultshader.fragment = new ol.webgl.Fragment(ol.DEBUG_WEBGL ? - 'precision mediump float;\n\n\n\nuniform vec4 u_color;\nuniform float u_opacity;\n\nvoid main(void) {\n gl_FragColor = u_color;\n float alpha = u_color.a * u_opacity;\n if (alpha == 0.0) {\n discard;\n }\n gl_FragColor.a = alpha;\n}\n' : - 'precision mediump float;uniform vec4 e;uniform float f;void main(void){gl_FragColor=e;float alpha=e.a*f;if(alpha==0.0){discard;}gl_FragColor.a=alpha;}'); - -ol.render.webgl.polygonreplay.defaultshader.vertex = new ol.webgl.Vertex(ol.DEBUG_WEBGL ? - '\n\nattribute vec2 a_position;\n\nuniform mat4 u_projectionMatrix;\nuniform mat4 u_offsetScaleMatrix;\nuniform mat4 u_offsetRotateMatrix;\n\nvoid main(void) {\n gl_Position = u_projectionMatrix * vec4(a_position, 0.0, 1.0);\n}\n\n\n' : - 'attribute vec2 a;uniform mat4 b;uniform mat4 c;uniform mat4 d;void main(void){gl_Position=b*vec4(a,0.0,1.0);}'); - -// This file is automatically generated, do not edit -goog.provide('ol.render.webgl.polygonreplay.defaultshader.Locations'); - -goog.require('ol'); - - -/** - * @constructor - * @param {WebGLRenderingContext} gl GL. - * @param {WebGLProgram} program Program. - * @struct - */ -ol.render.webgl.polygonreplay.defaultshader.Locations = function(gl, program) { - - /** - * @type {WebGLUniformLocation} - */ - this.u_projectionMatrix = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_projectionMatrix' : 'b'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_offsetScaleMatrix = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_offsetScaleMatrix' : 'c'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_offsetRotateMatrix = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_offsetRotateMatrix' : 'd'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_color = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_color' : 'e'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_opacity = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_opacity' : 'f'); - - /** - * @type {number} - */ - this.a_position = gl.getAttribLocation( - program, ol.DEBUG_WEBGL ? 'a_position' : 'a'); -}; - -goog.provide('ol.structs.LinkedList'); - -/** - * Creates an empty linked list structure. - * - * @constructor - * @struct - * @param {boolean=} opt_circular The last item is connected to the first one, - * and the first item to the last one. Default is true. - */ -ol.structs.LinkedList = function(opt_circular) { - - /** - * @private - * @type {ol.LinkedListItem|undefined} - */ - this.first_ = undefined; - - /** - * @private - * @type {ol.LinkedListItem|undefined} - */ - this.last_ = undefined; - - /** - * @private - * @type {ol.LinkedListItem|undefined} - */ - this.head_ = undefined; - - /** - * @private - * @type {boolean} - */ - this.circular_ = opt_circular === undefined ? true : opt_circular; - - /** - * @private - * @type {number} - */ - this.length_ = 0; -}; - -/** - * Inserts an item into the linked list right after the current one. - * - * @param {?} data Item data. - */ -ol.structs.LinkedList.prototype.insertItem = function(data) { - - /** @type {ol.LinkedListItem} */ - var item = { - prev: undefined, - next: undefined, - data: data - }; - - var head = this.head_; - - //Initialize the list. - if (!head) { - this.first_ = item; - this.last_ = item; - if (this.circular_) { - item.next = item; - item.prev = item; - } - } else { - //Link the new item to the adjacent ones. - var next = head.next; - item.prev = head; - item.next = next; - head.next = item; - if (next) { - next.prev = item; - } - - if (head === this.last_) { - this.last_ = item; - } - } - this.head_ = item; - this.length_++; -}; - -/** - * Removes the current item from the list. Sets the cursor to the next item, - * if possible. - */ -ol.structs.LinkedList.prototype.removeItem = function() { - var head = this.head_; - if (head) { - var next = head.next; - var prev = head.prev; - if (next) { - next.prev = prev; - } - if (prev) { - prev.next = next; - } - this.head_ = next || prev; - - if (this.first_ === this.last_) { - this.head_ = undefined; - this.first_ = undefined; - this.last_ = undefined; - } else if (this.first_ === head) { - this.first_ = this.head_; - } else if (this.last_ === head) { - this.last_ = prev ? this.head_.prev : this.head_; - } - this.length_--; - } -}; - -/** - * Sets the cursor to the first item, and returns the associated data. - * - * @return {?} Item data. - */ -ol.structs.LinkedList.prototype.firstItem = function() { - this.head_ = this.first_; - if (this.head_) { - return this.head_.data; - } - return undefined; -}; - -/** -* Sets the cursor to the last item, and returns the associated data. -* -* @return {?} Item data. -*/ -ol.structs.LinkedList.prototype.lastItem = function() { - this.head_ = this.last_; - if (this.head_) { - return this.head_.data; - } - return undefined; -}; - -/** - * Sets the cursor to the next item, and returns the associated data. - * - * @return {?} Item data. - */ -ol.structs.LinkedList.prototype.nextItem = function() { - if (this.head_ && this.head_.next) { - this.head_ = this.head_.next; - return this.head_.data; - } - return undefined; -}; - -/** - * Returns the next item's data without moving the cursor. - * - * @return {?} Item data. - */ -ol.structs.LinkedList.prototype.getNextItem = function() { - if (this.head_ && this.head_.next) { - return this.head_.next.data; - } - return undefined; -}; - -/** - * Sets the cursor to the previous item, and returns the associated data. - * - * @return {?} Item data. - */ -ol.structs.LinkedList.prototype.prevItem = function() { - if (this.head_ && this.head_.prev) { - this.head_ = this.head_.prev; - return this.head_.data; - } - return undefined; -}; - -/** - * Returns the previous item's data without moving the cursor. - * - * @return {?} Item data. - */ -ol.structs.LinkedList.prototype.getPrevItem = function() { - if (this.head_ && this.head_.prev) { - return this.head_.prev.data; - } - return undefined; -}; - -/** - * Returns the current item's data. - * - * @return {?} Item data. - */ -ol.structs.LinkedList.prototype.getCurrItem = function() { - if (this.head_) { - return this.head_.data; - } - return undefined; -}; - -/** - * Sets the first item of the list. This only works for circular lists, and sets - * the last item accordingly. - */ -ol.structs.LinkedList.prototype.setFirstItem = function() { - if (this.circular_ && this.head_) { - this.first_ = this.head_; - this.last_ = this.head_.prev; - } -}; - -/** - * Concatenates two lists. - * @param {ol.structs.LinkedList} list List to merge into the current list. - */ -ol.structs.LinkedList.prototype.concat = function(list) { - if (list.head_) { - if (this.head_) { - var end = this.head_.next; - this.head_.next = list.first_; - list.first_.prev = this.head_; - end.prev = list.last_; - list.last_.next = end; - this.length_ += list.length_; - } else { - this.head_ = list.head_; - this.first_ = list.first_; - this.last_ = list.last_; - this.length_ = list.length_; - } - list.head_ = undefined; - list.first_ = undefined; - list.last_ = undefined; - list.length_ = 0; - } -}; - -/** - * Returns the current length of the list. - * - * @return {number} Length. - */ -ol.structs.LinkedList.prototype.getLength = function() { - return this.length_; -}; - -goog.provide('ol.render.webgl.PolygonReplay'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.color'); -goog.require('ol.extent'); -goog.require('ol.obj'); -goog.require('ol.geom.flat.contains'); -goog.require('ol.geom.flat.orient'); -goog.require('ol.geom.flat.transform'); -goog.require('ol.render.webgl.polygonreplay.defaultshader'); -goog.require('ol.render.webgl.polygonreplay.defaultshader.Locations'); -goog.require('ol.render.webgl.LineStringReplay'); -goog.require('ol.render.webgl.Replay'); -goog.require('ol.render.webgl'); -goog.require('ol.style.Stroke'); -goog.require('ol.structs.LinkedList'); -goog.require('ol.structs.RBush'); -goog.require('ol.webgl'); -goog.require('ol.webgl.Buffer'); - - -/** - * @constructor - * @extends {ol.render.webgl.Replay} - * @param {number} tolerance Tolerance. - * @param {ol.Extent} maxExtent Max extent. - * @struct - */ -ol.render.webgl.PolygonReplay = function(tolerance, maxExtent) { - ol.render.webgl.Replay.call(this, tolerance, maxExtent); - - this.lineStringReplay = new ol.render.webgl.LineStringReplay( - tolerance, maxExtent); - - /** - * @private - * @type {ol.render.webgl.polygonreplay.defaultshader.Locations} - */ - this.defaultLocations_ = null; - - /** - * @private - * @type {Array.<Array.<number>>} - */ - this.styles_ = []; - - /** - * @private - * @type {Array.<number>} - */ - this.styleIndices_ = []; - - /** - * @private - * @type {{fillColor: (Array.<number>|null), - * changed: boolean}|null} - */ - this.state_ = { - fillColor: null, - changed: false - }; - -}; -ol.inherits(ol.render.webgl.PolygonReplay, ol.render.webgl.Replay); - - -/** - * Draw one polygon. - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {Array.<Array.<number>>} holeFlatCoordinates Hole flat coordinates. - * @param {number} stride Stride. - * @private - */ -ol.render.webgl.PolygonReplay.prototype.drawCoordinates_ = function( - flatCoordinates, holeFlatCoordinates, stride) { - // Triangulate the polygon - var outerRing = new ol.structs.LinkedList(); - var rtree = new ol.structs.RBush(); - // Initialize the outer ring - this.processFlatCoordinates_(flatCoordinates, stride, outerRing, rtree, true); - var maxCoords = this.getMaxCoords_(outerRing); - - // Eliminate holes, if there are any - if (holeFlatCoordinates.length) { - var i, ii; - var holeLists = []; - for (i = 0, ii = holeFlatCoordinates.length; i < ii; ++i) { - var holeList = { - list: new ol.structs.LinkedList(), - maxCoords: undefined, - rtree: new ol.structs.RBush() - }; - holeLists.push(holeList); - this.processFlatCoordinates_(holeFlatCoordinates[i], - stride, holeList.list, holeList.rtree, false); - this.classifyPoints_(holeList.list, holeList.rtree, true); - holeList.maxCoords = this.getMaxCoords_(holeList.list); - } - holeLists.sort(function(a, b) { - return b.maxCoords[0] === a.maxCoords[0] ? - a.maxCoords[1] - b.maxCoords[1] : b.maxCoords[0] - a.maxCoords[0]; - }); - for (i = 0; i < holeLists.length; ++i) { - var currList = holeLists[i].list; - var start = currList.firstItem(); - var currItem = start; - var intersection; - do { - //TODO: Triangulate holes when they intersect the outer ring. - if (this.getIntersections_(currItem, rtree).length) { - intersection = true; - break; - } - currItem = currList.nextItem(); - } while (start !== currItem); - if (!intersection) { - if (this.bridgeHole_(currList, holeLists[i].maxCoords[0], outerRing, maxCoords[0], rtree)) { - rtree.concat(holeLists[i].rtree); - this.classifyPoints_(outerRing, rtree, false); - } - } - } - } else { - this.classifyPoints_(outerRing, rtree, false); - } - this.triangulate_(outerRing, rtree); -}; - - -/** - * Inserts flat coordinates in a linked list and adds them to the vertex buffer. - * @private - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} stride Stride. - * @param {ol.structs.LinkedList} list Linked list. - * @param {ol.structs.RBush} rtree R-Tree of the polygon. - * @param {boolean} clockwise Coordinate order should be clockwise. - */ -ol.render.webgl.PolygonReplay.prototype.processFlatCoordinates_ = function( - flatCoordinates, stride, list, rtree, clockwise) { - var isClockwise = ol.geom.flat.orient.linearRingIsClockwise(flatCoordinates, - 0, flatCoordinates.length, stride); - var i, ii; - var n = this.vertices.length / 2; - /** @type {ol.WebglPolygonVertex} */ - var start; - /** @type {ol.WebglPolygonVertex} */ - var p0; - /** @type {ol.WebglPolygonVertex} */ - var p1; - var extents = []; - var segments = []; - if (clockwise === isClockwise) { - start = this.createPoint_(flatCoordinates[0], flatCoordinates[1], n++); - p0 = start; - for (i = stride, ii = flatCoordinates.length; i < ii; i += stride) { - p1 = this.createPoint_(flatCoordinates[i], flatCoordinates[i + 1], n++); - segments.push(this.insertItem_(p0, p1, list)); - extents.push([Math.min(p0.x, p1.x), Math.min(p0.y, p1.y), Math.max(p0.x, p1.x), - Math.max(p0.y, p1.y)]); - p0 = p1; - } - segments.push(this.insertItem_(p1, start, list)); - extents.push([Math.min(p0.x, p1.x), Math.min(p0.y, p1.y), Math.max(p0.x, p1.x), - Math.max(p0.y, p1.y)]); - } else { - var end = flatCoordinates.length - stride; - start = this.createPoint_(flatCoordinates[end], flatCoordinates[end + 1], n++); - p0 = start; - for (i = end - stride, ii = 0; i >= ii; i -= stride) { - p1 = this.createPoint_(flatCoordinates[i], flatCoordinates[i + 1], n++); - segments.push(this.insertItem_(p0, p1, list)); - extents.push([Math.min(p0.x, p1.x), Math.min(p0.y, p1.y), Math.max(p0.x, p1.x), - Math.max(p0.y, p1.y)]); - p0 = p1; - } - segments.push(this.insertItem_(p1, start, list)); - extents.push([Math.min(p0.x, p1.x), Math.min(p0.y, p1.y), Math.max(p0.x, p1.x), - Math.max(p0.y, p1.y)]); - } - rtree.load(extents, segments); -}; - - -/** - * Returns the rightmost coordinates of a polygon on the X axis. - * @private - * @param {ol.structs.LinkedList} list Polygons ring. - * @return {Array.<number>} Max X coordinates. - */ -ol.render.webgl.PolygonReplay.prototype.getMaxCoords_ = function(list) { - var start = list.firstItem(); - var seg = start; - var maxCoords = [seg.p0.x, seg.p0.y]; - - do { - seg = list.nextItem(); - if (seg.p0.x > maxCoords[0]) { - maxCoords = [seg.p0.x, seg.p0.y]; - } - } while (seg !== start); - - return maxCoords; -}; - - -/** - * Classifies the points of a polygon list as convex, reflex. Removes collinear vertices. - * @private - * @param {ol.structs.LinkedList} list Polygon ring. - * @param {ol.structs.RBush} rtree R-Tree of the polygon. - * @param {boolean} ccw The orientation of the polygon is counter-clockwise. - * @return {boolean} There were reclassified points. - */ -ol.render.webgl.PolygonReplay.prototype.classifyPoints_ = function(list, rtree, ccw) { - var start = list.firstItem(); - var s0 = start; - var s1 = list.nextItem(); - var pointsReclassified = false; - do { - var reflex = ccw ? ol.render.webgl.triangleIsCounterClockwise(s1.p1.x, - s1.p1.y, s0.p1.x, s0.p1.y, s0.p0.x, s0.p0.y) : - ol.render.webgl.triangleIsCounterClockwise(s0.p0.x, s0.p0.y, s0.p1.x, - s0.p1.y, s1.p1.x, s1.p1.y); - if (reflex === undefined) { - this.removeItem_(s0, s1, list, rtree); - pointsReclassified = true; - if (s1 === start) { - start = list.getNextItem(); - } - s1 = s0; - list.prevItem(); - } else if (s0.p1.reflex !== reflex) { - s0.p1.reflex = reflex; - pointsReclassified = true; - } - s0 = s1; - s1 = list.nextItem(); - } while (s0 !== start); - return pointsReclassified; -}; - - -/** - * @private - * @param {ol.structs.LinkedList} hole Linked list of the hole. - * @param {number} holeMaxX Maximum X value of the hole. - * @param {ol.structs.LinkedList} list Linked list of the polygon. - * @param {number} listMaxX Maximum X value of the polygon. - * @param {ol.structs.RBush} rtree R-Tree of the polygon. - * @return {boolean} Bridging was successful. - */ -ol.render.webgl.PolygonReplay.prototype.bridgeHole_ = function(hole, holeMaxX, - list, listMaxX, rtree) { - var seg = hole.firstItem(); - while (seg.p1.x !== holeMaxX) { - seg = hole.nextItem(); - } - - var p1 = seg.p1; - /** @type {ol.WebglPolygonVertex} */ - var p2 = {x: listMaxX, y: p1.y, i: -1}; - var minDist = Infinity; - var i, ii, bestPoint; - /** @type {ol.WebglPolygonVertex} */ - var p5; - - var intersectingSegments = this.getIntersections_({p0: p1, p1: p2}, rtree, true); - for (i = 0, ii = intersectingSegments.length; i < ii; ++i) { - var currSeg = intersectingSegments[i]; - var intersection = this.calculateIntersection_(p1, p2, currSeg.p0, - currSeg.p1, true); - var dist = Math.abs(p1.x - intersection[0]); - if (dist < minDist && ol.render.webgl.triangleIsCounterClockwise(p1.x, p1.y, - currSeg.p0.x, currSeg.p0.y, currSeg.p1.x, currSeg.p1.y) !== undefined) { - minDist = dist; - p5 = {x: intersection[0], y: intersection[1], i: -1}; - seg = currSeg; - } - } - if (minDist === Infinity) { - return false; - } - bestPoint = seg.p1; - - if (minDist > 0) { - var pointsInTriangle = this.getPointsInTriangle_(p1, p5, seg.p1, rtree); - if (pointsInTriangle.length) { - var theta = Infinity; - for (i = 0, ii = pointsInTriangle.length; i < ii; ++i) { - var currPoint = pointsInTriangle[i]; - var currTheta = Math.atan2(p1.y - currPoint.y, p2.x - currPoint.x); - if (currTheta < theta || (currTheta === theta && currPoint.x < bestPoint.x)) { - theta = currTheta; - bestPoint = currPoint; - } - } - } - } - - seg = list.firstItem(); - while (seg.p1.x !== bestPoint.x || seg.p1.y !== bestPoint.y) { - seg = list.nextItem(); - } - - //We clone the bridge points as they can have different convexity. - var p0Bridge = {x: p1.x, y: p1.y, i: p1.i, reflex: undefined}; - var p1Bridge = {x: seg.p1.x, y: seg.p1.y, i: seg.p1.i, reflex: undefined}; - - hole.getNextItem().p0 = p0Bridge; - this.insertItem_(p1, seg.p1, hole, rtree); - this.insertItem_(p1Bridge, p0Bridge, hole, rtree); - seg.p1 = p1Bridge; - hole.setFirstItem(); - list.concat(hole); - - return true; -}; - - -/** - * @private - * @param {ol.structs.LinkedList} list Linked list of the polygon. - * @param {ol.structs.RBush} rtree R-Tree of the polygon. - */ -ol.render.webgl.PolygonReplay.prototype.triangulate_ = function(list, rtree) { - var ccw = false; - var simple = this.isSimple_(list, rtree); - - // Start clipping ears - while (list.getLength() > 3) { - if (simple) { - if (!this.clipEars_(list, rtree, simple, ccw)) { - if (!this.classifyPoints_(list, rtree, ccw)) { - // Due to the behavior of OL's PIP algorithm, the ear clipping cannot - // introduce touching segments. However, the original data may have some. - if (!this.resolveSelfIntersections_(list, rtree, true)) { - break; - } - } - } - } else { - if (!this.clipEars_(list, rtree, simple, ccw)) { - // We ran out of ears, try to reclassify. - if (!this.classifyPoints_(list, rtree, ccw)) { - // We have a bad polygon, try to resolve local self-intersections. - if (!this.resolveSelfIntersections_(list, rtree)) { - simple = this.isSimple_(list, rtree); - if (!simple) { - // We have a really bad polygon, try more time consuming methods. - this.splitPolygon_(list, rtree); - break; - } else { - ccw = !this.isClockwise_(list); - this.classifyPoints_(list, rtree, ccw); - } - } - } - } - } - } - if (list.getLength() === 3) { - var numIndices = this.indices.length; - this.indices[numIndices++] = list.getPrevItem().p0.i; - this.indices[numIndices++] = list.getCurrItem().p0.i; - this.indices[numIndices++] = list.getNextItem().p0.i; - } -}; - - -/** - * @private - * @param {ol.structs.LinkedList} list Linked list of the polygon. - * @param {ol.structs.RBush} rtree R-Tree of the polygon. - * @param {boolean} simple The polygon is simple. - * @param {boolean} ccw Orientation of the polygon is counter-clockwise. - * @return {boolean} There were processed ears. - */ -ol.render.webgl.PolygonReplay.prototype.clipEars_ = function(list, rtree, simple, ccw) { - var numIndices = this.indices.length; - var start = list.firstItem(); - var s0 = list.getPrevItem(); - var s1 = start; - var s2 = list.nextItem(); - var s3 = list.getNextItem(); - var p0, p1, p2; - var processedEars = false; - do { - p0 = s1.p0; - p1 = s1.p1; - p2 = s2.p1; - if (p1.reflex === false) { - // We might have a valid ear - var variableCriterion; - if (simple) { - variableCriterion = this.getPointsInTriangle_(p0, p1, p2, rtree, true).length === 0; - } else { - variableCriterion = ccw ? this.diagonalIsInside_(s3.p1, p2, p1, p0, - s0.p0) : this.diagonalIsInside_(s0.p0, p0, p1, p2, s3.p1); - } - if ((simple || this.getIntersections_({p0: p0, p1: p2}, rtree).length === 0) && - variableCriterion) { - //The diagonal is completely inside the polygon - if (simple || p0.reflex === false || p2.reflex === false || - ol.geom.flat.orient.linearRingIsClockwise([s0.p0.x, s0.p0.y, p0.x, - p0.y, p1.x, p1.y, p2.x, p2.y, s3.p1.x, s3.p1.y], 0, 10, 2) === !ccw) { - //The diagonal is persumably valid, we have an ear - this.indices[numIndices++] = p0.i; - this.indices[numIndices++] = p1.i; - this.indices[numIndices++] = p2.i; - this.removeItem_(s1, s2, list, rtree); - if (s2 === start) { - start = s3; - } - processedEars = true; - } - } - } - // Else we have a reflex point. - s0 = list.getPrevItem(); - s1 = list.getCurrItem(); - s2 = list.nextItem(); - s3 = list.getNextItem(); - } while (s1 !== start && list.getLength() > 3); - - return processedEars; -}; - - -/** - * @private - * @param {ol.structs.LinkedList} list Linked list of the polygon. - * @param {ol.structs.RBush} rtree R-Tree of the polygon. - * @param {boolean=} opt_touch Resolve touching segments. - * @return {boolean} There were resolved intersections. -*/ -ol.render.webgl.PolygonReplay.prototype.resolveSelfIntersections_ = function( - list, rtree, opt_touch) { - var start = list.firstItem(); - list.nextItem(); - var s0 = start; - var s1 = list.nextItem(); - var resolvedIntersections = false; - - do { - var intersection = this.calculateIntersection_(s0.p0, s0.p1, s1.p0, s1.p1, - opt_touch); - if (intersection) { - var breakCond = false; - var numVertices = this.vertices.length; - var numIndices = this.indices.length; - var n = numVertices / 2; - var seg = list.prevItem(); - list.removeItem(); - rtree.remove(seg); - breakCond = (seg === start); - var p; - if (opt_touch) { - if (intersection[0] === s0.p0.x && intersection[1] === s0.p0.y) { - list.prevItem(); - p = s0.p0; - s1.p0 = p; - rtree.remove(s0); - breakCond = breakCond || (s0 === start); - } else { - p = s1.p1; - s0.p1 = p; - rtree.remove(s1); - breakCond = breakCond || (s1 === start); - } - list.removeItem(); - } else { - p = this.createPoint_(intersection[0], intersection[1], n); - s0.p1 = p; - s1.p0 = p; - rtree.update([Math.min(s0.p0.x, s0.p1.x), Math.min(s0.p0.y, s0.p1.y), - Math.max(s0.p0.x, s0.p1.x), Math.max(s0.p0.y, s0.p1.y)], s0); - rtree.update([Math.min(s1.p0.x, s1.p1.x), Math.min(s1.p0.y, s1.p1.y), - Math.max(s1.p0.x, s1.p1.x), Math.max(s1.p0.y, s1.p1.y)], s1); - } - - this.indices[numIndices++] = seg.p0.i; - this.indices[numIndices++] = seg.p1.i; - this.indices[numIndices++] = p.i; - - resolvedIntersections = true; - if (breakCond) { - break; - } - } - - s0 = list.getPrevItem(); - s1 = list.nextItem(); - } while (s0 !== start); - return resolvedIntersections; -}; - - -/** - * @private - * @param {ol.structs.LinkedList} list Linked list of the polygon. - * @param {ol.structs.RBush} rtree R-Tree of the polygon. - * @return {boolean} The polygon is simple. - */ -ol.render.webgl.PolygonReplay.prototype.isSimple_ = function(list, rtree) { - var start = list.firstItem(); - var seg = start; - do { - if (this.getIntersections_(seg, rtree).length) { - return false; - } - seg = list.nextItem(); - } while (seg !== start); - return true; -}; - - -/** - * @private - * @param {ol.structs.LinkedList} list Linked list of the polygon. - * @return {boolean} Orientation is clockwise. - */ -ol.render.webgl.PolygonReplay.prototype.isClockwise_ = function(list) { - var length = list.getLength() * 2; - var flatCoordinates = new Array(length); - var start = list.firstItem(); - var seg = start; - var i = 0; - do { - flatCoordinates[i++] = seg.p0.x; - flatCoordinates[i++] = seg.p0.y; - seg = list.nextItem(); - } while (seg !== start); - return ol.geom.flat.orient.linearRingIsClockwise(flatCoordinates, 0, length, 2); -}; - - -/** - * @private - * @param {ol.structs.LinkedList} list Linked list of the polygon. - * @param {ol.structs.RBush} rtree R-Tree of the polygon. - */ -ol.render.webgl.PolygonReplay.prototype.splitPolygon_ = function(list, rtree) { - var start = list.firstItem(); - var s0 = start; - do { - var intersections = this.getIntersections_(s0, rtree); - if (intersections.length) { - var s1 = intersections[0]; - var n = this.vertices.length / 2; - var intersection = this.calculateIntersection_(s0.p0, - s0.p1, s1.p0, s1.p1); - var p = this.createPoint_(intersection[0], intersection[1], n); - var newPolygon = new ol.structs.LinkedList(); - var newRtree = new ol.structs.RBush(); - this.insertItem_(p, s0.p1, newPolygon, newRtree); - s0.p1 = p; - rtree.update([Math.min(s0.p0.x, p.x), Math.min(s0.p0.y, p.y), - Math.max(s0.p0.x, p.x), Math.max(s0.p0.y, p.y)], s0); - var currItem = list.nextItem(); - while (currItem !== s1) { - this.insertItem_(currItem.p0, currItem.p1, newPolygon, newRtree); - rtree.remove(currItem); - list.removeItem(); - currItem = list.getCurrItem(); - } - this.insertItem_(s1.p0, p, newPolygon, newRtree); - s1.p0 = p; - rtree.update([Math.min(s1.p1.x, p.x), Math.min(s1.p1.y, p.y), - Math.max(s1.p1.x, p.x), Math.max(s1.p1.y, p.y)], s1); - this.classifyPoints_(list, rtree, false); - this.triangulate_(list, rtree); - this.classifyPoints_(newPolygon, newRtree, false); - this.triangulate_(newPolygon, newRtree); - break; - } - s0 = list.nextItem(); - } while (s0 !== start); -}; - - -/** - * @private - * @param {number} x X coordinate. - * @param {number} y Y coordinate. - * @param {number} i Index. - * @return {ol.WebglPolygonVertex} List item. - */ -ol.render.webgl.PolygonReplay.prototype.createPoint_ = function(x, y, i) { - var numVertices = this.vertices.length; - this.vertices[numVertices++] = x; - this.vertices[numVertices++] = y; - /** @type {ol.WebglPolygonVertex} */ - var p = { - x: x, - y: y, - i: i, - reflex: undefined - }; - return p; -}; - - -/** - * @private - * @param {ol.WebglPolygonVertex} p0 First point of segment. - * @param {ol.WebglPolygonVertex} p1 Second point of segment. - * @param {ol.structs.LinkedList} list Polygon ring. - * @param {ol.structs.RBush=} opt_rtree Insert the segment into the R-Tree. - * @return {ol.WebglPolygonSegment} segment. - */ -ol.render.webgl.PolygonReplay.prototype.insertItem_ = function(p0, p1, list, opt_rtree) { - var seg = { - p0: p0, - p1: p1 - }; - list.insertItem(seg); - if (opt_rtree) { - opt_rtree.insert([Math.min(p0.x, p1.x), Math.min(p0.y, p1.y), - Math.max(p0.x, p1.x), Math.max(p0.y, p1.y)], seg); - } - return seg; -}; - - -/** - * @private - * @param {ol.WebglPolygonSegment} s0 Segment before the remove candidate. - * @param {ol.WebglPolygonSegment} s1 Remove candidate segment. - * @param {ol.structs.LinkedList} list Polygon ring. - * @param {ol.structs.RBush} rtree R-Tree of the polygon. - */ -ol.render.webgl.PolygonReplay.prototype.removeItem_ = function(s0, s1, list, rtree) { - if (list.getCurrItem() === s1) { - list.removeItem(); - s0.p1 = s1.p1; - rtree.remove(s1); - rtree.update([Math.min(s0.p0.x, s0.p1.x), Math.min(s0.p0.y, s0.p1.y), - Math.max(s0.p0.x, s0.p1.x), Math.max(s0.p0.y, s0.p1.y)], s0); - } -}; - - -/** - * @private - * @param {ol.WebglPolygonVertex} p0 First point. - * @param {ol.WebglPolygonVertex} p1 Second point. - * @param {ol.WebglPolygonVertex} p2 Third point. - * @param {ol.structs.RBush} rtree R-Tree of the polygon. - * @param {boolean=} opt_reflex Only include reflex points. - * @return {Array.<ol.WebglPolygonVertex>} Points in the triangle. - */ -ol.render.webgl.PolygonReplay.prototype.getPointsInTriangle_ = function(p0, p1, - p2, rtree, opt_reflex) { - var i, ii, j, p; - var result = []; - var segmentsInExtent = rtree.getInExtent([Math.min(p0.x, p1.x, p2.x), - Math.min(p0.y, p1.y, p2.y), Math.max(p0.x, p1.x, p2.x), Math.max(p0.y, - p1.y, p2.y)]); - for (i = 0, ii = segmentsInExtent.length; i < ii; ++i) { - for (j in segmentsInExtent[i]) { - p = segmentsInExtent[i][j]; - if (typeof p === 'object' && (!opt_reflex || p.reflex)) { - if ((p.x !== p0.x || p.y !== p0.y) && (p.x !== p1.x || p.y !== p1.y) && - (p.x !== p2.x || p.y !== p2.y) && result.indexOf(p) === -1 && - ol.geom.flat.contains.linearRingContainsXY([p0.x, p0.y, p1.x, p1.y, - p2.x, p2.y], 0, 6, 2, p.x, p.y)) { - result.push(p); - } - } - } - } - return result; -}; - - -/** - * @private - * @param {ol.WebglPolygonSegment} segment Segment. - * @param {ol.structs.RBush} rtree R-Tree of the polygon. - * @param {boolean=} opt_touch Touching segments should be considered an intersection. - * @return {Array.<ol.WebglPolygonSegment>} Intersecting segments. - */ -ol.render.webgl.PolygonReplay.prototype.getIntersections_ = function(segment, rtree, opt_touch) { - var p0 = segment.p0; - var p1 = segment.p1; - var segmentsInExtent = rtree.getInExtent([Math.min(p0.x, p1.x), - Math.min(p0.y, p1.y), Math.max(p0.x, p1.x), Math.max(p0.y, p1.y)]); - var result = []; - var i, ii; - for (i = 0, ii = segmentsInExtent.length; i < ii; ++i) { - var currSeg = segmentsInExtent[i]; - if (segment !== currSeg && (opt_touch || currSeg.p0 !== p1 || currSeg.p1 !== p0) && - this.calculateIntersection_(p0, p1, currSeg.p0, currSeg.p1, opt_touch)) { - result.push(currSeg); - } - } - return result; -}; - - -/** - * Line intersection algorithm by Paul Bourke. - * @see http://paulbourke.net/geometry/pointlineplane/ - * - * @private - * @param {ol.WebglPolygonVertex} p0 First point. - * @param {ol.WebglPolygonVertex} p1 Second point. - * @param {ol.WebglPolygonVertex} p2 Third point. - * @param {ol.WebglPolygonVertex} p3 Fourth point. - * @param {boolean=} opt_touch Touching segments should be considered an intersection. - * @return {Array.<number>|undefined} Intersection coordinates. - */ -ol.render.webgl.PolygonReplay.prototype.calculateIntersection_ = function(p0, - p1, p2, p3, opt_touch) { - var denom = (p3.y - p2.y) * (p1.x - p0.x) - (p3.x - p2.x) * (p1.y - p0.y); - if (denom !== 0) { - var ua = ((p3.x - p2.x) * (p0.y - p2.y) - (p3.y - p2.y) * (p0.x - p2.x)) / denom; - var ub = ((p1.x - p0.x) * (p0.y - p2.y) - (p1.y - p0.y) * (p0.x - p2.x)) / denom; - if ((!opt_touch && ua > ol.render.webgl.EPSILON && ua < 1 - ol.render.webgl.EPSILON && - ub > ol.render.webgl.EPSILON && ub < 1 - ol.render.webgl.EPSILON) || (opt_touch && - ua >= 0 && ua <= 1 && ub >= 0 && ub <= 1)) { - return [p0.x + ua * (p1.x - p0.x), p0.y + ua * (p1.y - p0.y)]; - } - } - return undefined; -}; - - -/** - * @private - * @param {ol.WebglPolygonVertex} p0 Point before the start of the diagonal. - * @param {ol.WebglPolygonVertex} p1 Start point of the diagonal. - * @param {ol.WebglPolygonVertex} p2 Ear candidate. - * @param {ol.WebglPolygonVertex} p3 End point of the diagonal. - * @param {ol.WebglPolygonVertex} p4 Point after the end of the diagonal. - * @return {boolean} Diagonal is inside the polygon. - */ -ol.render.webgl.PolygonReplay.prototype.diagonalIsInside_ = function(p0, p1, p2, p3, p4) { - if (p1.reflex === undefined || p3.reflex === undefined) { - return false; - } - var p1IsLeftOf = (p2.x - p3.x) * (p1.y - p3.y) > (p2.y - p3.y) * (p1.x - p3.x); - var p1IsRightOf = (p4.x - p3.x) * (p1.y - p3.y) < (p4.y - p3.y) * (p1.x - p3.x); - var p3IsLeftOf = (p0.x - p1.x) * (p3.y - p1.y) > (p0.y - p1.y) * (p3.x - p1.x); - var p3IsRightOf = (p2.x - p1.x) * (p3.y - p1.y) < (p2.y - p1.y) * (p3.x - p1.x); - var p1InCone = p3.reflex ? p1IsRightOf || p1IsLeftOf : p1IsRightOf && p1IsLeftOf; - var p3InCone = p1.reflex ? p3IsRightOf || p3IsLeftOf : p3IsRightOf && p3IsLeftOf; - return p1InCone && p3InCone; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.PolygonReplay.prototype.drawMultiPolygon = function(multiPolygonGeometry, feature) { - var endss = multiPolygonGeometry.getEndss(); - var stride = multiPolygonGeometry.getStride(); - var currIndex = this.indices.length; - var currLineIndex = this.lineStringReplay.getCurrentIndex(); - var flatCoordinates = multiPolygonGeometry.getFlatCoordinates(); - var i, ii, j, jj; - var start = 0; - for (i = 0, ii = endss.length; i < ii; ++i) { - var ends = endss[i]; - if (ends.length > 0) { - var outerRing = ol.geom.flat.transform.translate(flatCoordinates, start, ends[0], - stride, -this.origin[0], -this.origin[1]); - if (outerRing.length) { - var holes = []; - var holeFlatCoords; - for (j = 1, jj = ends.length; j < jj; ++j) { - if (ends[j] !== ends[j - 1]) { - holeFlatCoords = ol.geom.flat.transform.translate(flatCoordinates, ends[j - 1], - ends[j], stride, -this.origin[0], -this.origin[1]); - holes.push(holeFlatCoords); - } - } - this.lineStringReplay.drawPolygonCoordinates(outerRing, holes, stride); - this.drawCoordinates_(outerRing, holes, stride); - } - } - start = ends[ends.length - 1]; - } - if (this.indices.length > currIndex) { - this.startIndices.push(currIndex); - this.startIndicesFeature.push(feature); - if (this.state_.changed) { - this.styleIndices_.push(currIndex); - this.state_.changed = false; - } - } - if (this.lineStringReplay.getCurrentIndex() > currLineIndex) { - this.lineStringReplay.setPolygonStyle(feature, currLineIndex); - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.PolygonReplay.prototype.drawPolygon = function(polygonGeometry, feature) { - var ends = polygonGeometry.getEnds(); - var stride = polygonGeometry.getStride(); - if (ends.length > 0) { - var flatCoordinates = polygonGeometry.getFlatCoordinates().map(Number); - var outerRing = ol.geom.flat.transform.translate(flatCoordinates, 0, ends[0], - stride, -this.origin[0], -this.origin[1]); - if (outerRing.length) { - var holes = []; - var i, ii, holeFlatCoords; - for (i = 1, ii = ends.length; i < ii; ++i) { - if (ends[i] !== ends[i - 1]) { - holeFlatCoords = ol.geom.flat.transform.translate(flatCoordinates, ends[i - 1], - ends[i], stride, -this.origin[0], -this.origin[1]); - holes.push(holeFlatCoords); - } - } - - this.startIndices.push(this.indices.length); - this.startIndicesFeature.push(feature); - if (this.state_.changed) { - this.styleIndices_.push(this.indices.length); - this.state_.changed = false; - } - this.lineStringReplay.setPolygonStyle(feature); - - this.lineStringReplay.drawPolygonCoordinates(outerRing, holes, stride); - this.drawCoordinates_(outerRing, holes, stride); - } - } -}; - - -/** - * @inheritDoc - **/ -ol.render.webgl.PolygonReplay.prototype.finish = function(context) { - // create, bind, and populate the vertices buffer - this.verticesBuffer = new ol.webgl.Buffer(this.vertices); - - // create, bind, and populate the indices buffer - this.indicesBuffer = new ol.webgl.Buffer(this.indices); - - this.startIndices.push(this.indices.length); - - this.lineStringReplay.finish(context); - - //Clean up, if there is nothing to draw - if (this.styleIndices_.length === 0 && this.styles_.length > 0) { - this.styles_ = []; - } - - this.vertices = null; - this.indices = null; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.PolygonReplay.prototype.getDeleteResourcesFunction = function(context) { - var verticesBuffer = this.verticesBuffer; - var indicesBuffer = this.indicesBuffer; - var lineDeleter = this.lineStringReplay.getDeleteResourcesFunction(context); - return function() { - context.deleteBuffer(verticesBuffer); - context.deleteBuffer(indicesBuffer); - lineDeleter(); - }; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.PolygonReplay.prototype.setUpProgram = function(gl, context, size, pixelRatio) { - // get the program - var fragmentShader, vertexShader; - fragmentShader = ol.render.webgl.polygonreplay.defaultshader.fragment; - vertexShader = ol.render.webgl.polygonreplay.defaultshader.vertex; - var program = context.getProgram(fragmentShader, vertexShader); - - // get the locations - var locations; - if (!this.defaultLocations_) { - locations = new ol.render.webgl.polygonreplay.defaultshader.Locations(gl, program); - this.defaultLocations_ = locations; - } else { - locations = this.defaultLocations_; - } - - context.useProgram(program); - - // enable the vertex attrib arrays - gl.enableVertexAttribArray(locations.a_position); - gl.vertexAttribPointer(locations.a_position, 2, ol.webgl.FLOAT, - false, 8, 0); - - return locations; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.PolygonReplay.prototype.shutDownProgram = function(gl, locations) { - gl.disableVertexAttribArray(locations.a_position); -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.PolygonReplay.prototype.drawReplay = function(gl, context, skippedFeaturesHash, hitDetection) { - //Save GL parameters. - var tmpDepthFunc = /** @type {number} */ (gl.getParameter(gl.DEPTH_FUNC)); - var tmpDepthMask = /** @type {boolean} */ (gl.getParameter(gl.DEPTH_WRITEMASK)); - - if (!hitDetection) { - gl.enable(gl.DEPTH_TEST); - gl.depthMask(true); - gl.depthFunc(gl.NOTEQUAL); - } - - if (!ol.obj.isEmpty(skippedFeaturesHash)) { - this.drawReplaySkipping_(gl, context, skippedFeaturesHash); - } else { - //Draw by style groups to minimize drawElements() calls. - var i, start, end, nextStyle; - end = this.startIndices[this.startIndices.length - 1]; - for (i = this.styleIndices_.length - 1; i >= 0; --i) { - start = this.styleIndices_[i]; - nextStyle = this.styles_[i]; - this.setFillStyle_(gl, nextStyle); - this.drawElements(gl, context, start, end); - end = start; - } - } - if (!hitDetection) { - gl.disable(gl.DEPTH_TEST); - gl.clear(gl.DEPTH_BUFFER_BIT); - //Restore GL parameters. - gl.depthMask(tmpDepthMask); - gl.depthFunc(tmpDepthFunc); - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.PolygonReplay.prototype.drawHitDetectionReplayOneByOne = function(gl, context, skippedFeaturesHash, - featureCallback, opt_hitExtent) { - var i, start, end, nextStyle, groupStart, feature, featureUid, featureIndex; - featureIndex = this.startIndices.length - 2; - end = this.startIndices[featureIndex + 1]; - for (i = this.styleIndices_.length - 1; i >= 0; --i) { - nextStyle = this.styles_[i]; - this.setFillStyle_(gl, nextStyle); - groupStart = this.styleIndices_[i]; - - while (featureIndex >= 0 && - this.startIndices[featureIndex] >= groupStart) { - start = this.startIndices[featureIndex]; - feature = this.startIndicesFeature[featureIndex]; - featureUid = ol.getUid(feature).toString(); - - if (skippedFeaturesHash[featureUid] === undefined && - feature.getGeometry() && - (opt_hitExtent === undefined || ol.extent.intersects( - /** @type {Array<number>} */ (opt_hitExtent), - feature.getGeometry().getExtent()))) { - gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT); - this.drawElements(gl, context, start, end); - - var result = featureCallback(feature); - - if (result) { - return result; - } - - } - featureIndex--; - end = start; - } - } - return undefined; -}; - - -/** - * @private - * @param {WebGLRenderingContext} gl gl. - * @param {ol.webgl.Context} context Context. - * @param {Object} skippedFeaturesHash Ids of features to skip. - */ -ol.render.webgl.PolygonReplay.prototype.drawReplaySkipping_ = function(gl, context, skippedFeaturesHash) { - var i, start, end, nextStyle, groupStart, feature, featureUid, featureIndex, featureStart; - featureIndex = this.startIndices.length - 2; - end = start = this.startIndices[featureIndex + 1]; - for (i = this.styleIndices_.length - 1; i >= 0; --i) { - nextStyle = this.styles_[i]; - this.setFillStyle_(gl, nextStyle); - groupStart = this.styleIndices_[i]; - - while (featureIndex >= 0 && - this.startIndices[featureIndex] >= groupStart) { - featureStart = this.startIndices[featureIndex]; - feature = this.startIndicesFeature[featureIndex]; - featureUid = ol.getUid(feature).toString(); - - if (skippedFeaturesHash[featureUid]) { - if (start !== end) { - this.drawElements(gl, context, start, end); - gl.clear(gl.DEPTH_BUFFER_BIT); - } - end = featureStart; - } - featureIndex--; - start = featureStart; - } - if (start !== end) { - this.drawElements(gl, context, start, end); - gl.clear(gl.DEPTH_BUFFER_BIT); - } - start = end = groupStart; - } -}; - - -/** - * @private - * @param {WebGLRenderingContext} gl gl. - * @param {Array.<number>} color Color. - */ -ol.render.webgl.PolygonReplay.prototype.setFillStyle_ = function(gl, color) { - gl.uniform4fv(this.defaultLocations_.u_color, color); -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.PolygonReplay.prototype.setFillStrokeStyle = function(fillStyle, strokeStyle) { - var fillStyleColor = fillStyle ? fillStyle.getColor() : [0, 0, 0, 0]; - if (!(fillStyleColor instanceof CanvasGradient) && - !(fillStyleColor instanceof CanvasPattern)) { - fillStyleColor = ol.color.asArray(fillStyleColor).map(function(c, i) { - return i != 3 ? c / 255 : c; - }) || ol.render.webgl.defaultFillStyle; - } else { - fillStyleColor = ol.render.webgl.defaultFillStyle; - } - if (!this.state_.fillColor || !ol.array.equals(fillStyleColor, this.state_.fillColor)) { - this.state_.fillColor = fillStyleColor; - this.state_.changed = true; - this.styles_.push(fillStyleColor); - } - //Provide a null stroke style, if no strokeStyle is provided. Required for the draw interaction to work. - if (strokeStyle) { - this.lineStringReplay.setFillStrokeStyle(null, strokeStyle); - } else { - var nullStrokeStyle = new ol.style.Stroke({ - color: [0, 0, 0, 0], - lineWidth: 0 - }); - this.lineStringReplay.setFillStrokeStyle(null, nullStrokeStyle); - } -}; - -goog.provide('ol.style.Atlas'); - -goog.require('ol.dom'); - - -/** - * This class facilitates the creation of image atlases. - * - * Images added to an atlas will be rendered onto a single - * atlas canvas. The distribution of images on the canvas is - * managed with the bin packing algorithm described in: - * http://www.blackpawn.com/texts/lightmaps/ - * - * @constructor - * @struct - * @param {number} size The size in pixels of the sprite image. - * @param {number} space The space in pixels between images. - * Because texture coordinates are float values, the edges of - * images might not be completely correct (in a way that the - * edges overlap when being rendered). To avoid this we add a - * padding around each image. - */ -ol.style.Atlas = function(size, space) { - - /** - * @private - * @type {number} - */ - this.space_ = space; - - /** - * @private - * @type {Array.<ol.AtlasBlock>} - */ - this.emptyBlocks_ = [{x: 0, y: 0, width: size, height: size}]; - - /** - * @private - * @type {Object.<string, ol.AtlasInfo>} - */ - this.entries_ = {}; - - /** - * @private - * @type {CanvasRenderingContext2D} - */ - this.context_ = ol.dom.createCanvasContext2D(size, size); - - /** - * @private - * @type {HTMLCanvasElement} - */ - this.canvas_ = this.context_.canvas; -}; - - -/** - * @param {string} id The identifier of the entry to check. - * @return {?ol.AtlasInfo} The atlas info. - */ -ol.style.Atlas.prototype.get = function(id) { - return this.entries_[id] || null; -}; - - -/** - * @param {string} id The identifier of the entry to add. - * @param {number} width The width. - * @param {number} height The height. - * @param {function(CanvasRenderingContext2D, number, number)} renderCallback - * Called to render the new image onto an atlas image. - * @param {Object=} opt_this Value to use as `this` when executing - * `renderCallback`. - * @return {?ol.AtlasInfo} The position and atlas image for the entry. - */ -ol.style.Atlas.prototype.add = function(id, width, height, renderCallback, opt_this) { - var block, i, ii; - for (i = 0, ii = this.emptyBlocks_.length; i < ii; ++i) { - block = this.emptyBlocks_[i]; - if (block.width >= width + this.space_ && - block.height >= height + this.space_) { - // we found a block that is big enough for our entry - var entry = { - offsetX: block.x + this.space_, - offsetY: block.y + this.space_, - image: this.canvas_ - }; - this.entries_[id] = entry; - - // render the image on the atlas image - renderCallback.call(opt_this, this.context_, - block.x + this.space_, block.y + this.space_); - - // split the block after the insertion, either horizontally or vertically - this.split_(i, block, width + this.space_, height + this.space_); - - return entry; - } - } - - // there is no space for the new entry in this atlas - return null; -}; - - -/** - * @private - * @param {number} index The index of the block. - * @param {ol.AtlasBlock} block The block to split. - * @param {number} width The width of the entry to insert. - * @param {number} height The height of the entry to insert. - */ -ol.style.Atlas.prototype.split_ = function(index, block, width, height) { - var deltaWidth = block.width - width; - var deltaHeight = block.height - height; - - /** @type {ol.AtlasBlock} */ - var newBlock1; - /** @type {ol.AtlasBlock} */ - var newBlock2; - - if (deltaWidth > deltaHeight) { - // split vertically - // block right of the inserted entry - newBlock1 = { - x: block.x + width, - y: block.y, - width: block.width - width, - height: block.height - }; - - // block below the inserted entry - newBlock2 = { - x: block.x, - y: block.y + height, - width: width, - height: block.height - height - }; - this.updateBlocks_(index, newBlock1, newBlock2); - } else { - // split horizontally - // block right of the inserted entry - newBlock1 = { - x: block.x + width, - y: block.y, - width: block.width - width, - height: height - }; - - // block below the inserted entry - newBlock2 = { - x: block.x, - y: block.y + height, - width: block.width, - height: block.height - height - }; - this.updateBlocks_(index, newBlock1, newBlock2); - } -}; - - -/** - * Remove the old block and insert new blocks at the same array position. - * The new blocks are inserted at the same position, so that splitted - * blocks (that are potentially smaller) are filled first. - * @private - * @param {number} index The index of the block to remove. - * @param {ol.AtlasBlock} newBlock1 The 1st block to add. - * @param {ol.AtlasBlock} newBlock2 The 2nd block to add. - */ -ol.style.Atlas.prototype.updateBlocks_ = function(index, newBlock1, newBlock2) { - var args = [index, 1]; - if (newBlock1.width > 0 && newBlock1.height > 0) { - args.push(newBlock1); - } - if (newBlock2.width > 0 && newBlock2.height > 0) { - args.push(newBlock2); - } - this.emptyBlocks_.splice.apply(this.emptyBlocks_, args); -}; - -goog.provide('ol.style.AtlasManager'); - -goog.require('ol'); -goog.require('ol.style.Atlas'); - - -/** - * Manages the creation of image atlases. - * - * Images added to this manager will be inserted into an atlas, which - * will be used for rendering. - * The `size` given in the constructor is the size for the first - * atlas. After that, when new atlases are created, they will have - * twice the size as the latest atlas (until `maxSize` is reached). - * - * If an application uses many images or very large images, it is recommended - * to set a higher `size` value to avoid the creation of too many atlases. - * - * @constructor - * @struct - * @api - * @param {olx.style.AtlasManagerOptions=} opt_options Options. - */ -ol.style.AtlasManager = function(opt_options) { - - var options = opt_options || {}; - - /** - * The size in pixels of the latest atlas image. - * @private - * @type {number} - */ - this.currentSize_ = options.initialSize !== undefined ? - options.initialSize : ol.INITIAL_ATLAS_SIZE; - - /** - * The maximum size in pixels of atlas images. - * @private - * @type {number} - */ - this.maxSize_ = options.maxSize !== undefined ? - options.maxSize : ol.MAX_ATLAS_SIZE != -1 ? - ol.MAX_ATLAS_SIZE : ol.WEBGL_MAX_TEXTURE_SIZE !== undefined ? - ol.WEBGL_MAX_TEXTURE_SIZE : 2048; - - /** - * The size in pixels between images. - * @private - * @type {number} - */ - this.space_ = options.space !== undefined ? options.space : 1; - - /** - * @private - * @type {Array.<ol.style.Atlas>} - */ - this.atlases_ = [new ol.style.Atlas(this.currentSize_, this.space_)]; - - /** - * The size in pixels of the latest atlas image for hit-detection images. - * @private - * @type {number} - */ - this.currentHitSize_ = this.currentSize_; - - /** - * @private - * @type {Array.<ol.style.Atlas>} - */ - this.hitAtlases_ = [new ol.style.Atlas(this.currentHitSize_, this.space_)]; -}; - - -/** - * @param {string} id The identifier of the entry to check. - * @return {?ol.AtlasManagerInfo} The position and atlas image for the - * entry, or `null` if the entry is not part of the atlas manager. - */ -ol.style.AtlasManager.prototype.getInfo = function(id) { - /** @type {?ol.AtlasInfo} */ - var info = this.getInfo_(this.atlases_, id); - - if (!info) { - return null; - } - var hitInfo = /** @type {ol.AtlasInfo} */ (this.getInfo_(this.hitAtlases_, id)); - - return this.mergeInfos_(info, hitInfo); -}; - - -/** - * @private - * @param {Array.<ol.style.Atlas>} atlases The atlases to search. - * @param {string} id The identifier of the entry to check. - * @return {?ol.AtlasInfo} The position and atlas image for the entry, - * or `null` if the entry is not part of the atlases. - */ -ol.style.AtlasManager.prototype.getInfo_ = function(atlases, id) { - var atlas, info, i, ii; - for (i = 0, ii = atlases.length; i < ii; ++i) { - atlas = atlases[i]; - info = atlas.get(id); - if (info) { - return info; - } - } - return null; -}; - - -/** - * @private - * @param {ol.AtlasInfo} info The info for the real image. - * @param {ol.AtlasInfo} hitInfo The info for the hit-detection - * image. - * @return {?ol.AtlasManagerInfo} The position and atlas image for the - * entry, or `null` if the entry is not part of the atlases. - */ -ol.style.AtlasManager.prototype.mergeInfos_ = function(info, hitInfo) { - return /** @type {ol.AtlasManagerInfo} */ ({ - offsetX: info.offsetX, - offsetY: info.offsetY, - image: info.image, - hitImage: hitInfo.image - }); -}; - - -/** - * Add an image to the atlas manager. - * - * If an entry for the given id already exists, the entry will - * be overridden (but the space on the atlas graphic will not be freed). - * - * If `renderHitCallback` is provided, the image (or the hit-detection version - * of the image) will be rendered into a separate hit-detection atlas image. - * - * @param {string} id The identifier of the entry to add. - * @param {number} width The width. - * @param {number} height The height. - * @param {function(CanvasRenderingContext2D, number, number)} renderCallback - * Called to render the new image onto an atlas image. - * @param {function(CanvasRenderingContext2D, number, number)=} - * opt_renderHitCallback Called to render a hit-detection image onto a hit - * detection atlas image. - * @param {Object=} opt_this Value to use as `this` when executing - * `renderCallback` and `renderHitCallback`. - * @return {?ol.AtlasManagerInfo} The position and atlas image for the - * entry, or `null` if the image is too big. - */ -ol.style.AtlasManager.prototype.add = function(id, width, height, - renderCallback, opt_renderHitCallback, opt_this) { - if (width + this.space_ > this.maxSize_ || - height + this.space_ > this.maxSize_) { - return null; - } - - /** @type {?ol.AtlasInfo} */ - var info = this.add_(false, - id, width, height, renderCallback, opt_this); - if (!info) { - return null; - } - - // even if no hit-detection entry is requested, we insert a fake entry into - // the hit-detection atlas, to make sure that the offset is the same for - // the original image and the hit-detection image. - var renderHitCallback = opt_renderHitCallback !== undefined ? - opt_renderHitCallback : ol.nullFunction; - - var hitInfo = /** @type {ol.AtlasInfo} */ (this.add_(true, - id, width, height, renderHitCallback, opt_this)); - - return this.mergeInfos_(info, hitInfo); -}; - - -/** - * @private - * @param {boolean} isHitAtlas If the hit-detection atlases are used. - * @param {string} id The identifier of the entry to add. - * @param {number} width The width. - * @param {number} height The height. - * @param {function(CanvasRenderingContext2D, number, number)} renderCallback - * Called to render the new image onto an atlas image. - * @param {Object=} opt_this Value to use as `this` when executing - * `renderCallback` and `renderHitCallback`. - * @return {?ol.AtlasInfo} The position and atlas image for the entry, - * or `null` if the image is too big. - */ -ol.style.AtlasManager.prototype.add_ = function(isHitAtlas, id, width, height, - renderCallback, opt_this) { - var atlases = (isHitAtlas) ? this.hitAtlases_ : this.atlases_; - var atlas, info, i, ii; - for (i = 0, ii = atlases.length; i < ii; ++i) { - atlas = atlases[i]; - info = atlas.add(id, width, height, renderCallback, opt_this); - if (info) { - return info; - } else if (!info && i === ii - 1) { - // the entry could not be added to one of the existing atlases, - // create a new atlas that is twice as big and try to add to this one. - var size; - if (isHitAtlas) { - size = Math.min(this.currentHitSize_ * 2, this.maxSize_); - this.currentHitSize_ = size; - } else { - size = Math.min(this.currentSize_ * 2, this.maxSize_); - this.currentSize_ = size; - } - atlas = new ol.style.Atlas(size, this.space_); - atlases.push(atlas); - // run the loop another time - ++ii; - } - } - return null; -}; - -goog.provide('ol.render.webgl.TextReplay'); - -goog.require('ol'); -goog.require('ol.colorlike'); -goog.require('ol.dom'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.has'); -goog.require('ol.render.replay'); -goog.require('ol.render.webgl'); -goog.require('ol.render.webgl.TextureReplay'); -goog.require('ol.style.AtlasManager'); -goog.require('ol.webgl.Buffer'); - - -/** - * @constructor - * @extends {ol.render.webgl.TextureReplay} - * @param {number} tolerance Tolerance. - * @param {ol.Extent} maxExtent Max extent. - * @struct - */ -ol.render.webgl.TextReplay = function(tolerance, maxExtent) { - ol.render.webgl.TextureReplay.call(this, tolerance, maxExtent); - - /** - * @private - * @type {Array.<HTMLCanvasElement>} - */ - this.images_ = []; - - /** - * @private - * @type {Array.<WebGLTexture>} - */ - this.textures_ = []; - - /** - * @private - * @type {HTMLCanvasElement} - */ - this.measureCanvas_ = ol.dom.createCanvasContext2D(0, 0).canvas; - - /** - * @private - * @type {{strokeColor: (ol.ColorLike|null), - * lineCap: (string|undefined), - * lineDash: Array.<number>, - * lineDashOffset: (number|undefined), - * lineJoin: (string|undefined), - * lineWidth: number, - * miterLimit: (number|undefined), - * fillColor: (ol.ColorLike|null), - * font: (string|undefined), - * scale: (number|undefined)}} - */ - this.state_ = { - strokeColor: null, - lineCap: undefined, - lineDash: null, - lineDashOffset: undefined, - lineJoin: undefined, - lineWidth: 0, - miterLimit: undefined, - fillColor: null, - font: undefined, - scale: undefined - }; - - /** - * @private - * @type {string} - */ - this.text_ = ''; - - /** - * @private - * @type {number|undefined} - */ - this.textAlign_ = undefined; - - /** - * @private - * @type {number|undefined} - */ - this.textBaseline_ = undefined; - - /** - * @private - * @type {number|undefined} - */ - this.offsetX_ = undefined; - - /** - * @private - * @type {number|undefined} - */ - this.offsetY_ = undefined; - - /** - * @private - * @type {Object.<string, ol.WebglGlyphAtlas>} - */ - this.atlases_ = {}; - - /** - * @private - * @type {ol.WebglGlyphAtlas|undefined} - */ - this.currAtlas_ = undefined; - - this.scale = 1; - - this.opacity = 1; - -}; -ol.inherits(ol.render.webgl.TextReplay, ol.render.webgl.TextureReplay); - - -/** - * @inheritDoc - */ -ol.render.webgl.TextReplay.prototype.drawText = function(geometry, feature) { - if (this.text_) { - var flatCoordinates = null; - var offset = 0; - var end = 2; - var stride = 2; - switch (geometry.getType()) { - case ol.geom.GeometryType.POINT: - case ol.geom.GeometryType.MULTI_POINT: - flatCoordinates = geometry.getFlatCoordinates(); - end = flatCoordinates.length; - stride = geometry.getStride(); - break; - case ol.geom.GeometryType.CIRCLE: - flatCoordinates = /** @type {ol.geom.Circle} */ (geometry).getCenter(); - break; - case ol.geom.GeometryType.LINE_STRING: - flatCoordinates = /** @type {ol.geom.LineString} */ (geometry).getFlatMidpoint(); - break; - case ol.geom.GeometryType.MULTI_LINE_STRING: - flatCoordinates = /** @type {ol.geom.MultiLineString} */ (geometry).getFlatMidpoints(); - end = flatCoordinates.length; - break; - case ol.geom.GeometryType.POLYGON: - flatCoordinates = /** @type {ol.geom.Polygon} */ (geometry).getFlatInteriorPoint(); - break; - case ol.geom.GeometryType.MULTI_POLYGON: - flatCoordinates = /** @type {ol.geom.MultiPolygon} */ (geometry).getFlatInteriorPoints(); - end = flatCoordinates.length; - break; - default: - } - this.startIndices.push(this.indices.length); - this.startIndicesFeature.push(feature); - - var glyphAtlas = this.currAtlas_; - var lines = this.text_.split('\n'); - var textSize = this.getTextSize_(lines); - var i, ii, j, jj, currX, currY, charArr, charInfo; - var anchorX = Math.round(textSize[0] * this.textAlign_ - this.offsetX_); - var anchorY = Math.round(textSize[1] * this.textBaseline_ - this.offsetY_); - var lineWidth = (this.state_.lineWidth / 2) * this.state_.scale; - - for (i = 0, ii = lines.length; i < ii; ++i) { - currX = 0; - currY = glyphAtlas.height * i; - charArr = lines[i].split(''); - - for (j = 0, jj = charArr.length; j < jj; ++j) { - charInfo = glyphAtlas.atlas.getInfo(charArr[j]); - - if (charInfo) { - var image = charInfo.image; - - this.anchorX = anchorX - currX; - this.anchorY = anchorY - currY; - this.originX = j === 0 ? charInfo.offsetX - lineWidth : charInfo.offsetX; - this.originY = charInfo.offsetY; - this.height = glyphAtlas.height; - this.width = j === 0 || j === charArr.length - 1 ? - glyphAtlas.width[charArr[j]] + lineWidth : glyphAtlas.width[charArr[j]]; - this.imageHeight = image.height; - this.imageWidth = image.width; - - var currentImage; - if (this.images_.length === 0) { - this.images_.push(image); - } else { - currentImage = this.images_[this.images_.length - 1]; - if (ol.getUid(currentImage) != ol.getUid(image)) { - this.groupIndices.push(this.indices.length); - this.images_.push(image); - } - } - - this.drawText_(flatCoordinates, offset, end, stride); - } - currX += this.width; - } - } - } -}; - - -/** - * @private - * @param {Array.<string>} lines Label to draw split to lines. - * @return {Array.<number>} Size of the label in pixels. - */ -ol.render.webgl.TextReplay.prototype.getTextSize_ = function(lines) { - var self = this; - var glyphAtlas = this.currAtlas_; - var textHeight = lines.length * glyphAtlas.height; - //Split every line to an array of chars, sum up their width, and select the longest. - var textWidth = lines.map(function(str) { - var sum = 0; - var i, ii; - for (i = 0, ii = str.length; i < ii; ++i) { - var curr = str[i]; - if (!glyphAtlas.width[curr]) { - self.addCharToAtlas_(curr); - } - sum += glyphAtlas.width[curr] ? glyphAtlas.width[curr] : 0; - } - return sum; - }).reduce(function(max, curr) { - return Math.max(max, curr); - }); - - return [textWidth, textHeight]; -}; - - -/** - * @private - * @param {Array.<number>} flatCoordinates Flat coordinates. - * @param {number} offset Offset. - * @param {number} end End. - * @param {number} stride Stride. - */ -ol.render.webgl.TextReplay.prototype.drawText_ = function(flatCoordinates, offset, - end, stride) { - var i, ii; - for (i = offset, ii = end; i < ii; i += stride) { - this.drawCoordinates(flatCoordinates, offset, end, stride); - } -}; - - -/** - * @private - * @param {string} char Character. - */ -ol.render.webgl.TextReplay.prototype.addCharToAtlas_ = function(char) { - if (char.length === 1) { - var glyphAtlas = this.currAtlas_; - var state = this.state_; - var mCtx = this.measureCanvas_.getContext('2d'); - mCtx.font = state.font; - var width = Math.ceil(mCtx.measureText(char).width * state.scale); - - var info = glyphAtlas.atlas.add(char, width, glyphAtlas.height, - function(ctx, x, y) { - //Parameterize the canvas - ctx.font = /** @type {string} */ (state.font); - ctx.fillStyle = state.fillColor; - ctx.strokeStyle = state.strokeColor; - ctx.lineWidth = state.lineWidth; - ctx.lineCap = /*** @type {string} */ (state.lineCap); - ctx.lineJoin = /** @type {string} */ (state.lineJoin); - ctx.miterLimit = /** @type {number} */ (state.miterLimit); - ctx.textAlign = 'left'; - ctx.textBaseline = 'top'; - if (ol.has.CANVAS_LINE_DASH && state.lineDash) { - //FIXME: use pixelRatio - ctx.setLineDash(state.lineDash); - ctx.lineDashOffset = /** @type {number} */ (state.lineDashOffset); - } - if (state.scale !== 1) { - //FIXME: use pixelRatio - ctx.setTransform(/** @type {number} */ (state.scale), 0, 0, - /** @type {number} */ (state.scale), 0, 0); - } - - //Draw the character on the canvas - if (state.strokeColor) { - ctx.strokeText(char, x, y); - } - if (state.fillColor) { - ctx.fillText(char, x, y); - } - }); - - if (info) { - glyphAtlas.width[char] = width; - } - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.TextReplay.prototype.finish = function(context) { - var gl = context.getGL(); - - this.groupIndices.push(this.indices.length); - this.hitDetectionGroupIndices = this.groupIndices; - - // create, bind, and populate the vertices buffer - this.verticesBuffer = new ol.webgl.Buffer(this.vertices); - - // create, bind, and populate the indices buffer - this.indicesBuffer = new ol.webgl.Buffer(this.indices); - - // create textures - /** @type {Object.<string, WebGLTexture>} */ - var texturePerImage = {}; - - this.createTextures(this.textures_, this.images_, texturePerImage, gl); - - this.state_ = { - strokeColor: null, - lineCap: undefined, - lineDash: null, - lineDashOffset: undefined, - lineJoin: undefined, - lineWidth: 0, - miterLimit: undefined, - fillColor: null, - font: undefined, - scale: undefined - }; - this.text_ = ''; - this.textAlign_ = undefined; - this.textBaseline_ = undefined; - this.offsetX_ = undefined; - this.offsetY_ = undefined; - this.images_ = null; - this.atlases_ = {}; - this.currAtlas_ = undefined; - ol.render.webgl.TextureReplay.prototype.finish.call(this, context); -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.TextReplay.prototype.setTextStyle = function(textStyle) { - var state = this.state_; - var textFillStyle = textStyle.getFill(); - var textStrokeStyle = textStyle.getStroke(); - if (!textStyle || !textStyle.getText() || (!textFillStyle && !textStrokeStyle)) { - this.text_ = ''; - } else { - if (!textFillStyle) { - state.fillColor = null; - } else { - var textFillStyleColor = textFillStyle.getColor(); - state.fillColor = ol.colorlike.asColorLike(textFillStyleColor ? - textFillStyleColor : ol.render.webgl.defaultFillStyle); - } - if (!textStrokeStyle) { - state.strokeColor = null; - state.lineWidth = 0; - } else { - var textStrokeStyleColor = textStrokeStyle.getColor(); - state.strokeColor = ol.colorlike.asColorLike(textStrokeStyleColor ? - textStrokeStyleColor : ol.render.webgl.defaultStrokeStyle); - state.lineWidth = textStrokeStyle.getWidth() || ol.render.webgl.defaultLineWidth; - state.lineCap = textStrokeStyle.getLineCap() || ol.render.webgl.defaultLineCap; - state.lineDashOffset = textStrokeStyle.getLineDashOffset() || ol.render.webgl.defaultLineDashOffset; - state.lineJoin = textStrokeStyle.getLineJoin() || ol.render.webgl.defaultLineJoin; - state.miterLimit = textStrokeStyle.getMiterLimit() || ol.render.webgl.defaultMiterLimit; - var lineDash = textStrokeStyle.getLineDash(); - state.lineDash = lineDash ? lineDash.slice() : ol.render.webgl.defaultLineDash; - } - state.font = textStyle.getFont() || ol.render.webgl.defaultFont; - state.scale = textStyle.getScale() || 1; - this.text_ = /** @type {string} */ (textStyle.getText()); - var textAlign = ol.render.replay.TEXT_ALIGN[textStyle.getTextAlign()]; - var textBaseline = ol.render.replay.TEXT_ALIGN[textStyle.getTextBaseline()]; - this.textAlign_ = textAlign === undefined ? - ol.render.webgl.defaultTextAlign : textAlign; - this.textBaseline_ = textBaseline === undefined ? - ol.render.webgl.defaultTextBaseline : textBaseline; - this.offsetX_ = textStyle.getOffsetX() || 0; - this.offsetY_ = textStyle.getOffsetY() || 0; - this.rotateWithView = !!textStyle.getRotateWithView(); - this.rotation = textStyle.getRotation() || 0; - - this.currAtlas_ = this.getAtlas_(state); - } -}; - - -/** - * @private - * @param {Object} state Font attributes. - * @return {ol.WebglGlyphAtlas} Glyph atlas. - */ -ol.render.webgl.TextReplay.prototype.getAtlas_ = function(state) { - var params = []; - var i; - for (i in state) { - if (state[i] || state[i] === 0) { - if (Array.isArray(state[i])) { - params = params.concat(state[i]); - } else { - params.push(state[i]); - } - } - } - var hash = this.calculateHash_(params); - if (!this.atlases_[hash]) { - var mCtx = this.measureCanvas_.getContext('2d'); - mCtx.font = state.font; - var height = Math.ceil((mCtx.measureText('M').width * 1.5 + - state.lineWidth / 2) * state.scale); - - this.atlases_[hash] = { - atlas: new ol.style.AtlasManager({ - space: state.lineWidth + 1 - }), - width: {}, - height: height - }; - } - return this.atlases_[hash]; -}; - - -/** - * @private - * @param {Array.<string|number>} params Array of parameters. - * @return {string} Hash string. - */ -ol.render.webgl.TextReplay.prototype.calculateHash_ = function(params) { - //TODO: Create a more performant, reliable, general hash function. - var i, ii; - var hash = ''; - for (i = 0, ii = params.length; i < ii; ++i) { - hash += params[i]; - } - return hash; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.TextReplay.prototype.getTextures = function(opt_all) { - return this.textures_; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.TextReplay.prototype.getHitDetectionTextures = function() { - return this.textures_; -}; - -goog.provide('ol.render.webgl.ReplayGroup'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.extent'); -goog.require('ol.obj'); -goog.require('ol.render.replay'); -goog.require('ol.render.ReplayGroup'); -goog.require('ol.render.webgl.CircleReplay'); -goog.require('ol.render.webgl.ImageReplay'); -goog.require('ol.render.webgl.LineStringReplay'); -goog.require('ol.render.webgl.PolygonReplay'); -goog.require('ol.render.webgl.TextReplay'); - - -/** - * @constructor - * @extends {ol.render.ReplayGroup} - * @param {number} tolerance Tolerance. - * @param {ol.Extent} maxExtent Max extent. - * @param {number=} opt_renderBuffer Render buffer. - * @struct - */ -ol.render.webgl.ReplayGroup = function(tolerance, maxExtent, opt_renderBuffer) { - ol.render.ReplayGroup.call(this); - - /** - * @type {ol.Extent} - * @private - */ - this.maxExtent_ = maxExtent; - - /** - * @type {number} - * @private - */ - this.tolerance_ = tolerance; - - /** - * @type {number|undefined} - * @private - */ - this.renderBuffer_ = opt_renderBuffer; - - /** - * @private - * @type {!Object.<string, - * Object.<ol.render.ReplayType, ol.render.webgl.Replay>>} - */ - this.replaysByZIndex_ = {}; - -}; -ol.inherits(ol.render.webgl.ReplayGroup, ol.render.ReplayGroup); - - -/** - * @param {ol.webgl.Context} context WebGL context. - * @return {function()} Delete resources function. - */ -ol.render.webgl.ReplayGroup.prototype.getDeleteResourcesFunction = function(context) { - var functions = []; - var zKey; - for (zKey in this.replaysByZIndex_) { - var replays = this.replaysByZIndex_[zKey]; - var replayKey; - for (replayKey in replays) { - functions.push( - replays[replayKey].getDeleteResourcesFunction(context)); - } - } - return function() { - var length = functions.length; - var result; - for (var i = 0; i < length; i++) { - result = functions[i].apply(this, arguments); - } - return result; - }; -}; - - -/** - * @param {ol.webgl.Context} context Context. - */ -ol.render.webgl.ReplayGroup.prototype.finish = function(context) { - var zKey; - for (zKey in this.replaysByZIndex_) { - var replays = this.replaysByZIndex_[zKey]; - var replayKey; - for (replayKey in replays) { - replays[replayKey].finish(context); - } - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.ReplayGroup.prototype.getReplay = function(zIndex, replayType) { - var zIndexKey = zIndex !== undefined ? zIndex.toString() : '0'; - var replays = this.replaysByZIndex_[zIndexKey]; - if (replays === undefined) { - replays = {}; - this.replaysByZIndex_[zIndexKey] = replays; - } - var replay = replays[replayType]; - if (replay === undefined) { - /** - * @type {Function} - */ - var Constructor = ol.render.webgl.ReplayGroup.BATCH_CONSTRUCTORS_[replayType]; - replay = new Constructor(this.tolerance_, this.maxExtent_); - replays[replayType] = replay; - } - return replay; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.ReplayGroup.prototype.isEmpty = function() { - return ol.obj.isEmpty(this.replaysByZIndex_); -}; - - -/** - * @param {ol.webgl.Context} context Context. - * @param {ol.Coordinate} center Center. - * @param {number} resolution Resolution. - * @param {number} rotation Rotation. - * @param {ol.Size} size Size. - * @param {number} pixelRatio Pixel ratio. - * @param {number} opacity Global opacity. - * @param {Object.<string, boolean>} skippedFeaturesHash Ids of features - * to skip. - */ -ol.render.webgl.ReplayGroup.prototype.replay = function(context, - center, resolution, rotation, size, pixelRatio, - opacity, skippedFeaturesHash) { - /** @type {Array.<number>} */ - var zs = Object.keys(this.replaysByZIndex_).map(Number); - zs.sort(ol.array.numberSafeCompareFunction); - - var i, ii, j, jj, replays, replay; - for (i = 0, ii = zs.length; i < ii; ++i) { - replays = this.replaysByZIndex_[zs[i].toString()]; - for (j = 0, jj = ol.render.replay.ORDER.length; j < jj; ++j) { - replay = replays[ol.render.replay.ORDER[j]]; - if (replay !== undefined) { - replay.replay(context, - center, resolution, rotation, size, pixelRatio, - opacity, skippedFeaturesHash, - undefined, false); - } - } - } -}; - - -/** - * @private - * @param {ol.webgl.Context} context Context. - * @param {ol.Coordinate} center Center. - * @param {number} resolution Resolution. - * @param {number} rotation Rotation. - * @param {ol.Size} size Size. - * @param {number} pixelRatio Pixel ratio. - * @param {number} opacity Global opacity. - * @param {Object.<string, boolean>} skippedFeaturesHash Ids of features - * to skip. - * @param {function((ol.Feature|ol.render.Feature)): T|undefined} featureCallback Feature callback. - * @param {boolean} oneByOne Draw features one-by-one for the hit-detecion. - * @param {ol.Extent=} opt_hitExtent Hit extent: Only features intersecting - * this extent are checked. - * @return {T|undefined} Callback result. - * @template T - */ -ol.render.webgl.ReplayGroup.prototype.replayHitDetection_ = function(context, - center, resolution, rotation, size, pixelRatio, opacity, - skippedFeaturesHash, featureCallback, oneByOne, opt_hitExtent) { - /** @type {Array.<number>} */ - var zs = Object.keys(this.replaysByZIndex_).map(Number); - zs.sort(function(a, b) { - return b - a; - }); - - var i, ii, j, replays, replay, result; - for (i = 0, ii = zs.length; i < ii; ++i) { - replays = this.replaysByZIndex_[zs[i].toString()]; - for (j = ol.render.replay.ORDER.length - 1; j >= 0; --j) { - replay = replays[ol.render.replay.ORDER[j]]; - if (replay !== undefined) { - result = replay.replay(context, - center, resolution, rotation, size, pixelRatio, opacity, - skippedFeaturesHash, featureCallback, oneByOne, opt_hitExtent); - if (result) { - return result; - } - } - } - } - return undefined; -}; - - -/** - * @param {ol.Coordinate} coordinate Coordinate. - * @param {ol.webgl.Context} context Context. - * @param {ol.Coordinate} center Center. - * @param {number} resolution Resolution. - * @param {number} rotation Rotation. - * @param {ol.Size} size Size. - * @param {number} pixelRatio Pixel ratio. - * @param {number} opacity Global opacity. - * @param {Object.<string, boolean>} skippedFeaturesHash Ids of features - * to skip. - * @param {function((ol.Feature|ol.render.Feature)): T|undefined} callback Feature callback. - * @return {T|undefined} Callback result. - * @template T - */ -ol.render.webgl.ReplayGroup.prototype.forEachFeatureAtCoordinate = function( - coordinate, context, center, resolution, rotation, size, pixelRatio, - opacity, skippedFeaturesHash, - callback) { - var gl = context.getGL(); - gl.bindFramebuffer( - gl.FRAMEBUFFER, context.getHitDetectionFramebuffer()); - - - /** - * @type {ol.Extent} - */ - var hitExtent; - if (this.renderBuffer_ !== undefined) { - // build an extent around the coordinate, so that only features that - // intersect this extent are checked - hitExtent = ol.extent.buffer( - ol.extent.createOrUpdateFromCoordinate(coordinate), - resolution * this.renderBuffer_); - } - - return this.replayHitDetection_(context, - coordinate, resolution, rotation, ol.render.webgl.ReplayGroup.HIT_DETECTION_SIZE_, - pixelRatio, opacity, skippedFeaturesHash, - /** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @return {?} Callback result. - */ - function(feature) { - var imageData = new Uint8Array(4); - gl.readPixels(0, 0, 1, 1, gl.RGBA, gl.UNSIGNED_BYTE, imageData); - - if (imageData[3] > 0) { - var result = callback(feature); - if (result) { - return result; - } - } - }, true, hitExtent); -}; - - -/** - * @param {ol.Coordinate} coordinate Coordinate. - * @param {ol.webgl.Context} context Context. - * @param {ol.Coordinate} center Center. - * @param {number} resolution Resolution. - * @param {number} rotation Rotation. - * @param {ol.Size} size Size. - * @param {number} pixelRatio Pixel ratio. - * @param {number} opacity Global opacity. - * @param {Object.<string, boolean>} skippedFeaturesHash Ids of features - * to skip. - * @return {boolean} Is there a feature at the given coordinate? - */ -ol.render.webgl.ReplayGroup.prototype.hasFeatureAtCoordinate = function( - coordinate, context, center, resolution, rotation, size, pixelRatio, - opacity, skippedFeaturesHash) { - var gl = context.getGL(); - gl.bindFramebuffer( - gl.FRAMEBUFFER, context.getHitDetectionFramebuffer()); - - var hasFeature = this.replayHitDetection_(context, - coordinate, resolution, rotation, ol.render.webgl.ReplayGroup.HIT_DETECTION_SIZE_, - pixelRatio, opacity, skippedFeaturesHash, - /** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @return {boolean} Is there a feature? - */ - function(feature) { - var imageData = new Uint8Array(4); - gl.readPixels(0, 0, 1, 1, gl.RGBA, gl.UNSIGNED_BYTE, imageData); - return imageData[3] > 0; - }, false); - - return hasFeature !== undefined; -}; - -/** - * @const - * @private - * @type {Array.<number>} - */ -ol.render.webgl.ReplayGroup.HIT_DETECTION_SIZE_ = [1, 1]; - -/** - * @const - * @private - * @type {Object.<ol.render.ReplayType, - * function(new: ol.render.webgl.Replay, number, - * ol.Extent)>} - */ -ol.render.webgl.ReplayGroup.BATCH_CONSTRUCTORS_ = { - 'Circle': ol.render.webgl.CircleReplay, - 'Image': ol.render.webgl.ImageReplay, - 'LineString': ol.render.webgl.LineStringReplay, - 'Polygon': ol.render.webgl.PolygonReplay, - 'Text': ol.render.webgl.TextReplay -}; - -goog.provide('ol.render.webgl.Immediate'); - -goog.require('ol'); -goog.require('ol.extent'); -goog.require('ol.geom.GeometryType'); -goog.require('ol.render.ReplayType'); -goog.require('ol.render.VectorContext'); -goog.require('ol.render.webgl.ReplayGroup'); - - -/** - * @constructor - * @extends {ol.render.VectorContext} - * @param {ol.webgl.Context} context Context. - * @param {ol.Coordinate} center Center. - * @param {number} resolution Resolution. - * @param {number} rotation Rotation. - * @param {ol.Size} size Size. - * @param {ol.Extent} extent Extent. - * @param {number} pixelRatio Pixel ratio. - * @struct - */ -ol.render.webgl.Immediate = function(context, center, resolution, rotation, size, extent, pixelRatio) { - ol.render.VectorContext.call(this); - - /** - * @private - */ - this.context_ = context; - - /** - * @private - */ - this.center_ = center; - - /** - * @private - */ - this.extent_ = extent; - - /** - * @private - */ - this.pixelRatio_ = pixelRatio; - - /** - * @private - */ - this.size_ = size; - - /** - * @private - */ - this.rotation_ = rotation; - - /** - * @private - */ - this.resolution_ = resolution; - - /** - * @private - * @type {ol.style.Image} - */ - this.imageStyle_ = null; - - /** - * @private - * @type {ol.style.Fill} - */ - this.fillStyle_ = null; - - /** - * @private - * @type {ol.style.Stroke} - */ - this.strokeStyle_ = null; - - /** - * @private - * @type {ol.style.Text} - */ - this.textStyle_ = null; - -}; -ol.inherits(ol.render.webgl.Immediate, ol.render.VectorContext); - - -/** - * @param {ol.render.webgl.ReplayGroup} replayGroup Replay group. - * @param {ol.geom.Geometry|ol.render.Feature} geometry Geometry. - * @private - */ -ol.render.webgl.Immediate.prototype.drawText_ = function(replayGroup, geometry) { - var context = this.context_; - var replay = /** @type {ol.render.webgl.TextReplay} */ ( - replayGroup.getReplay(0, ol.render.ReplayType.TEXT)); - replay.setTextStyle(this.textStyle_); - replay.drawText(geometry, null); - replay.finish(context); - // default colors - var opacity = 1; - var skippedFeatures = {}; - var featureCallback; - var oneByOne = false; - replay.replay(this.context_, this.center_, this.resolution_, this.rotation_, - this.size_, this.pixelRatio_, opacity, skippedFeatures, featureCallback, - oneByOne); - replay.getDeleteResourcesFunction(context)(); -}; - - -/** - * Set the rendering style. Note that since this is an immediate rendering API, - * any `zIndex` on the provided style will be ignored. - * - * @param {ol.style.Style} style The rendering style. - * @override - * @api - */ -ol.render.webgl.Immediate.prototype.setStyle = function(style) { - this.setFillStrokeStyle(style.getFill(), style.getStroke()); - this.setImageStyle(style.getImage()); - this.setTextStyle(style.getText()); -}; - - -/** - * Render a geometry into the canvas. Call - * {@link ol.render.webgl.Immediate#setStyle} first to set the rendering style. - * - * @param {ol.geom.Geometry|ol.render.Feature} geometry The geometry to render. - * @override - * @api - */ -ol.render.webgl.Immediate.prototype.drawGeometry = function(geometry) { - var type = geometry.getType(); - switch (type) { - case ol.geom.GeometryType.POINT: - this.drawPoint(/** @type {ol.geom.Point} */ (geometry), null); - break; - case ol.geom.GeometryType.LINE_STRING: - this.drawLineString(/** @type {ol.geom.LineString} */ (geometry), null); - break; - case ol.geom.GeometryType.POLYGON: - this.drawPolygon(/** @type {ol.geom.Polygon} */ (geometry), null); - break; - case ol.geom.GeometryType.MULTI_POINT: - this.drawMultiPoint(/** @type {ol.geom.MultiPoint} */ (geometry), null); - break; - case ol.geom.GeometryType.MULTI_LINE_STRING: - this.drawMultiLineString(/** @type {ol.geom.MultiLineString} */ (geometry), null); - break; - case ol.geom.GeometryType.MULTI_POLYGON: - this.drawMultiPolygon(/** @type {ol.geom.MultiPolygon} */ (geometry), null); - break; - case ol.geom.GeometryType.GEOMETRY_COLLECTION: - this.drawGeometryCollection(/** @type {ol.geom.GeometryCollection} */ (geometry), null); - break; - case ol.geom.GeometryType.CIRCLE: - this.drawCircle(/** @type {ol.geom.Circle} */ (geometry), null); - break; - default: - // pass - } -}; - - -/** - * @inheritDoc - * @api - */ -ol.render.webgl.Immediate.prototype.drawFeature = function(feature, style) { - var geometry = style.getGeometryFunction()(feature); - if (!geometry || - !ol.extent.intersects(this.extent_, geometry.getExtent())) { - return; - } - this.setStyle(style); - this.drawGeometry(geometry); -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.Immediate.prototype.drawGeometryCollection = function(geometry, data) { - var geometries = geometry.getGeometriesArray(); - var i, ii; - for (i = 0, ii = geometries.length; i < ii; ++i) { - this.drawGeometry(geometries[i]); - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.Immediate.prototype.drawPoint = function(geometry, data) { - var context = this.context_; - var replayGroup = new ol.render.webgl.ReplayGroup(1, this.extent_); - var replay = /** @type {ol.render.webgl.ImageReplay} */ ( - replayGroup.getReplay(0, ol.render.ReplayType.IMAGE)); - replay.setImageStyle(this.imageStyle_); - replay.drawPoint(geometry, data); - replay.finish(context); - // default colors - var opacity = 1; - var skippedFeatures = {}; - var featureCallback; - var oneByOne = false; - replay.replay(this.context_, this.center_, this.resolution_, this.rotation_, - this.size_, this.pixelRatio_, opacity, skippedFeatures, featureCallback, - oneByOne); - replay.getDeleteResourcesFunction(context)(); - - if (this.textStyle_) { - this.drawText_(replayGroup, geometry); - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.Immediate.prototype.drawMultiPoint = function(geometry, data) { - var context = this.context_; - var replayGroup = new ol.render.webgl.ReplayGroup(1, this.extent_); - var replay = /** @type {ol.render.webgl.ImageReplay} */ ( - replayGroup.getReplay(0, ol.render.ReplayType.IMAGE)); - replay.setImageStyle(this.imageStyle_); - replay.drawMultiPoint(geometry, data); - replay.finish(context); - var opacity = 1; - var skippedFeatures = {}; - var featureCallback; - var oneByOne = false; - replay.replay(this.context_, this.center_, this.resolution_, this.rotation_, - this.size_, this.pixelRatio_, opacity, skippedFeatures, featureCallback, - oneByOne); - replay.getDeleteResourcesFunction(context)(); - - if (this.textStyle_) { - this.drawText_(replayGroup, geometry); - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.Immediate.prototype.drawLineString = function(geometry, data) { - var context = this.context_; - var replayGroup = new ol.render.webgl.ReplayGroup(1, this.extent_); - var replay = /** @type {ol.render.webgl.LineStringReplay} */ ( - replayGroup.getReplay(0, ol.render.ReplayType.LINE_STRING)); - replay.setFillStrokeStyle(null, this.strokeStyle_); - replay.drawLineString(geometry, data); - replay.finish(context); - var opacity = 1; - var skippedFeatures = {}; - var featureCallback; - var oneByOne = false; - replay.replay(this.context_, this.center_, this.resolution_, this.rotation_, - this.size_, this.pixelRatio_, opacity, skippedFeatures, featureCallback, - oneByOne); - replay.getDeleteResourcesFunction(context)(); - - if (this.textStyle_) { - this.drawText_(replayGroup, geometry); - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.Immediate.prototype.drawMultiLineString = function(geometry, data) { - var context = this.context_; - var replayGroup = new ol.render.webgl.ReplayGroup(1, this.extent_); - var replay = /** @type {ol.render.webgl.LineStringReplay} */ ( - replayGroup.getReplay(0, ol.render.ReplayType.LINE_STRING)); - replay.setFillStrokeStyle(null, this.strokeStyle_); - replay.drawMultiLineString(geometry, data); - replay.finish(context); - var opacity = 1; - var skippedFeatures = {}; - var featureCallback; - var oneByOne = false; - replay.replay(this.context_, this.center_, this.resolution_, this.rotation_, - this.size_, this.pixelRatio_, opacity, skippedFeatures, featureCallback, - oneByOne); - replay.getDeleteResourcesFunction(context)(); - - if (this.textStyle_) { - this.drawText_(replayGroup, geometry); - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.Immediate.prototype.drawPolygon = function(geometry, data) { - var context = this.context_; - var replayGroup = new ol.render.webgl.ReplayGroup(1, this.extent_); - var replay = /** @type {ol.render.webgl.PolygonReplay} */ ( - replayGroup.getReplay(0, ol.render.ReplayType.POLYGON)); - replay.setFillStrokeStyle(this.fillStyle_, this.strokeStyle_); - replay.drawPolygon(geometry, data); - replay.finish(context); - var opacity = 1; - var skippedFeatures = {}; - var featureCallback; - var oneByOne = false; - replay.replay(this.context_, this.center_, this.resolution_, this.rotation_, - this.size_, this.pixelRatio_, opacity, skippedFeatures, featureCallback, - oneByOne); - replay.getDeleteResourcesFunction(context)(); - - if (this.textStyle_) { - this.drawText_(replayGroup, geometry); - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.Immediate.prototype.drawMultiPolygon = function(geometry, data) { - var context = this.context_; - var replayGroup = new ol.render.webgl.ReplayGroup(1, this.extent_); - var replay = /** @type {ol.render.webgl.PolygonReplay} */ ( - replayGroup.getReplay(0, ol.render.ReplayType.POLYGON)); - replay.setFillStrokeStyle(this.fillStyle_, this.strokeStyle_); - replay.drawMultiPolygon(geometry, data); - replay.finish(context); - var opacity = 1; - var skippedFeatures = {}; - var featureCallback; - var oneByOne = false; - replay.replay(this.context_, this.center_, this.resolution_, this.rotation_, - this.size_, this.pixelRatio_, opacity, skippedFeatures, featureCallback, - oneByOne); - replay.getDeleteResourcesFunction(context)(); - - if (this.textStyle_) { - this.drawText_(replayGroup, geometry); - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.Immediate.prototype.drawCircle = function(geometry, data) { - var context = this.context_; - var replayGroup = new ol.render.webgl.ReplayGroup(1, this.extent_); - var replay = /** @type {ol.render.webgl.CircleReplay} */ ( - replayGroup.getReplay(0, ol.render.ReplayType.CIRCLE)); - replay.setFillStrokeStyle(this.fillStyle_, this.strokeStyle_); - replay.drawCircle(geometry, data); - replay.finish(context); - var opacity = 1; - var skippedFeatures = {}; - var featureCallback; - var oneByOne = false; - replay.replay(this.context_, this.center_, this.resolution_, this.rotation_, - this.size_, this.pixelRatio_, opacity, skippedFeatures, featureCallback, - oneByOne); - replay.getDeleteResourcesFunction(context)(); - - if (this.textStyle_) { - this.drawText_(replayGroup, geometry); - } -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.Immediate.prototype.setImageStyle = function(imageStyle) { - this.imageStyle_ = imageStyle; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.Immediate.prototype.setFillStrokeStyle = function(fillStyle, strokeStyle) { - this.fillStyle_ = fillStyle; - this.strokeStyle_ = strokeStyle; -}; - - -/** - * @inheritDoc - */ -ol.render.webgl.Immediate.prototype.setTextStyle = function(textStyle) { - this.textStyle_ = textStyle; -}; - -// This file is automatically generated, do not edit -goog.provide('ol.renderer.webgl.defaultmapshader'); - -goog.require('ol'); -goog.require('ol.webgl.Fragment'); -goog.require('ol.webgl.Vertex'); - - -ol.renderer.webgl.defaultmapshader.fragment = new ol.webgl.Fragment(ol.DEBUG_WEBGL ? - 'precision mediump float;\nvarying vec2 v_texCoord;\n\n\nuniform float u_opacity;\nuniform sampler2D u_texture;\n\nvoid main(void) {\n vec4 texColor = texture2D(u_texture, v_texCoord);\n gl_FragColor.rgb = texColor.rgb;\n gl_FragColor.a = texColor.a * u_opacity;\n}\n' : - 'precision mediump float;varying vec2 a;uniform float f;uniform sampler2D g;void main(void){vec4 texColor=texture2D(g,a);gl_FragColor.rgb=texColor.rgb;gl_FragColor.a=texColor.a*f;}'); - -ol.renderer.webgl.defaultmapshader.vertex = new ol.webgl.Vertex(ol.DEBUG_WEBGL ? - 'varying vec2 v_texCoord;\n\n\nattribute vec2 a_position;\nattribute vec2 a_texCoord;\n\nuniform mat4 u_texCoordMatrix;\nuniform mat4 u_projectionMatrix;\n\nvoid main(void) {\n gl_Position = u_projectionMatrix * vec4(a_position, 0., 1.);\n v_texCoord = (u_texCoordMatrix * vec4(a_texCoord, 0., 1.)).st;\n}\n\n\n' : - 'varying vec2 a;attribute vec2 b;attribute vec2 c;uniform mat4 d;uniform mat4 e;void main(void){gl_Position=e*vec4(b,0.,1.);a=(d*vec4(c,0.,1.)).st;}'); - -// This file is automatically generated, do not edit -goog.provide('ol.renderer.webgl.defaultmapshader.Locations'); - -goog.require('ol'); - - -/** - * @constructor - * @param {WebGLRenderingContext} gl GL. - * @param {WebGLProgram} program Program. - * @struct - */ -ol.renderer.webgl.defaultmapshader.Locations = function(gl, program) { - - /** - * @type {WebGLUniformLocation} - */ - this.u_texCoordMatrix = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_texCoordMatrix' : 'd'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_projectionMatrix = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_projectionMatrix' : 'e'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_opacity = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_opacity' : 'f'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_texture = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_texture' : 'g'); - - /** - * @type {number} - */ - this.a_position = gl.getAttribLocation( - program, ol.DEBUG_WEBGL ? 'a_position' : 'b'); - - /** - * @type {number} - */ - this.a_texCoord = gl.getAttribLocation( - program, ol.DEBUG_WEBGL ? 'a_texCoord' : 'c'); -}; - -goog.provide('ol.renderer.webgl.Layer'); - -goog.require('ol'); -goog.require('ol.render.Event'); -goog.require('ol.render.EventType'); -goog.require('ol.render.webgl.Immediate'); -goog.require('ol.renderer.Layer'); -goog.require('ol.renderer.webgl.defaultmapshader'); -goog.require('ol.renderer.webgl.defaultmapshader.Locations'); -goog.require('ol.transform'); -goog.require('ol.vec.Mat4'); -goog.require('ol.webgl'); -goog.require('ol.webgl.Buffer'); -goog.require('ol.webgl.Context'); - - -/** - * @constructor - * @abstract - * @extends {ol.renderer.Layer} - * @param {ol.renderer.webgl.Map} mapRenderer Map renderer. - * @param {ol.layer.Layer} layer Layer. - */ -ol.renderer.webgl.Layer = function(mapRenderer, layer) { - - ol.renderer.Layer.call(this, layer); - - /** - * @protected - * @type {ol.renderer.webgl.Map} - */ - this.mapRenderer = mapRenderer; - - /** - * @private - * @type {ol.webgl.Buffer} - */ - this.arrayBuffer_ = new ol.webgl.Buffer([ - -1, -1, 0, 0, - 1, -1, 1, 0, - -1, 1, 0, 1, - 1, 1, 1, 1 - ]); - - /** - * @protected - * @type {WebGLTexture} - */ - this.texture = null; - - /** - * @protected - * @type {WebGLFramebuffer} - */ - this.framebuffer = null; - - /** - * @protected - * @type {number|undefined} - */ - this.framebufferDimension = undefined; - - /** - * @protected - * @type {ol.Transform} - */ - this.texCoordMatrix = ol.transform.create(); - - /** - * @protected - * @type {ol.Transform} - */ - this.projectionMatrix = ol.transform.create(); - - /** - * @type {Array.<number>} - * @private - */ - this.tmpMat4_ = ol.vec.Mat4.create(); - - /** - * @private - * @type {ol.renderer.webgl.defaultmapshader.Locations} - */ - this.defaultLocations_ = null; - -}; -ol.inherits(ol.renderer.webgl.Layer, ol.renderer.Layer); - - -/** - * @param {olx.FrameState} frameState Frame state. - * @param {number} framebufferDimension Framebuffer dimension. - * @protected - */ -ol.renderer.webgl.Layer.prototype.bindFramebuffer = function(frameState, framebufferDimension) { - - var gl = this.mapRenderer.getGL(); - - if (this.framebufferDimension === undefined || - this.framebufferDimension != framebufferDimension) { - /** - * @param {WebGLRenderingContext} gl GL. - * @param {WebGLFramebuffer} framebuffer Framebuffer. - * @param {WebGLTexture} texture Texture. - */ - var postRenderFunction = function(gl, framebuffer, texture) { - if (!gl.isContextLost()) { - gl.deleteFramebuffer(framebuffer); - gl.deleteTexture(texture); - } - }.bind(null, gl, this.framebuffer, this.texture); - - frameState.postRenderFunctions.push( - /** @type {ol.PostRenderFunction} */ (postRenderFunction) - ); - - var texture = ol.webgl.Context.createEmptyTexture( - gl, framebufferDimension, framebufferDimension); - - var framebuffer = gl.createFramebuffer(); - gl.bindFramebuffer(ol.webgl.FRAMEBUFFER, framebuffer); - gl.framebufferTexture2D(ol.webgl.FRAMEBUFFER, - ol.webgl.COLOR_ATTACHMENT0, ol.webgl.TEXTURE_2D, texture, 0); - - this.texture = texture; - this.framebuffer = framebuffer; - this.framebufferDimension = framebufferDimension; - - } else { - gl.bindFramebuffer(ol.webgl.FRAMEBUFFER, this.framebuffer); - } - -}; - - -/** - * @param {olx.FrameState} frameState Frame state. - * @param {ol.LayerState} layerState Layer state. - * @param {ol.webgl.Context} context Context. - */ -ol.renderer.webgl.Layer.prototype.composeFrame = function(frameState, layerState, context) { - - this.dispatchComposeEvent_( - ol.render.EventType.PRECOMPOSE, context, frameState); - - context.bindBuffer(ol.webgl.ARRAY_BUFFER, this.arrayBuffer_); - - var gl = context.getGL(); - - var fragmentShader = ol.renderer.webgl.defaultmapshader.fragment; - var vertexShader = ol.renderer.webgl.defaultmapshader.vertex; - - var program = context.getProgram(fragmentShader, vertexShader); - - var locations; - if (!this.defaultLocations_) { - locations = new ol.renderer.webgl.defaultmapshader.Locations(gl, program); - this.defaultLocations_ = locations; - } else { - locations = this.defaultLocations_; - } - - if (context.useProgram(program)) { - gl.enableVertexAttribArray(locations.a_position); - gl.vertexAttribPointer( - locations.a_position, 2, ol.webgl.FLOAT, false, 16, 0); - gl.enableVertexAttribArray(locations.a_texCoord); - gl.vertexAttribPointer( - locations.a_texCoord, 2, ol.webgl.FLOAT, false, 16, 8); - gl.uniform1i(locations.u_texture, 0); - } - - gl.uniformMatrix4fv(locations.u_texCoordMatrix, false, - ol.vec.Mat4.fromTransform(this.tmpMat4_, this.getTexCoordMatrix())); - gl.uniformMatrix4fv(locations.u_projectionMatrix, false, - ol.vec.Mat4.fromTransform(this.tmpMat4_, this.getProjectionMatrix())); - gl.uniform1f(locations.u_opacity, layerState.opacity); - gl.bindTexture(ol.webgl.TEXTURE_2D, this.getTexture()); - gl.drawArrays(ol.webgl.TRIANGLE_STRIP, 0, 4); - - this.dispatchComposeEvent_( - ol.render.EventType.POSTCOMPOSE, context, frameState); - -}; - - -/** - * @param {ol.render.EventType} type Event type. - * @param {ol.webgl.Context} context WebGL context. - * @param {olx.FrameState} frameState Frame state. - * @private - */ -ol.renderer.webgl.Layer.prototype.dispatchComposeEvent_ = function(type, context, frameState) { - var layer = this.getLayer(); - if (layer.hasListener(type)) { - var viewState = frameState.viewState; - var resolution = viewState.resolution; - var pixelRatio = frameState.pixelRatio; - var extent = frameState.extent; - var center = viewState.center; - var rotation = viewState.rotation; - var size = frameState.size; - - var render = new ol.render.webgl.Immediate( - context, center, resolution, rotation, size, extent, pixelRatio); - var composeEvent = new ol.render.Event( - type, render, frameState, null, context); - layer.dispatchEvent(composeEvent); - } -}; - - -/** - * @return {!ol.Transform} Matrix. - */ -ol.renderer.webgl.Layer.prototype.getTexCoordMatrix = function() { - return this.texCoordMatrix; -}; - - -/** - * @return {WebGLTexture} Texture. - */ -ol.renderer.webgl.Layer.prototype.getTexture = function() { - return this.texture; -}; - - -/** - * @return {!ol.Transform} Matrix. - */ -ol.renderer.webgl.Layer.prototype.getProjectionMatrix = function() { - return this.projectionMatrix; -}; - - -/** - * Handle webglcontextlost. - */ -ol.renderer.webgl.Layer.prototype.handleWebGLContextLost = function() { - this.texture = null; - this.framebuffer = null; - this.framebufferDimension = undefined; -}; - - -/** - * @abstract - * @param {olx.FrameState} frameState Frame state. - * @param {ol.LayerState} layerState Layer state. - * @param {ol.webgl.Context} context Context. - * @return {boolean} whether composeFrame should be called. - */ -ol.renderer.webgl.Layer.prototype.prepareFrame = function(frameState, layerState, context) {}; - - -/** - * @abstract - * @param {ol.Pixel} pixel Pixel. - * @param {olx.FrameState} frameState FrameState. - * @param {function(this: S, ol.layer.Layer, (Uint8ClampedArray|Uint8Array)): T} callback Layer - * callback. - * @param {S} thisArg Value to use as `this` when executing `callback`. - * @return {T|undefined} Callback result. - * @template S,T,U - */ -ol.renderer.webgl.Layer.prototype.forEachLayerAtPixel = function(pixel, frameState, callback, thisArg) {}; - -goog.provide('ol.reproj'); - -goog.require('ol.dom'); -goog.require('ol.extent'); -goog.require('ol.math'); -goog.require('ol.proj'); - - -/** - * Calculates ideal resolution to use from the source in order to achieve - * pixel mapping as close as possible to 1:1 during reprojection. - * The resolution is calculated regardless of what resolutions - * are actually available in the dataset (TileGrid, Image, ...). - * - * @param {ol.proj.Projection} sourceProj Source projection. - * @param {ol.proj.Projection} targetProj Target projection. - * @param {ol.Coordinate} targetCenter Target center. - * @param {number} targetResolution Target resolution. - * @return {number} The best resolution to use. Can be +-Infinity, NaN or 0. - */ -ol.reproj.calculateSourceResolution = function(sourceProj, targetProj, - targetCenter, targetResolution) { - - var sourceCenter = ol.proj.transform(targetCenter, targetProj, sourceProj); - - // calculate the ideal resolution of the source data - var sourceResolution = - ol.proj.getPointResolution(targetProj, targetResolution, targetCenter); - - var targetMetersPerUnit = targetProj.getMetersPerUnit(); - if (targetMetersPerUnit !== undefined) { - sourceResolution *= targetMetersPerUnit; - } - var sourceMetersPerUnit = sourceProj.getMetersPerUnit(); - if (sourceMetersPerUnit !== undefined) { - sourceResolution /= sourceMetersPerUnit; - } - - // Based on the projection properties, the point resolution at the specified - // coordinates may be slightly different. We need to reverse-compensate this - // in order to achieve optimal results. - - var sourceExtent = sourceProj.getExtent(); - if (!sourceExtent || ol.extent.containsCoordinate(sourceExtent, sourceCenter)) { - var compensationFactor = - ol.proj.getPointResolution(sourceProj, sourceResolution, sourceCenter) / - sourceResolution; - if (isFinite(compensationFactor) && compensationFactor > 0) { - sourceResolution /= compensationFactor; - } - } - - return sourceResolution; -}; - - -/** - * Enlarge the clipping triangle point by 1 pixel to ensure the edges overlap - * in order to mask gaps caused by antialiasing. - * - * @param {number} centroidX Centroid of the triangle (x coordinate in pixels). - * @param {number} centroidY Centroid of the triangle (y coordinate in pixels). - * @param {number} x X coordinate of the point (in pixels). - * @param {number} y Y coordinate of the point (in pixels). - * @return {ol.Coordinate} New point 1 px farther from the centroid. - * @private - */ -ol.reproj.enlargeClipPoint_ = function(centroidX, centroidY, x, y) { - var dX = x - centroidX, dY = y - centroidY; - var distance = Math.sqrt(dX * dX + dY * dY); - return [Math.round(x + dX / distance), Math.round(y + dY / distance)]; -}; - - -/** - * Renders the source data into new canvas based on the triangulation. - * - * @param {number} width Width of the canvas. - * @param {number} height Height of the canvas. - * @param {number} pixelRatio Pixel ratio. - * @param {number} sourceResolution Source resolution. - * @param {ol.Extent} sourceExtent Extent of the data source. - * @param {number} targetResolution Target resolution. - * @param {ol.Extent} targetExtent Target extent. - * @param {ol.reproj.Triangulation} triangulation Calculated triangulation. - * @param {Array.<{extent: ol.Extent, - * image: (HTMLCanvasElement|Image|HTMLVideoElement)}>} sources - * Array of sources. - * @param {number} gutter Gutter of the sources. - * @param {boolean=} opt_renderEdges Render reprojection edges. - * @return {HTMLCanvasElement} Canvas with reprojected data. - */ -ol.reproj.render = function(width, height, pixelRatio, - sourceResolution, sourceExtent, targetResolution, targetExtent, - triangulation, sources, gutter, opt_renderEdges) { - - var context = ol.dom.createCanvasContext2D(Math.round(pixelRatio * width), - Math.round(pixelRatio * height)); - - if (sources.length === 0) { - return context.canvas; - } - - context.scale(pixelRatio, pixelRatio); - - var sourceDataExtent = ol.extent.createEmpty(); - sources.forEach(function(src, i, arr) { - ol.extent.extend(sourceDataExtent, src.extent); - }); - - var canvasWidthInUnits = ol.extent.getWidth(sourceDataExtent); - var canvasHeightInUnits = ol.extent.getHeight(sourceDataExtent); - var stitchContext = ol.dom.createCanvasContext2D( - Math.round(pixelRatio * canvasWidthInUnits / sourceResolution), - Math.round(pixelRatio * canvasHeightInUnits / sourceResolution)); - - var stitchScale = pixelRatio / sourceResolution; - - sources.forEach(function(src, i, arr) { - var xPos = src.extent[0] - sourceDataExtent[0]; - var yPos = -(src.extent[3] - sourceDataExtent[3]); - var srcWidth = ol.extent.getWidth(src.extent); - var srcHeight = ol.extent.getHeight(src.extent); - - stitchContext.drawImage( - src.image, - gutter, gutter, - src.image.width - 2 * gutter, src.image.height - 2 * gutter, - xPos * stitchScale, yPos * stitchScale, - srcWidth * stitchScale, srcHeight * stitchScale); - }); - - var targetTopLeft = ol.extent.getTopLeft(targetExtent); - - triangulation.getTriangles().forEach(function(triangle, i, arr) { - /* Calculate affine transform (src -> dst) - * Resulting matrix can be used to transform coordinate - * from `sourceProjection` to destination pixels. - * - * To optimize number of context calls and increase numerical stability, - * we also do the following operations: - * trans(-topLeftExtentCorner), scale(1 / targetResolution), scale(1, -1) - * here before solving the linear system so [ui, vi] are pixel coordinates. - * - * Src points: xi, yi - * Dst points: ui, vi - * Affine coefficients: aij - * - * | x0 y0 1 0 0 0 | |a00| |u0| - * | x1 y1 1 0 0 0 | |a01| |u1| - * | x2 y2 1 0 0 0 | x |a02| = |u2| - * | 0 0 0 x0 y0 1 | |a10| |v0| - * | 0 0 0 x1 y1 1 | |a11| |v1| - * | 0 0 0 x2 y2 1 | |a12| |v2| - */ - var source = triangle.source, target = triangle.target; - var x0 = source[0][0], y0 = source[0][1], - x1 = source[1][0], y1 = source[1][1], - x2 = source[2][0], y2 = source[2][1]; - var u0 = (target[0][0] - targetTopLeft[0]) / targetResolution, - v0 = -(target[0][1] - targetTopLeft[1]) / targetResolution; - var u1 = (target[1][0] - targetTopLeft[0]) / targetResolution, - v1 = -(target[1][1] - targetTopLeft[1]) / targetResolution; - var u2 = (target[2][0] - targetTopLeft[0]) / targetResolution, - v2 = -(target[2][1] - targetTopLeft[1]) / targetResolution; - - // Shift all the source points to improve numerical stability - // of all the subsequent calculations. The [x0, y0] is used here. - // This is also used to simplify the linear system. - var sourceNumericalShiftX = x0, sourceNumericalShiftY = y0; - x0 = 0; - y0 = 0; - x1 -= sourceNumericalShiftX; - y1 -= sourceNumericalShiftY; - x2 -= sourceNumericalShiftX; - y2 -= sourceNumericalShiftY; - - var augmentedMatrix = [ - [x1, y1, 0, 0, u1 - u0], - [x2, y2, 0, 0, u2 - u0], - [0, 0, x1, y1, v1 - v0], - [0, 0, x2, y2, v2 - v0] - ]; - var affineCoefs = ol.math.solveLinearSystem(augmentedMatrix); - if (!affineCoefs) { - return; - } - - context.save(); - context.beginPath(); - var centroidX = (u0 + u1 + u2) / 3, centroidY = (v0 + v1 + v2) / 3; - var p0 = ol.reproj.enlargeClipPoint_(centroidX, centroidY, u0, v0); - var p1 = ol.reproj.enlargeClipPoint_(centroidX, centroidY, u1, v1); - var p2 = ol.reproj.enlargeClipPoint_(centroidX, centroidY, u2, v2); - - context.moveTo(p1[0], p1[1]); - context.lineTo(p0[0], p0[1]); - context.lineTo(p2[0], p2[1]); - context.clip(); - - context.transform( - affineCoefs[0], affineCoefs[2], affineCoefs[1], affineCoefs[3], u0, v0); - - context.translate(sourceDataExtent[0] - sourceNumericalShiftX, - sourceDataExtent[3] - sourceNumericalShiftY); - - context.scale(sourceResolution / pixelRatio, - -sourceResolution / pixelRatio); - - context.drawImage(stitchContext.canvas, 0, 0); - context.restore(); - }); - - if (opt_renderEdges) { - context.save(); - - context.strokeStyle = 'black'; - context.lineWidth = 1; - - triangulation.getTriangles().forEach(function(triangle, i, arr) { - var target = triangle.target; - var u0 = (target[0][0] - targetTopLeft[0]) / targetResolution, - v0 = -(target[0][1] - targetTopLeft[1]) / targetResolution; - var u1 = (target[1][0] - targetTopLeft[0]) / targetResolution, - v1 = -(target[1][1] - targetTopLeft[1]) / targetResolution; - var u2 = (target[2][0] - targetTopLeft[0]) / targetResolution, - v2 = -(target[2][1] - targetTopLeft[1]) / targetResolution; - - context.beginPath(); - context.moveTo(u1, v1); - context.lineTo(u0, v0); - context.lineTo(u2, v2); - context.closePath(); - context.stroke(); - }); - - context.restore(); - } - return context.canvas; -}; - -goog.provide('ol.reproj.Triangulation'); - -goog.require('ol'); -goog.require('ol.extent'); -goog.require('ol.math'); -goog.require('ol.proj'); - - -/** - * @classdesc - * Class containing triangulation of the given target extent. - * Used for determining source data and the reprojection itself. - * - * @param {ol.proj.Projection} sourceProj Source projection. - * @param {ol.proj.Projection} targetProj Target projection. - * @param {ol.Extent} targetExtent Target extent to triangulate. - * @param {ol.Extent} maxSourceExtent Maximal source extent that can be used. - * @param {number} errorThreshold Acceptable error (in source units). - * @constructor - */ -ol.reproj.Triangulation = function(sourceProj, targetProj, targetExtent, - maxSourceExtent, errorThreshold) { - - /** - * @type {ol.proj.Projection} - * @private - */ - this.sourceProj_ = sourceProj; - - /** - * @type {ol.proj.Projection} - * @private - */ - this.targetProj_ = targetProj; - - /** @type {!Object.<string, ol.Coordinate>} */ - var transformInvCache = {}; - var transformInv = ol.proj.getTransform(this.targetProj_, this.sourceProj_); - - /** - * @param {ol.Coordinate} c A coordinate. - * @return {ol.Coordinate} Transformed coordinate. - * @private - */ - this.transformInv_ = function(c) { - var key = c[0] + '/' + c[1]; - if (!transformInvCache[key]) { - transformInvCache[key] = transformInv(c); - } - return transformInvCache[key]; - }; - - /** - * @type {ol.Extent} - * @private - */ - this.maxSourceExtent_ = maxSourceExtent; - - /** - * @type {number} - * @private - */ - this.errorThresholdSquared_ = errorThreshold * errorThreshold; - - /** - * @type {Array.<ol.ReprojTriangle>} - * @private - */ - this.triangles_ = []; - - /** - * Indicates that the triangulation crosses edge of the source projection. - * @type {boolean} - * @private - */ - this.wrapsXInSource_ = false; - - /** - * @type {boolean} - * @private - */ - this.canWrapXInSource_ = this.sourceProj_.canWrapX() && - !!maxSourceExtent && - !!this.sourceProj_.getExtent() && - (ol.extent.getWidth(maxSourceExtent) == - ol.extent.getWidth(this.sourceProj_.getExtent())); - - /** - * @type {?number} - * @private - */ - this.sourceWorldWidth_ = this.sourceProj_.getExtent() ? - ol.extent.getWidth(this.sourceProj_.getExtent()) : null; - - /** - * @type {?number} - * @private - */ - this.targetWorldWidth_ = this.targetProj_.getExtent() ? - ol.extent.getWidth(this.targetProj_.getExtent()) : null; - - var destinationTopLeft = ol.extent.getTopLeft(targetExtent); - var destinationTopRight = ol.extent.getTopRight(targetExtent); - var destinationBottomRight = ol.extent.getBottomRight(targetExtent); - var destinationBottomLeft = ol.extent.getBottomLeft(targetExtent); - var sourceTopLeft = this.transformInv_(destinationTopLeft); - var sourceTopRight = this.transformInv_(destinationTopRight); - var sourceBottomRight = this.transformInv_(destinationBottomRight); - var sourceBottomLeft = this.transformInv_(destinationBottomLeft); - - this.addQuad_( - destinationTopLeft, destinationTopRight, - destinationBottomRight, destinationBottomLeft, - sourceTopLeft, sourceTopRight, sourceBottomRight, sourceBottomLeft, - ol.RASTER_REPROJECTION_MAX_SUBDIVISION); - - if (this.wrapsXInSource_) { - var leftBound = Infinity; - this.triangles_.forEach(function(triangle, i, arr) { - leftBound = Math.min(leftBound, - triangle.source[0][0], triangle.source[1][0], triangle.source[2][0]); - }); - - // Shift triangles to be as close to `leftBound` as possible - // (if the distance is more than `worldWidth / 2` it can be closer. - this.triangles_.forEach(function(triangle) { - if (Math.max(triangle.source[0][0], triangle.source[1][0], - triangle.source[2][0]) - leftBound > this.sourceWorldWidth_ / 2) { - var newTriangle = [[triangle.source[0][0], triangle.source[0][1]], - [triangle.source[1][0], triangle.source[1][1]], - [triangle.source[2][0], triangle.source[2][1]]]; - if ((newTriangle[0][0] - leftBound) > this.sourceWorldWidth_ / 2) { - newTriangle[0][0] -= this.sourceWorldWidth_; - } - if ((newTriangle[1][0] - leftBound) > this.sourceWorldWidth_ / 2) { - newTriangle[1][0] -= this.sourceWorldWidth_; - } - if ((newTriangle[2][0] - leftBound) > this.sourceWorldWidth_ / 2) { - newTriangle[2][0] -= this.sourceWorldWidth_; - } - - // Rarely (if the extent contains both the dateline and prime meridian) - // the shift can in turn break some triangles. - // Detect this here and don't shift in such cases. - var minX = Math.min( - newTriangle[0][0], newTriangle[1][0], newTriangle[2][0]); - var maxX = Math.max( - newTriangle[0][0], newTriangle[1][0], newTriangle[2][0]); - if ((maxX - minX) < this.sourceWorldWidth_ / 2) { - triangle.source = newTriangle; - } - } - }, this); - } - - transformInvCache = {}; -}; - - -/** - * Adds triangle to the triangulation. - * @param {ol.Coordinate} a The target a coordinate. - * @param {ol.Coordinate} b The target b coordinate. - * @param {ol.Coordinate} c The target c coordinate. - * @param {ol.Coordinate} aSrc The source a coordinate. - * @param {ol.Coordinate} bSrc The source b coordinate. - * @param {ol.Coordinate} cSrc The source c coordinate. - * @private - */ -ol.reproj.Triangulation.prototype.addTriangle_ = function(a, b, c, - aSrc, bSrc, cSrc) { - this.triangles_.push({ - source: [aSrc, bSrc, cSrc], - target: [a, b, c] - }); -}; - - -/** - * Adds quad (points in clock-wise order) to the triangulation - * (and reprojects the vertices) if valid. - * Performs quad subdivision if needed to increase precision. - * - * @param {ol.Coordinate} a The target a coordinate. - * @param {ol.Coordinate} b The target b coordinate. - * @param {ol.Coordinate} c The target c coordinate. - * @param {ol.Coordinate} d The target d coordinate. - * @param {ol.Coordinate} aSrc The source a coordinate. - * @param {ol.Coordinate} bSrc The source b coordinate. - * @param {ol.Coordinate} cSrc The source c coordinate. - * @param {ol.Coordinate} dSrc The source d coordinate. - * @param {number} maxSubdivision Maximal allowed subdivision of the quad. - * @private - */ -ol.reproj.Triangulation.prototype.addQuad_ = function(a, b, c, d, - aSrc, bSrc, cSrc, dSrc, maxSubdivision) { - - var sourceQuadExtent = ol.extent.boundingExtent([aSrc, bSrc, cSrc, dSrc]); - var sourceCoverageX = this.sourceWorldWidth_ ? - ol.extent.getWidth(sourceQuadExtent) / this.sourceWorldWidth_ : null; - var sourceWorldWidth = /** @type {number} */ (this.sourceWorldWidth_); - - // when the quad is wrapped in the source projection - // it covers most of the projection extent, but not fully - var wrapsX = this.sourceProj_.canWrapX() && - sourceCoverageX > 0.5 && sourceCoverageX < 1; - - var needsSubdivision = false; - - if (maxSubdivision > 0) { - if (this.targetProj_.isGlobal() && this.targetWorldWidth_) { - var targetQuadExtent = ol.extent.boundingExtent([a, b, c, d]); - var targetCoverageX = - ol.extent.getWidth(targetQuadExtent) / this.targetWorldWidth_; - needsSubdivision |= - targetCoverageX > ol.RASTER_REPROJECTION_MAX_TRIANGLE_WIDTH; - } - if (!wrapsX && this.sourceProj_.isGlobal() && sourceCoverageX) { - needsSubdivision |= - sourceCoverageX > ol.RASTER_REPROJECTION_MAX_TRIANGLE_WIDTH; - } - } - - if (!needsSubdivision && this.maxSourceExtent_) { - if (!ol.extent.intersects(sourceQuadExtent, this.maxSourceExtent_)) { - // whole quad outside source projection extent -> ignore - return; - } - } - - if (!needsSubdivision) { - if (!isFinite(aSrc[0]) || !isFinite(aSrc[1]) || - !isFinite(bSrc[0]) || !isFinite(bSrc[1]) || - !isFinite(cSrc[0]) || !isFinite(cSrc[1]) || - !isFinite(dSrc[0]) || !isFinite(dSrc[1])) { - if (maxSubdivision > 0) { - needsSubdivision = true; - } else { - return; - } - } - } - - if (maxSubdivision > 0) { - if (!needsSubdivision) { - var center = [(a[0] + c[0]) / 2, (a[1] + c[1]) / 2]; - var centerSrc = this.transformInv_(center); - - var dx; - if (wrapsX) { - var centerSrcEstimX = - (ol.math.modulo(aSrc[0], sourceWorldWidth) + - ol.math.modulo(cSrc[0], sourceWorldWidth)) / 2; - dx = centerSrcEstimX - - ol.math.modulo(centerSrc[0], sourceWorldWidth); - } else { - dx = (aSrc[0] + cSrc[0]) / 2 - centerSrc[0]; - } - var dy = (aSrc[1] + cSrc[1]) / 2 - centerSrc[1]; - var centerSrcErrorSquared = dx * dx + dy * dy; - needsSubdivision = centerSrcErrorSquared > this.errorThresholdSquared_; - } - if (needsSubdivision) { - if (Math.abs(a[0] - c[0]) <= Math.abs(a[1] - c[1])) { - // split horizontally (top & bottom) - var bc = [(b[0] + c[0]) / 2, (b[1] + c[1]) / 2]; - var bcSrc = this.transformInv_(bc); - var da = [(d[0] + a[0]) / 2, (d[1] + a[1]) / 2]; - var daSrc = this.transformInv_(da); - - this.addQuad_( - a, b, bc, da, aSrc, bSrc, bcSrc, daSrc, maxSubdivision - 1); - this.addQuad_( - da, bc, c, d, daSrc, bcSrc, cSrc, dSrc, maxSubdivision - 1); - } else { - // split vertically (left & right) - var ab = [(a[0] + b[0]) / 2, (a[1] + b[1]) / 2]; - var abSrc = this.transformInv_(ab); - var cd = [(c[0] + d[0]) / 2, (c[1] + d[1]) / 2]; - var cdSrc = this.transformInv_(cd); - - this.addQuad_( - a, ab, cd, d, aSrc, abSrc, cdSrc, dSrc, maxSubdivision - 1); - this.addQuad_( - ab, b, c, cd, abSrc, bSrc, cSrc, cdSrc, maxSubdivision - 1); - } - return; - } - } - - if (wrapsX) { - if (!this.canWrapXInSource_) { - return; - } - this.wrapsXInSource_ = true; - } - - this.addTriangle_(a, c, d, aSrc, cSrc, dSrc); - this.addTriangle_(a, b, c, aSrc, bSrc, cSrc); -}; - - -/** - * Calculates extent of the 'source' coordinates from all the triangles. - * - * @return {ol.Extent} Calculated extent. - */ -ol.reproj.Triangulation.prototype.calculateSourceExtent = function() { - var extent = ol.extent.createEmpty(); - - this.triangles_.forEach(function(triangle, i, arr) { - var src = triangle.source; - ol.extent.extendCoordinate(extent, src[0]); - ol.extent.extendCoordinate(extent, src[1]); - ol.extent.extendCoordinate(extent, src[2]); - }); - - return extent; -}; - - -/** - * @return {Array.<ol.ReprojTriangle>} Array of the calculated triangles. - */ -ol.reproj.Triangulation.prototype.getTriangles = function() { - return this.triangles_; -}; - -goog.provide('ol.reproj.Image'); - -goog.require('ol'); -goog.require('ol.ImageBase'); -goog.require('ol.ImageState'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.extent'); -goog.require('ol.reproj'); -goog.require('ol.reproj.Triangulation'); - - -/** - * @classdesc - * Class encapsulating single reprojected image. - * See {@link ol.source.Image}. - * - * @constructor - * @extends {ol.ImageBase} - * @param {ol.proj.Projection} sourceProj Source projection (of the data). - * @param {ol.proj.Projection} targetProj Target projection. - * @param {ol.Extent} targetExtent Target extent. - * @param {number} targetResolution Target resolution. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.ReprojImageFunctionType} getImageFunction - * Function returning source images (extent, resolution, pixelRatio). - */ -ol.reproj.Image = function(sourceProj, targetProj, - targetExtent, targetResolution, pixelRatio, getImageFunction) { - - /** - * @private - * @type {ol.proj.Projection} - */ - this.targetProj_ = targetProj; - - /** - * @private - * @type {ol.Extent} - */ - this.maxSourceExtent_ = sourceProj.getExtent(); - var maxTargetExtent = targetProj.getExtent(); - - var limitedTargetExtent = maxTargetExtent ? - ol.extent.getIntersection(targetExtent, maxTargetExtent) : targetExtent; - - var targetCenter = ol.extent.getCenter(limitedTargetExtent); - var sourceResolution = ol.reproj.calculateSourceResolution( - sourceProj, targetProj, targetCenter, targetResolution); - - var errorThresholdInPixels = ol.DEFAULT_RASTER_REPROJECTION_ERROR_THRESHOLD; - - /** - * @private - * @type {!ol.reproj.Triangulation} - */ - this.triangulation_ = new ol.reproj.Triangulation( - sourceProj, targetProj, limitedTargetExtent, this.maxSourceExtent_, - sourceResolution * errorThresholdInPixels); - - /** - * @private - * @type {number} - */ - this.targetResolution_ = targetResolution; - - /** - * @private - * @type {ol.Extent} - */ - this.targetExtent_ = targetExtent; - - var sourceExtent = this.triangulation_.calculateSourceExtent(); - - /** - * @private - * @type {ol.ImageBase} - */ - this.sourceImage_ = - getImageFunction(sourceExtent, sourceResolution, pixelRatio); - - /** - * @private - * @type {number} - */ - this.sourcePixelRatio_ = - this.sourceImage_ ? this.sourceImage_.getPixelRatio() : 1; - - /** - * @private - * @type {HTMLCanvasElement} - */ - this.canvas_ = null; - - /** - * @private - * @type {?ol.EventsKey} - */ - this.sourceListenerKey_ = null; - - - var state = ol.ImageState.LOADED; - var attributions = []; - - if (this.sourceImage_) { - state = ol.ImageState.IDLE; - attributions = this.sourceImage_.getAttributions(); - } - - ol.ImageBase.call(this, targetExtent, targetResolution, this.sourcePixelRatio_, - state, attributions); -}; -ol.inherits(ol.reproj.Image, ol.ImageBase); - - -/** - * @inheritDoc - */ -ol.reproj.Image.prototype.disposeInternal = function() { - if (this.state == ol.ImageState.LOADING) { - this.unlistenSource_(); - } - ol.ImageBase.prototype.disposeInternal.call(this); -}; - - -/** - * @inheritDoc - */ -ol.reproj.Image.prototype.getImage = function() { - return this.canvas_; -}; - - -/** - * @return {ol.proj.Projection} Projection. - */ -ol.reproj.Image.prototype.getProjection = function() { - return this.targetProj_; -}; - - -/** - * @private - */ -ol.reproj.Image.prototype.reproject_ = function() { - var sourceState = this.sourceImage_.getState(); - if (sourceState == ol.ImageState.LOADED) { - var width = ol.extent.getWidth(this.targetExtent_) / this.targetResolution_; - var height = - ol.extent.getHeight(this.targetExtent_) / this.targetResolution_; - - this.canvas_ = ol.reproj.render(width, height, this.sourcePixelRatio_, - this.sourceImage_.getResolution(), this.maxSourceExtent_, - this.targetResolution_, this.targetExtent_, this.triangulation_, [{ - extent: this.sourceImage_.getExtent(), - image: this.sourceImage_.getImage() - }], 0); - } - this.state = sourceState; - this.changed(); -}; - - -/** - * @inheritDoc - */ -ol.reproj.Image.prototype.load = function() { - if (this.state == ol.ImageState.IDLE) { - this.state = ol.ImageState.LOADING; - this.changed(); - - var sourceState = this.sourceImage_.getState(); - if (sourceState == ol.ImageState.LOADED || - sourceState == ol.ImageState.ERROR) { - this.reproject_(); - } else { - this.sourceListenerKey_ = ol.events.listen(this.sourceImage_, - ol.events.EventType.CHANGE, function(e) { - var sourceState = this.sourceImage_.getState(); - if (sourceState == ol.ImageState.LOADED || - sourceState == ol.ImageState.ERROR) { - this.unlistenSource_(); - this.reproject_(); - } - }, this); - this.sourceImage_.load(); - } - } -}; - - -/** - * @private - */ -ol.reproj.Image.prototype.unlistenSource_ = function() { - ol.events.unlistenByKey(/** @type {!ol.EventsKey} */ (this.sourceListenerKey_)); - this.sourceListenerKey_ = null; -}; - -goog.provide('ol.source.Image'); - -goog.require('ol'); -goog.require('ol.ImageState'); -goog.require('ol.array'); -goog.require('ol.events.Event'); -goog.require('ol.extent'); -goog.require('ol.proj'); -goog.require('ol.reproj.Image'); -goog.require('ol.source.Source'); - - -/** - * @classdesc - * Abstract base class; normally only used for creating subclasses and not - * instantiated in apps. - * Base class for sources providing a single image. - * - * @constructor - * @abstract - * @extends {ol.source.Source} - * @param {ol.SourceImageOptions} options Single image source options. - * @api - */ -ol.source.Image = function(options) { - ol.source.Source.call(this, { - attributions: options.attributions, - extent: options.extent, - logo: options.logo, - projection: options.projection, - state: options.state - }); - - /** - * @private - * @type {Array.<number>} - */ - this.resolutions_ = options.resolutions !== undefined ? - options.resolutions : null; - - - /** - * @private - * @type {ol.reproj.Image} - */ - this.reprojectedImage_ = null; - - - /** - * @private - * @type {number} - */ - this.reprojectedRevision_ = 0; -}; -ol.inherits(ol.source.Image, ol.source.Source); - - -/** - * @return {Array.<number>} Resolutions. - * @override - */ -ol.source.Image.prototype.getResolutions = function() { - return this.resolutions_; -}; - - -/** - * @protected - * @param {number} resolution Resolution. - * @return {number} Resolution. - */ -ol.source.Image.prototype.findNearestResolution = function(resolution) { - if (this.resolutions_) { - var idx = ol.array.linearFindNearest(this.resolutions_, resolution, 0); - resolution = this.resolutions_[idx]; - } - return resolution; -}; - - -/** - * @param {ol.Extent} extent Extent. - * @param {number} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.proj.Projection} projection Projection. - * @return {ol.ImageBase} Single image. - */ -ol.source.Image.prototype.getImage = function(extent, resolution, pixelRatio, projection) { - var sourceProjection = this.getProjection(); - if (!ol.ENABLE_RASTER_REPROJECTION || - !sourceProjection || - !projection || - ol.proj.equivalent(sourceProjection, projection)) { - if (sourceProjection) { - projection = sourceProjection; - } - return this.getImageInternal(extent, resolution, pixelRatio, projection); - } else { - if (this.reprojectedImage_) { - if (this.reprojectedRevision_ == this.getRevision() && - ol.proj.equivalent( - this.reprojectedImage_.getProjection(), projection) && - this.reprojectedImage_.getResolution() == resolution && - ol.extent.equals(this.reprojectedImage_.getExtent(), extent)) { - return this.reprojectedImage_; - } - this.reprojectedImage_.dispose(); - this.reprojectedImage_ = null; - } - - this.reprojectedImage_ = new ol.reproj.Image( - sourceProjection, projection, extent, resolution, pixelRatio, - function(extent, resolution, pixelRatio) { - return this.getImageInternal(extent, resolution, - pixelRatio, sourceProjection); - }.bind(this)); - this.reprojectedRevision_ = this.getRevision(); - - return this.reprojectedImage_; - } -}; - - -/** - * @abstract - * @param {ol.Extent} extent Extent. - * @param {number} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.proj.Projection} projection Projection. - * @return {ol.ImageBase} Single image. - * @protected - */ -ol.source.Image.prototype.getImageInternal = function(extent, resolution, pixelRatio, projection) {}; - - -/** - * Handle image change events. - * @param {ol.events.Event} event Event. - * @protected - */ -ol.source.Image.prototype.handleImageChange = function(event) { - var image = /** @type {ol.Image} */ (event.target); - switch (image.getState()) { - case ol.ImageState.LOADING: - this.dispatchEvent( - new ol.source.Image.Event(ol.source.Image.EventType_.IMAGELOADSTART, - image)); - break; - case ol.ImageState.LOADED: - this.dispatchEvent( - new ol.source.Image.Event(ol.source.Image.EventType_.IMAGELOADEND, - image)); - break; - case ol.ImageState.ERROR: - this.dispatchEvent( - new ol.source.Image.Event(ol.source.Image.EventType_.IMAGELOADERROR, - image)); - break; - default: - // pass - } -}; - - -/** - * Default image load function for image sources that use ol.Image image - * instances. - * @param {ol.Image} image Image. - * @param {string} src Source. - */ -ol.source.Image.defaultImageLoadFunction = function(image, src) { - image.getImage().src = src; -}; - - -/** - * @classdesc - * Events emitted by {@link ol.source.Image} instances are instances of this - * type. - * - * @constructor - * @extends {ol.events.Event} - * @implements {oli.source.ImageEvent} - * @param {string} type Type. - * @param {ol.Image} image The image. - */ -ol.source.Image.Event = function(type, image) { - - ol.events.Event.call(this, type); - - /** - * The image related to the event. - * @type {ol.Image} - * @api - */ - this.image = image; - -}; -ol.inherits(ol.source.Image.Event, ol.events.Event); - - -/** - * @enum {string} - * @private - */ -ol.source.Image.EventType_ = { - - /** - * Triggered when an image starts loading. - * @event ol.source.Image.Event#imageloadstart - * @api - */ - IMAGELOADSTART: 'imageloadstart', - - /** - * Triggered when an image finishes loading. - * @event ol.source.Image.Event#imageloadend - * @api - */ - IMAGELOADEND: 'imageloadend', - - /** - * Triggered if image loading results in an error. - * @event ol.source.Image.Event#imageloaderror - * @api - */ - IMAGELOADERROR: 'imageloaderror' - -}; - -goog.provide('ol.source.ImageCanvas'); - -goog.require('ol'); -goog.require('ol.ImageCanvas'); -goog.require('ol.extent'); -goog.require('ol.source.Image'); - - -/** - * @classdesc - * Base class for image sources where a canvas element is the image. - * - * @constructor - * @extends {ol.source.Image} - * @param {olx.source.ImageCanvasOptions} options Constructor options. - * @api - */ -ol.source.ImageCanvas = function(options) { - - ol.source.Image.call(this, { - attributions: options.attributions, - logo: options.logo, - projection: options.projection, - resolutions: options.resolutions, - state: options.state - }); - - /** - * @private - * @type {ol.CanvasFunctionType} - */ - this.canvasFunction_ = options.canvasFunction; - - /** - * @private - * @type {ol.ImageCanvas} - */ - this.canvas_ = null; - - /** - * @private - * @type {number} - */ - this.renderedRevision_ = 0; - - /** - * @private - * @type {number} - */ - this.ratio_ = options.ratio !== undefined ? - options.ratio : 1.5; - -}; -ol.inherits(ol.source.ImageCanvas, ol.source.Image); - - -/** - * @inheritDoc - */ -ol.source.ImageCanvas.prototype.getImageInternal = function(extent, resolution, pixelRatio, projection) { - resolution = this.findNearestResolution(resolution); - - var canvas = this.canvas_; - if (canvas && - this.renderedRevision_ == this.getRevision() && - canvas.getResolution() == resolution && - canvas.getPixelRatio() == pixelRatio && - ol.extent.containsExtent(canvas.getExtent(), extent)) { - return canvas; - } - - extent = extent.slice(); - ol.extent.scaleFromCenter(extent, this.ratio_); - var width = ol.extent.getWidth(extent) / resolution; - var height = ol.extent.getHeight(extent) / resolution; - var size = [width * pixelRatio, height * pixelRatio]; - - var canvasElement = this.canvasFunction_( - extent, resolution, pixelRatio, size, projection); - if (canvasElement) { - canvas = new ol.ImageCanvas(extent, resolution, pixelRatio, - this.getAttributions(), canvasElement); - } - this.canvas_ = canvas; - this.renderedRevision_ = this.getRevision(); - - return canvas; -}; - -goog.provide('ol.source.ImageVector'); - -goog.require('ol'); -goog.require('ol.dom'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.extent'); -goog.require('ol.render.canvas.ReplayGroup'); -goog.require('ol.renderer.vector'); -goog.require('ol.source.ImageCanvas'); -goog.require('ol.style.Style'); -goog.require('ol.transform'); - - -/** - * @classdesc - * An image source whose images are canvas elements into which vector features - * read from a vector source (`ol.source.Vector`) are drawn. An - * `ol.source.ImageVector` object is to be used as the `source` of an image - * layer (`ol.layer.Image`). Image layers are rotated, scaled, and translated, - * as opposed to being re-rendered, during animations and interactions. So, like - * any other image layer, an image layer configured with an - * `ol.source.ImageVector` will exhibit this behaviour. This is in contrast to a - * vector layer, where vector features are re-drawn during animations and - * interactions. - * - * @constructor - * @extends {ol.source.ImageCanvas} - * @param {olx.source.ImageVectorOptions} options Options. - * @api - */ -ol.source.ImageVector = function(options) { - - /** - * @private - * @type {ol.source.Vector} - */ - this.source_ = options.source; - - /** - * @private - * @type {ol.Transform} - */ - this.transform_ = ol.transform.create(); - - /** - * @private - * @type {CanvasRenderingContext2D} - */ - this.canvasContext_ = ol.dom.createCanvasContext2D(); - - /** - * @private - * @type {ol.Size} - */ - this.canvasSize_ = [0, 0]; - - /** - * @private - * @type {number} - */ - this.renderBuffer_ = options.renderBuffer == undefined ? 100 : options.renderBuffer; - - /** - * @private - * @type {ol.render.canvas.ReplayGroup} - */ - this.replayGroup_ = null; - - ol.source.ImageCanvas.call(this, { - attributions: options.attributions, - canvasFunction: this.canvasFunctionInternal_.bind(this), - logo: options.logo, - projection: options.projection, - ratio: options.ratio, - resolutions: options.resolutions, - state: this.source_.getState() - }); - - /** - * User provided style. - * @type {ol.style.Style|Array.<ol.style.Style>|ol.StyleFunction} - * @private - */ - this.style_ = null; - - /** - * Style function for use within the library. - * @type {ol.StyleFunction|undefined} - * @private - */ - this.styleFunction_ = undefined; - - this.setStyle(options.style); - - ol.events.listen(this.source_, ol.events.EventType.CHANGE, - this.handleSourceChange_, this); - -}; -ol.inherits(ol.source.ImageVector, ol.source.ImageCanvas); - - -/** - * @param {ol.Extent} extent Extent. - * @param {number} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.Size} size Size. - * @param {ol.proj.Projection} projection Projection; - * @return {HTMLCanvasElement} Canvas element. - * @private - */ -ol.source.ImageVector.prototype.canvasFunctionInternal_ = function(extent, resolution, pixelRatio, size, projection) { - - var replayGroup = new ol.render.canvas.ReplayGroup( - ol.renderer.vector.getTolerance(resolution, pixelRatio), extent, - resolution, pixelRatio, this.source_.getOverlaps(), this.renderBuffer_); - - this.source_.loadFeatures(extent, resolution, projection); - - var loading = false; - this.source_.forEachFeatureInExtent(extent, - /** - * @param {ol.Feature} feature Feature. - */ - function(feature) { - loading = loading || - this.renderFeature_(feature, resolution, pixelRatio, replayGroup); - }, this); - replayGroup.finish(); - - if (loading) { - return null; - } - - if (this.canvasSize_[0] != size[0] || this.canvasSize_[1] != size[1]) { - this.canvasContext_.canvas.width = size[0]; - this.canvasContext_.canvas.height = size[1]; - this.canvasSize_[0] = size[0]; - this.canvasSize_[1] = size[1]; - } else { - this.canvasContext_.clearRect(0, 0, size[0], size[1]); - } - - var transform = this.getTransform_(ol.extent.getCenter(extent), - resolution, pixelRatio, size); - replayGroup.replay(this.canvasContext_, transform, 0, {}); - - this.replayGroup_ = replayGroup; - - return this.canvasContext_.canvas; -}; - - -/** - * @inheritDoc - */ -ol.source.ImageVector.prototype.forEachFeatureAtCoordinate = function( - coordinate, resolution, rotation, hitTolerance, skippedFeatureUids, callback) { - if (!this.replayGroup_) { - return undefined; - } else { - /** @type {Object.<string, boolean>} */ - var features = {}; - return this.replayGroup_.forEachFeatureAtCoordinate( - coordinate, resolution, 0, hitTolerance, skippedFeatureUids, - /** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @return {?} Callback result. - */ - function(feature) { - var key = ol.getUid(feature).toString(); - if (!(key in features)) { - features[key] = true; - return callback(feature); - } - }); - } -}; - - -/** - * Get a reference to the wrapped source. - * @return {ol.source.Vector} Source. - * @api - */ -ol.source.ImageVector.prototype.getSource = function() { - return this.source_; -}; - - -/** - * Get the style for features. This returns whatever was passed to the `style` - * option at construction or to the `setStyle` method. - * @return {ol.style.Style|Array.<ol.style.Style>|ol.StyleFunction} - * Layer style. - * @api - */ -ol.source.ImageVector.prototype.getStyle = function() { - return this.style_; -}; - - -/** - * Get the style function. - * @return {ol.StyleFunction|undefined} Layer style function. - * @api - */ -ol.source.ImageVector.prototype.getStyleFunction = function() { - return this.styleFunction_; -}; - - -/** - * @param {ol.Coordinate} center Center. - * @param {number} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.Size} size Size. - * @return {!ol.Transform} Transform. - * @private - */ -ol.source.ImageVector.prototype.getTransform_ = function(center, resolution, pixelRatio, size) { - var dx1 = size[0] / 2; - var dy1 = size[1] / 2; - var sx = pixelRatio / resolution; - var sy = -sx; - var dx2 = -center[0]; - var dy2 = -center[1]; - - return ol.transform.compose(this.transform_, dx1, dy1, sx, sy, 0, dx2, dy2); -}; - - -/** - * Handle changes in image style state. - * @param {ol.events.Event} event Image style change event. - * @private - */ -ol.source.ImageVector.prototype.handleImageChange_ = function(event) { - this.changed(); -}; - - -/** - * @private - */ -ol.source.ImageVector.prototype.handleSourceChange_ = function() { - // setState will trigger a CHANGE event, so we always rely - // change events by calling setState. - this.setState(this.source_.getState()); -}; - - -/** - * @param {ol.Feature} feature Feature. - * @param {number} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.render.canvas.ReplayGroup} replayGroup Replay group. - * @return {boolean} `true` if an image is loading. - * @private - */ -ol.source.ImageVector.prototype.renderFeature_ = function(feature, resolution, pixelRatio, replayGroup) { - var styles; - var styleFunction = feature.getStyleFunction(); - if (styleFunction) { - styles = styleFunction.call(feature, resolution); - } else if (this.styleFunction_) { - styles = this.styleFunction_(feature, resolution); - } - if (!styles) { - return false; - } - var i, ii, loading = false; - if (!Array.isArray(styles)) { - styles = [styles]; - } - for (i = 0, ii = styles.length; i < ii; ++i) { - loading = ol.renderer.vector.renderFeature( - replayGroup, feature, styles[i], - ol.renderer.vector.getSquaredTolerance(resolution, pixelRatio), - this.handleImageChange_, this) || loading; - } - return loading; -}; - - -/** - * Set the style for features. This can be a single style object, an array - * of styles, or a function that takes a feature and resolution and returns - * an array of styles. If it is `undefined` the default style is used. If - * it is `null` the layer has no style (a `null` style), so only features - * that have their own styles will be rendered in the layer. See - * {@link ol.style} for information on the default style. - * @param {ol.style.Style|Array.<ol.style.Style>|ol.StyleFunction|undefined} - * style Layer style. - * @api - */ -ol.source.ImageVector.prototype.setStyle = function(style) { - this.style_ = style !== undefined ? style : ol.style.Style.defaultFunction; - this.styleFunction_ = !style ? - undefined : ol.style.Style.createFunction(this.style_); - this.changed(); -}; - -goog.provide('ol.renderer.webgl.ImageLayer'); - -goog.require('ol'); -goog.require('ol.LayerType'); -goog.require('ol.ViewHint'); -goog.require('ol.dom'); -goog.require('ol.extent'); -goog.require('ol.functions'); -goog.require('ol.renderer.Type'); -goog.require('ol.renderer.webgl.Layer'); -goog.require('ol.source.ImageVector'); -goog.require('ol.transform'); -goog.require('ol.webgl'); -goog.require('ol.webgl.Context'); - - -/** - * @constructor - * @extends {ol.renderer.webgl.Layer} - * @param {ol.renderer.webgl.Map} mapRenderer Map renderer. - * @param {ol.layer.Image} imageLayer Tile layer. - * @api - */ -ol.renderer.webgl.ImageLayer = function(mapRenderer, imageLayer) { - - ol.renderer.webgl.Layer.call(this, mapRenderer, imageLayer); - - /** - * The last rendered image. - * @private - * @type {?ol.ImageBase} - */ - this.image_ = null; - - /** - * @private - * @type {CanvasRenderingContext2D} - */ - this.hitCanvasContext_ = null; - - /** - * @private - * @type {?ol.Transform} - */ - this.hitTransformationMatrix_ = null; - -}; -ol.inherits(ol.renderer.webgl.ImageLayer, ol.renderer.webgl.Layer); - - -/** - * Determine if this renderer handles the provided layer. - * @param {ol.renderer.Type} type The renderer type. - * @param {ol.layer.Layer} layer The candidate layer. - * @return {boolean} The renderer can render the layer. - */ -ol.renderer.webgl.ImageLayer['handles'] = function(type, layer) { - return type === ol.renderer.Type.WEBGL && layer.getType() === ol.LayerType.IMAGE; -}; - - -/** - * Create a layer renderer. - * @param {ol.renderer.Map} mapRenderer The map renderer. - * @param {ol.layer.Layer} layer The layer to be rendererd. - * @return {ol.renderer.webgl.ImageLayer} The layer renderer. - */ -ol.renderer.webgl.ImageLayer['create'] = function(mapRenderer, layer) { - return new ol.renderer.webgl.ImageLayer( - /** @type {ol.renderer.webgl.Map} */ (mapRenderer), - /** @type {ol.layer.Image} */ (layer) - ); -}; - - -/** - * @param {ol.ImageBase} image Image. - * @private - * @return {WebGLTexture} Texture. - */ -ol.renderer.webgl.ImageLayer.prototype.createTexture_ = function(image) { - - // We meet the conditions to work with non-power of two textures. - // http://www.khronos.org/webgl/wiki/WebGL_and_OpenGL_Differences#Non-Power_of_Two_Texture_Support - // http://learningwebgl.com/blog/?p=2101 - - var imageElement = image.getImage(); - var gl = this.mapRenderer.getGL(); - - return ol.webgl.Context.createTexture( - gl, imageElement, ol.webgl.CLAMP_TO_EDGE, ol.webgl.CLAMP_TO_EDGE); -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.ImageLayer.prototype.forEachFeatureAtCoordinate = function(coordinate, frameState, hitTolerance, callback, thisArg) { - var layer = this.getLayer(); - var source = layer.getSource(); - var resolution = frameState.viewState.resolution; - var rotation = frameState.viewState.rotation; - var skippedFeatureUids = frameState.skippedFeatureUids; - return source.forEachFeatureAtCoordinate( - coordinate, resolution, rotation, hitTolerance, skippedFeatureUids, - - /** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @return {?} Callback result. - */ - function(feature) { - return callback.call(thisArg, feature, layer); - }); -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.ImageLayer.prototype.prepareFrame = function(frameState, layerState, context) { - - var gl = this.mapRenderer.getGL(); - - var pixelRatio = frameState.pixelRatio; - var viewState = frameState.viewState; - var viewCenter = viewState.center; - var viewResolution = viewState.resolution; - var viewRotation = viewState.rotation; - - var image = this.image_; - var texture = this.texture; - var imageLayer = /** @type {ol.layer.Image} */ (this.getLayer()); - var imageSource = imageLayer.getSource(); - - var hints = frameState.viewHints; - - var renderedExtent = frameState.extent; - if (layerState.extent !== undefined) { - renderedExtent = ol.extent.getIntersection( - renderedExtent, layerState.extent); - } - if (!hints[ol.ViewHint.ANIMATING] && !hints[ol.ViewHint.INTERACTING] && - !ol.extent.isEmpty(renderedExtent)) { - var projection = viewState.projection; - if (!ol.ENABLE_RASTER_REPROJECTION) { - var sourceProjection = imageSource.getProjection(); - if (sourceProjection) { - projection = sourceProjection; - } - } - var image_ = imageSource.getImage(renderedExtent, viewResolution, - pixelRatio, projection); - if (image_) { - var loaded = this.loadImage(image_); - if (loaded) { - image = image_; - texture = this.createTexture_(image_); - if (this.texture) { - /** - * @param {WebGLRenderingContext} gl GL. - * @param {WebGLTexture} texture Texture. - */ - var postRenderFunction = function(gl, texture) { - if (!gl.isContextLost()) { - gl.deleteTexture(texture); - } - }.bind(null, gl, this.texture); - frameState.postRenderFunctions.push( - /** @type {ol.PostRenderFunction} */ (postRenderFunction) - ); - } - } - } - } - - if (image) { - var canvas = this.mapRenderer.getContext().getCanvas(); - - this.updateProjectionMatrix_(canvas.width, canvas.height, - pixelRatio, viewCenter, viewResolution, viewRotation, - image.getExtent()); - this.hitTransformationMatrix_ = null; - - // Translate and scale to flip the Y coord. - var texCoordMatrix = this.texCoordMatrix; - ol.transform.reset(texCoordMatrix); - ol.transform.scale(texCoordMatrix, 1, -1); - ol.transform.translate(texCoordMatrix, 0, -1); - - this.image_ = image; - this.texture = texture; - - this.updateAttributions(frameState.attributions, image.getAttributions()); - this.updateLogos(frameState, imageSource); - } - - return !!image; -}; - - -/** - * @param {number} canvasWidth Canvas width. - * @param {number} canvasHeight Canvas height. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.Coordinate} viewCenter View center. - * @param {number} viewResolution View resolution. - * @param {number} viewRotation View rotation. - * @param {ol.Extent} imageExtent Image extent. - * @private - */ -ol.renderer.webgl.ImageLayer.prototype.updateProjectionMatrix_ = function(canvasWidth, canvasHeight, pixelRatio, - viewCenter, viewResolution, viewRotation, imageExtent) { - - var canvasExtentWidth = canvasWidth * viewResolution; - var canvasExtentHeight = canvasHeight * viewResolution; - - var projectionMatrix = this.projectionMatrix; - ol.transform.reset(projectionMatrix); - ol.transform.scale(projectionMatrix, - pixelRatio * 2 / canvasExtentWidth, - pixelRatio * 2 / canvasExtentHeight); - ol.transform.rotate(projectionMatrix, -viewRotation); - ol.transform.translate(projectionMatrix, - imageExtent[0] - viewCenter[0], - imageExtent[1] - viewCenter[1]); - ol.transform.scale(projectionMatrix, - (imageExtent[2] - imageExtent[0]) / 2, - (imageExtent[3] - imageExtent[1]) / 2); - ol.transform.translate(projectionMatrix, 1, 1); - -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.ImageLayer.prototype.hasFeatureAtCoordinate = function(coordinate, frameState) { - var hasFeature = this.forEachFeatureAtCoordinate( - coordinate, frameState, 0, ol.functions.TRUE, this); - return hasFeature !== undefined; -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.ImageLayer.prototype.forEachLayerAtPixel = function(pixel, frameState, callback, thisArg) { - if (!this.image_ || !this.image_.getImage()) { - return undefined; - } - - if (this.getLayer().getSource() instanceof ol.source.ImageVector) { - // for ImageVector sources use the original hit-detection logic, - // so that for example also transparent polygons are detected - var coordinate = ol.transform.apply( - frameState.pixelToCoordinateTransform, pixel.slice()); - var hasFeature = this.forEachFeatureAtCoordinate( - coordinate, frameState, 0, ol.functions.TRUE, this); - - if (hasFeature) { - return callback.call(thisArg, this.getLayer(), null); - } else { - return undefined; - } - } else { - var imageSize = - [this.image_.getImage().width, this.image_.getImage().height]; - - if (!this.hitTransformationMatrix_) { - this.hitTransformationMatrix_ = this.getHitTransformationMatrix_( - frameState.size, imageSize); - } - - var pixelOnFrameBuffer = ol.transform.apply( - this.hitTransformationMatrix_, pixel.slice()); - - if (pixelOnFrameBuffer[0] < 0 || pixelOnFrameBuffer[0] > imageSize[0] || - pixelOnFrameBuffer[1] < 0 || pixelOnFrameBuffer[1] > imageSize[1]) { - // outside the image, no need to check - return undefined; - } - - if (!this.hitCanvasContext_) { - this.hitCanvasContext_ = ol.dom.createCanvasContext2D(1, 1); - } - - this.hitCanvasContext_.clearRect(0, 0, 1, 1); - this.hitCanvasContext_.drawImage(this.image_.getImage(), - pixelOnFrameBuffer[0], pixelOnFrameBuffer[1], 1, 1, 0, 0, 1, 1); - - var imageData = this.hitCanvasContext_.getImageData(0, 0, 1, 1).data; - if (imageData[3] > 0) { - return callback.call(thisArg, this.getLayer(), imageData); - } else { - return undefined; - } - } -}; - - -/** - * The transformation matrix to get the pixel on the image for a - * pixel on the map. - * @param {ol.Size} mapSize The map size. - * @param {ol.Size} imageSize The image size. - * @return {ol.Transform} The transformation matrix. - * @private - */ -ol.renderer.webgl.ImageLayer.prototype.getHitTransformationMatrix_ = function(mapSize, imageSize) { - // the first matrix takes a map pixel, flips the y-axis and scales to - // a range between -1 ... 1 - var mapCoordTransform = ol.transform.create(); - ol.transform.translate(mapCoordTransform, -1, -1); - ol.transform.scale(mapCoordTransform, 2 / mapSize[0], 2 / mapSize[1]); - ol.transform.translate(mapCoordTransform, 0, mapSize[1]); - ol.transform.scale(mapCoordTransform, 1, -1); - - // the second matrix is the inverse of the projection matrix used in the - // shader for drawing - var projectionMatrixInv = ol.transform.invert(this.projectionMatrix.slice()); - - // the third matrix scales to the image dimensions and flips the y-axis again - var transform = ol.transform.create(); - ol.transform.translate(transform, 0, imageSize[1]); - ol.transform.scale(transform, 1, -1); - ol.transform.scale(transform, imageSize[0] / 2, imageSize[1] / 2); - ol.transform.translate(transform, 1, 1); - - ol.transform.multiply(transform, projectionMatrixInv); - ol.transform.multiply(transform, mapCoordTransform); - - return transform; -}; - -// FIXME check against gl.getParameter(webgl.MAX_TEXTURE_SIZE) - -goog.provide('ol.renderer.webgl.Map'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.css'); -goog.require('ol.dom'); -goog.require('ol.events'); -goog.require('ol.has'); -goog.require('ol.layer.Layer'); -goog.require('ol.render.Event'); -goog.require('ol.render.EventType'); -goog.require('ol.render.webgl.Immediate'); -goog.require('ol.renderer.Map'); -goog.require('ol.renderer.Type'); -goog.require('ol.source.State'); -goog.require('ol.structs.LRUCache'); -goog.require('ol.structs.PriorityQueue'); -goog.require('ol.webgl'); -goog.require('ol.webgl.Context'); -goog.require('ol.webgl.ContextEventType'); - - -/** - * @constructor - * @extends {ol.renderer.Map} - * @param {Element} container Container. - * @param {ol.PluggableMap} map Map. - * @api - */ -ol.renderer.webgl.Map = function(container, map) { - ol.renderer.Map.call(this, container, map); - - /** - * @private - * @type {HTMLCanvasElement} - */ - this.canvas_ = /** @type {HTMLCanvasElement} */ - (document.createElement('CANVAS')); - this.canvas_.style.width = '100%'; - this.canvas_.style.height = '100%'; - this.canvas_.style.display = 'block'; - this.canvas_.className = ol.css.CLASS_UNSELECTABLE; - container.insertBefore(this.canvas_, container.childNodes[0] || null); - - /** - * @private - * @type {number} - */ - this.clipTileCanvasWidth_ = 0; - - /** - * @private - * @type {number} - */ - this.clipTileCanvasHeight_ = 0; - - /** - * @private - * @type {CanvasRenderingContext2D} - */ - this.clipTileContext_ = ol.dom.createCanvasContext2D(); - - /** - * @private - * @type {boolean} - */ - this.renderedVisible_ = true; - - /** - * @private - * @type {WebGLRenderingContext} - */ - this.gl_ = ol.webgl.getContext(this.canvas_, { - antialias: true, - depth: true, - failIfMajorPerformanceCaveat: true, - preserveDrawingBuffer: false, - stencil: true - }); - - /** - * @private - * @type {ol.webgl.Context} - */ - this.context_ = new ol.webgl.Context(this.canvas_, this.gl_); - - ol.events.listen(this.canvas_, ol.webgl.ContextEventType.LOST, - this.handleWebGLContextLost, this); - ol.events.listen(this.canvas_, ol.webgl.ContextEventType.RESTORED, - this.handleWebGLContextRestored, this); - - /** - * @private - * @type {ol.structs.LRUCache.<ol.WebglTextureCacheEntry|null>} - */ - this.textureCache_ = new ol.structs.LRUCache(); - - /** - * @private - * @type {ol.Coordinate} - */ - this.focus_ = null; - - /** - * @private - * @type {ol.structs.PriorityQueue.<Array>} - */ - this.tileTextureQueue_ = new ol.structs.PriorityQueue( - /** - * @param {Array.<*>} element Element. - * @return {number} Priority. - * @this {ol.renderer.webgl.Map} - */ - (function(element) { - var tileCenter = /** @type {ol.Coordinate} */ (element[1]); - var tileResolution = /** @type {number} */ (element[2]); - var deltaX = tileCenter[0] - this.focus_[0]; - var deltaY = tileCenter[1] - this.focus_[1]; - return 65536 * Math.log(tileResolution) + - Math.sqrt(deltaX * deltaX + deltaY * deltaY) / tileResolution; - }).bind(this), - /** - * @param {Array.<*>} element Element. - * @return {string} Key. - */ - function(element) { - return /** @type {ol.Tile} */ (element[0]).getKey(); - }); - - - /** - * @param {ol.PluggableMap} map Map. - * @param {?olx.FrameState} frameState Frame state. - * @return {boolean} false. - * @this {ol.renderer.webgl.Map} - */ - this.loadNextTileTexture_ = - function(map, frameState) { - if (!this.tileTextureQueue_.isEmpty()) { - this.tileTextureQueue_.reprioritize(); - var element = this.tileTextureQueue_.dequeue(); - var tile = /** @type {ol.Tile} */ (element[0]); - var tileSize = /** @type {ol.Size} */ (element[3]); - var tileGutter = /** @type {number} */ (element[4]); - this.bindTileTexture( - tile, tileSize, tileGutter, ol.webgl.LINEAR, ol.webgl.LINEAR); - } - return false; - }.bind(this); - - - /** - * @private - * @type {number} - */ - this.textureCacheFrameMarkerCount_ = 0; - - this.initializeGL_(); -}; -ol.inherits(ol.renderer.webgl.Map, ol.renderer.Map); - - -/** - * Determine if this renderer handles the provided layer. - * @param {ol.renderer.Type} type The renderer type. - * @return {boolean} The renderer can render the layer. - */ -ol.renderer.webgl.Map['handles'] = function(type) { - return ol.has.WEBGL && type === ol.renderer.Type.WEBGL; -}; - - -/** - * Create the map renderer. - * @param {Element} container Container. - * @param {ol.PluggableMap} map Map. - * @return {ol.renderer.webgl.Map} The map renderer. - */ -ol.renderer.webgl.Map['create'] = function(container, map) { - return new ol.renderer.webgl.Map(container, map); -}; - - -/** - * @param {ol.Tile} tile Tile. - * @param {ol.Size} tileSize Tile size. - * @param {number} tileGutter Tile gutter. - * @param {number} magFilter Mag filter. - * @param {number} minFilter Min filter. - */ -ol.renderer.webgl.Map.prototype.bindTileTexture = function(tile, tileSize, tileGutter, magFilter, minFilter) { - var gl = this.getGL(); - var tileKey = tile.getKey(); - if (this.textureCache_.containsKey(tileKey)) { - var textureCacheEntry = this.textureCache_.get(tileKey); - gl.bindTexture(ol.webgl.TEXTURE_2D, textureCacheEntry.texture); - if (textureCacheEntry.magFilter != magFilter) { - gl.texParameteri( - ol.webgl.TEXTURE_2D, ol.webgl.TEXTURE_MAG_FILTER, magFilter); - textureCacheEntry.magFilter = magFilter; - } - if (textureCacheEntry.minFilter != minFilter) { - gl.texParameteri( - ol.webgl.TEXTURE_2D, ol.webgl.TEXTURE_MIN_FILTER, minFilter); - textureCacheEntry.minFilter = minFilter; - } - } else { - var texture = gl.createTexture(); - gl.bindTexture(ol.webgl.TEXTURE_2D, texture); - if (tileGutter > 0) { - var clipTileCanvas = this.clipTileContext_.canvas; - var clipTileContext = this.clipTileContext_; - if (this.clipTileCanvasWidth_ !== tileSize[0] || - this.clipTileCanvasHeight_ !== tileSize[1]) { - clipTileCanvas.width = tileSize[0]; - clipTileCanvas.height = tileSize[1]; - this.clipTileCanvasWidth_ = tileSize[0]; - this.clipTileCanvasHeight_ = tileSize[1]; - } else { - clipTileContext.clearRect(0, 0, tileSize[0], tileSize[1]); - } - clipTileContext.drawImage(tile.getImage(), tileGutter, tileGutter, - tileSize[0], tileSize[1], 0, 0, tileSize[0], tileSize[1]); - gl.texImage2D(ol.webgl.TEXTURE_2D, 0, - ol.webgl.RGBA, ol.webgl.RGBA, - ol.webgl.UNSIGNED_BYTE, clipTileCanvas); - } else { - gl.texImage2D(ol.webgl.TEXTURE_2D, 0, - ol.webgl.RGBA, ol.webgl.RGBA, - ol.webgl.UNSIGNED_BYTE, tile.getImage()); - } - gl.texParameteri( - ol.webgl.TEXTURE_2D, ol.webgl.TEXTURE_MAG_FILTER, magFilter); - gl.texParameteri( - ol.webgl.TEXTURE_2D, ol.webgl.TEXTURE_MIN_FILTER, minFilter); - gl.texParameteri(ol.webgl.TEXTURE_2D, ol.webgl.TEXTURE_WRAP_S, - ol.webgl.CLAMP_TO_EDGE); - gl.texParameteri(ol.webgl.TEXTURE_2D, ol.webgl.TEXTURE_WRAP_T, - ol.webgl.CLAMP_TO_EDGE); - this.textureCache_.set(tileKey, { - texture: texture, - magFilter: magFilter, - minFilter: minFilter - }); - } -}; - - -/** - * @param {ol.render.EventType} type Event type. - * @param {olx.FrameState} frameState Frame state. - * @private - */ -ol.renderer.webgl.Map.prototype.dispatchComposeEvent_ = function(type, frameState) { - var map = this.getMap(); - if (map.hasListener(type)) { - var context = this.context_; - - var extent = frameState.extent; - var size = frameState.size; - var viewState = frameState.viewState; - var pixelRatio = frameState.pixelRatio; - - var resolution = viewState.resolution; - var center = viewState.center; - var rotation = viewState.rotation; - - var vectorContext = new ol.render.webgl.Immediate(context, - center, resolution, rotation, size, extent, pixelRatio); - var composeEvent = new ol.render.Event(type, vectorContext, - frameState, null, context); - map.dispatchEvent(composeEvent); - } -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.Map.prototype.disposeInternal = function() { - var gl = this.getGL(); - if (!gl.isContextLost()) { - this.textureCache_.forEach( - /** - * @param {?ol.WebglTextureCacheEntry} textureCacheEntry - * Texture cache entry. - */ - function(textureCacheEntry) { - if (textureCacheEntry) { - gl.deleteTexture(textureCacheEntry.texture); - } - }); - } - this.context_.dispose(); - ol.renderer.Map.prototype.disposeInternal.call(this); -}; - - -/** - * @param {ol.PluggableMap} map Map. - * @param {olx.FrameState} frameState Frame state. - * @private - */ -ol.renderer.webgl.Map.prototype.expireCache_ = function(map, frameState) { - var gl = this.getGL(); - var textureCacheEntry; - while (this.textureCache_.getCount() - this.textureCacheFrameMarkerCount_ > - ol.WEBGL_TEXTURE_CACHE_HIGH_WATER_MARK) { - textureCacheEntry = this.textureCache_.peekLast(); - if (!textureCacheEntry) { - if (+this.textureCache_.peekLastKey() == frameState.index) { - break; - } else { - --this.textureCacheFrameMarkerCount_; - } - } else { - gl.deleteTexture(textureCacheEntry.texture); - } - this.textureCache_.pop(); - } -}; - - -/** - * @return {ol.webgl.Context} The context. - */ -ol.renderer.webgl.Map.prototype.getContext = function() { - return this.context_; -}; - - -/** - * @return {WebGLRenderingContext} GL. - */ -ol.renderer.webgl.Map.prototype.getGL = function() { - return this.gl_; -}; - - -/** - * @return {ol.structs.PriorityQueue.<Array>} Tile texture queue. - */ -ol.renderer.webgl.Map.prototype.getTileTextureQueue = function() { - return this.tileTextureQueue_; -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.Map.prototype.getType = function() { - return ol.renderer.Type.WEBGL; -}; - - -/** - * @param {ol.events.Event} event Event. - * @protected - */ -ol.renderer.webgl.Map.prototype.handleWebGLContextLost = function(event) { - event.preventDefault(); - this.textureCache_.clear(); - this.textureCacheFrameMarkerCount_ = 0; - - var renderers = this.getLayerRenderers(); - for (var id in renderers) { - var renderer = /** @type {ol.renderer.webgl.Layer} */ (renderers[id]); - renderer.handleWebGLContextLost(); - } -}; - - -/** - * @protected - */ -ol.renderer.webgl.Map.prototype.handleWebGLContextRestored = function() { - this.initializeGL_(); - this.getMap().render(); -}; - - -/** - * @private - */ -ol.renderer.webgl.Map.prototype.initializeGL_ = function() { - var gl = this.gl_; - gl.activeTexture(ol.webgl.TEXTURE0); - gl.blendFuncSeparate( - ol.webgl.SRC_ALPHA, ol.webgl.ONE_MINUS_SRC_ALPHA, - ol.webgl.ONE, ol.webgl.ONE_MINUS_SRC_ALPHA); - gl.disable(ol.webgl.CULL_FACE); - gl.disable(ol.webgl.DEPTH_TEST); - gl.disable(ol.webgl.SCISSOR_TEST); - gl.disable(ol.webgl.STENCIL_TEST); -}; - - -/** - * @param {ol.Tile} tile Tile. - * @return {boolean} Is tile texture loaded. - */ -ol.renderer.webgl.Map.prototype.isTileTextureLoaded = function(tile) { - return this.textureCache_.containsKey(tile.getKey()); -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.Map.prototype.renderFrame = function(frameState) { - - var context = this.getContext(); - var gl = this.getGL(); - - if (gl.isContextLost()) { - return false; - } - - if (!frameState) { - if (this.renderedVisible_) { - this.canvas_.style.display = 'none'; - this.renderedVisible_ = false; - } - return false; - } - - this.focus_ = frameState.focus; - - this.textureCache_.set((-frameState.index).toString(), null); - ++this.textureCacheFrameMarkerCount_; - - this.dispatchComposeEvent_(ol.render.EventType.PRECOMPOSE, frameState); - - /** @type {Array.<ol.LayerState>} */ - var layerStatesToDraw = []; - var layerStatesArray = frameState.layerStatesArray; - ol.array.stableSort(layerStatesArray, ol.renderer.Map.sortByZIndex); - - var viewResolution = frameState.viewState.resolution; - var i, ii, layerRenderer, layerState; - for (i = 0, ii = layerStatesArray.length; i < ii; ++i) { - layerState = layerStatesArray[i]; - if (ol.layer.Layer.visibleAtResolution(layerState, viewResolution) && - layerState.sourceState == ol.source.State.READY) { - layerRenderer = /** @type {ol.renderer.webgl.Layer} */ (this.getLayerRenderer(layerState.layer)); - if (layerRenderer.prepareFrame(frameState, layerState, context)) { - layerStatesToDraw.push(layerState); - } - } - } - - var width = frameState.size[0] * frameState.pixelRatio; - var height = frameState.size[1] * frameState.pixelRatio; - if (this.canvas_.width != width || this.canvas_.height != height) { - this.canvas_.width = width; - this.canvas_.height = height; - } - - gl.bindFramebuffer(ol.webgl.FRAMEBUFFER, null); - - gl.clearColor(0, 0, 0, 0); - gl.clear(ol.webgl.COLOR_BUFFER_BIT); - gl.enable(ol.webgl.BLEND); - gl.viewport(0, 0, this.canvas_.width, this.canvas_.height); - - for (i = 0, ii = layerStatesToDraw.length; i < ii; ++i) { - layerState = layerStatesToDraw[i]; - layerRenderer = /** @type {ol.renderer.webgl.Layer} */ (this.getLayerRenderer(layerState.layer)); - layerRenderer.composeFrame(frameState, layerState, context); - } - - if (!this.renderedVisible_) { - this.canvas_.style.display = ''; - this.renderedVisible_ = true; - } - - this.calculateMatrices2D(frameState); - - if (this.textureCache_.getCount() - this.textureCacheFrameMarkerCount_ > - ol.WEBGL_TEXTURE_CACHE_HIGH_WATER_MARK) { - frameState.postRenderFunctions.push( - /** @type {ol.PostRenderFunction} */ (this.expireCache_.bind(this)) - ); - } - - if (!this.tileTextureQueue_.isEmpty()) { - frameState.postRenderFunctions.push(this.loadNextTileTexture_); - frameState.animate = true; - } - - this.dispatchComposeEvent_(ol.render.EventType.POSTCOMPOSE, frameState); - - this.scheduleRemoveUnusedLayerRenderers(frameState); - this.scheduleExpireIconCache(frameState); - -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.Map.prototype.forEachFeatureAtCoordinate = function(coordinate, frameState, hitTolerance, callback, thisArg, - layerFilter, thisArg2) { - var result; - - if (this.getGL().isContextLost()) { - return false; - } - - var viewState = frameState.viewState; - - var layerStates = frameState.layerStatesArray; - var numLayers = layerStates.length; - var i; - for (i = numLayers - 1; i >= 0; --i) { - var layerState = layerStates[i]; - var layer = layerState.layer; - if (ol.layer.Layer.visibleAtResolution(layerState, viewState.resolution) && - layerFilter.call(thisArg2, layer)) { - var layerRenderer = this.getLayerRenderer(layer); - result = layerRenderer.forEachFeatureAtCoordinate( - coordinate, frameState, hitTolerance, callback, thisArg); - if (result) { - return result; - } - } - } - return undefined; -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.Map.prototype.hasFeatureAtCoordinate = function(coordinate, frameState, hitTolerance, layerFilter, thisArg) { - var hasFeature = false; - - if (this.getGL().isContextLost()) { - return false; - } - - var viewState = frameState.viewState; - - var layerStates = frameState.layerStatesArray; - var numLayers = layerStates.length; - var i; - for (i = numLayers - 1; i >= 0; --i) { - var layerState = layerStates[i]; - var layer = layerState.layer; - if (ol.layer.Layer.visibleAtResolution(layerState, viewState.resolution) && - layerFilter.call(thisArg, layer)) { - var layerRenderer = this.getLayerRenderer(layer); - hasFeature = - layerRenderer.hasFeatureAtCoordinate(coordinate, frameState); - if (hasFeature) { - return true; - } - } - } - return hasFeature; -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.Map.prototype.forEachLayerAtPixel = function(pixel, frameState, callback, thisArg, - layerFilter, thisArg2) { - if (this.getGL().isContextLost()) { - return false; - } - - var viewState = frameState.viewState; - var result; - - var layerStates = frameState.layerStatesArray; - var numLayers = layerStates.length; - var i; - for (i = numLayers - 1; i >= 0; --i) { - var layerState = layerStates[i]; - var layer = layerState.layer; - if (ol.layer.Layer.visibleAtResolution(layerState, viewState.resolution) && - layerFilter.call(thisArg, layer)) { - var layerRenderer = /** @type {ol.renderer.webgl.Layer} */ (this.getLayerRenderer(layer)); - result = layerRenderer.forEachLayerAtPixel( - pixel, frameState, callback, thisArg); - if (result) { - return result; - } - } - } - return undefined; -}; - -// This file is automatically generated, do not edit -goog.provide('ol.renderer.webgl.tilelayershader'); - -goog.require('ol'); -goog.require('ol.webgl.Fragment'); -goog.require('ol.webgl.Vertex'); - - -ol.renderer.webgl.tilelayershader.fragment = new ol.webgl.Fragment(ol.DEBUG_WEBGL ? - 'precision mediump float;\nvarying vec2 v_texCoord;\n\n\nuniform sampler2D u_texture;\n\nvoid main(void) {\n gl_FragColor = texture2D(u_texture, v_texCoord);\n}\n' : - 'precision mediump float;varying vec2 a;uniform sampler2D e;void main(void){gl_FragColor=texture2D(e,a);}'); - -ol.renderer.webgl.tilelayershader.vertex = new ol.webgl.Vertex(ol.DEBUG_WEBGL ? - 'varying vec2 v_texCoord;\n\n\nattribute vec2 a_position;\nattribute vec2 a_texCoord;\nuniform vec4 u_tileOffset;\n\nvoid main(void) {\n gl_Position = vec4(a_position * u_tileOffset.xy + u_tileOffset.zw, 0., 1.);\n v_texCoord = a_texCoord;\n}\n\n\n' : - 'varying vec2 a;attribute vec2 b;attribute vec2 c;uniform vec4 d;void main(void){gl_Position=vec4(b*d.xy+d.zw,0.,1.);a=c;}'); - -// This file is automatically generated, do not edit -goog.provide('ol.renderer.webgl.tilelayershader.Locations'); - -goog.require('ol'); - - -/** - * @constructor - * @param {WebGLRenderingContext} gl GL. - * @param {WebGLProgram} program Program. - * @struct - */ -ol.renderer.webgl.tilelayershader.Locations = function(gl, program) { - - /** - * @type {WebGLUniformLocation} - */ - this.u_tileOffset = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_tileOffset' : 'd'); - - /** - * @type {WebGLUniformLocation} - */ - this.u_texture = gl.getUniformLocation( - program, ol.DEBUG_WEBGL ? 'u_texture' : 'e'); - - /** - * @type {number} - */ - this.a_position = gl.getAttribLocation( - program, ol.DEBUG_WEBGL ? 'a_position' : 'b'); - - /** - * @type {number} - */ - this.a_texCoord = gl.getAttribLocation( - program, ol.DEBUG_WEBGL ? 'a_texCoord' : 'c'); -}; - -// FIXME large resolutions lead to too large framebuffers :-( -// FIXME animated shaders! check in redraw - -goog.provide('ol.renderer.webgl.TileLayer'); - -goog.require('ol'); -goog.require('ol.LayerType'); -goog.require('ol.TileRange'); -goog.require('ol.TileState'); -goog.require('ol.array'); -goog.require('ol.extent'); -goog.require('ol.math'); -goog.require('ol.renderer.Type'); -goog.require('ol.renderer.webgl.Layer'); -goog.require('ol.renderer.webgl.tilelayershader'); -goog.require('ol.renderer.webgl.tilelayershader.Locations'); -goog.require('ol.size'); -goog.require('ol.transform'); -goog.require('ol.webgl'); -goog.require('ol.webgl.Buffer'); - - -/** - * @constructor - * @extends {ol.renderer.webgl.Layer} - * @param {ol.renderer.webgl.Map} mapRenderer Map renderer. - * @param {ol.layer.Tile} tileLayer Tile layer. - * @api - */ -ol.renderer.webgl.TileLayer = function(mapRenderer, tileLayer) { - - ol.renderer.webgl.Layer.call(this, mapRenderer, tileLayer); - - /** - * @private - * @type {ol.webgl.Fragment} - */ - this.fragmentShader_ = ol.renderer.webgl.tilelayershader.fragment; - - /** - * @private - * @type {ol.webgl.Vertex} - */ - this.vertexShader_ = ol.renderer.webgl.tilelayershader.vertex; - - /** - * @private - * @type {ol.renderer.webgl.tilelayershader.Locations} - */ - this.locations_ = null; - - /** - * @private - * @type {ol.webgl.Buffer} - */ - this.renderArrayBuffer_ = new ol.webgl.Buffer([ - 0, 0, 0, 1, - 1, 0, 1, 1, - 0, 1, 0, 0, - 1, 1, 1, 0 - ]); - - /** - * @private - * @type {ol.TileRange} - */ - this.renderedTileRange_ = null; - - /** - * @private - * @type {ol.Extent} - */ - this.renderedFramebufferExtent_ = null; - - /** - * @private - * @type {number} - */ - this.renderedRevision_ = -1; - - /** - * @private - * @type {ol.Size} - */ - this.tmpSize_ = [0, 0]; - -}; -ol.inherits(ol.renderer.webgl.TileLayer, ol.renderer.webgl.Layer); - - -/** - * Determine if this renderer handles the provided layer. - * @param {ol.renderer.Type} type The renderer type. - * @param {ol.layer.Layer} layer The candidate layer. - * @return {boolean} The renderer can render the layer. - */ -ol.renderer.webgl.TileLayer['handles'] = function(type, layer) { - return type === ol.renderer.Type.WEBGL && layer.getType() === ol.LayerType.TILE; -}; - - -/** - * Create a layer renderer. - * @param {ol.renderer.Map} mapRenderer The map renderer. - * @param {ol.layer.Layer} layer The layer to be rendererd. - * @return {ol.renderer.webgl.TileLayer} The layer renderer. - */ -ol.renderer.webgl.TileLayer['create'] = function(mapRenderer, layer) { - return new ol.renderer.webgl.TileLayer( - /** @type {ol.renderer.webgl.Map} */ (mapRenderer), - /** @type {ol.layer.Tile} */ (layer) - ); -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.TileLayer.prototype.disposeInternal = function() { - var context = this.mapRenderer.getContext(); - context.deleteBuffer(this.renderArrayBuffer_); - ol.renderer.webgl.Layer.prototype.disposeInternal.call(this); -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.TileLayer.prototype.createLoadedTileFinder = function(source, projection, tiles) { - var mapRenderer = this.mapRenderer; - - return ( - /** - * @param {number} zoom Zoom level. - * @param {ol.TileRange} tileRange Tile range. - * @return {boolean} The tile range is fully loaded. - */ - function(zoom, tileRange) { - function callback(tile) { - var loaded = mapRenderer.isTileTextureLoaded(tile); - if (loaded) { - if (!tiles[zoom]) { - tiles[zoom] = {}; - } - tiles[zoom][tile.tileCoord.toString()] = tile; - } - return loaded; - } - return source.forEachLoadedTile(projection, zoom, tileRange, callback); - }); -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.TileLayer.prototype.handleWebGLContextLost = function() { - ol.renderer.webgl.Layer.prototype.handleWebGLContextLost.call(this); - this.locations_ = null; -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.TileLayer.prototype.prepareFrame = function(frameState, layerState, context) { - - var mapRenderer = this.mapRenderer; - var gl = context.getGL(); - - var viewState = frameState.viewState; - var projection = viewState.projection; - - var tileLayer = /** @type {ol.layer.Tile} */ (this.getLayer()); - var tileSource = tileLayer.getSource(); - var tileGrid = tileSource.getTileGridForProjection(projection); - var z = tileGrid.getZForResolution(viewState.resolution); - var tileResolution = tileGrid.getResolution(z); - - var tilePixelSize = - tileSource.getTilePixelSize(z, frameState.pixelRatio, projection); - var pixelRatio = tilePixelSize[0] / - ol.size.toSize(tileGrid.getTileSize(z), this.tmpSize_)[0]; - var tilePixelResolution = tileResolution / pixelRatio; - var tileGutter = tileSource.getTilePixelRatio(pixelRatio) * tileSource.getGutter(projection); - - var center = viewState.center; - var extent = frameState.extent; - var tileRange = tileGrid.getTileRangeForExtentAndZ(extent, z); - - var framebufferExtent; - if (this.renderedTileRange_ && - this.renderedTileRange_.equals(tileRange) && - this.renderedRevision_ == tileSource.getRevision()) { - framebufferExtent = this.renderedFramebufferExtent_; - } else { - - var tileRangeSize = tileRange.getSize(); - - var maxDimension = Math.max( - tileRangeSize[0] * tilePixelSize[0], - tileRangeSize[1] * tilePixelSize[1]); - var framebufferDimension = ol.math.roundUpToPowerOfTwo(maxDimension); - var framebufferExtentDimension = tilePixelResolution * framebufferDimension; - var origin = tileGrid.getOrigin(z); - var minX = origin[0] + - tileRange.minX * tilePixelSize[0] * tilePixelResolution; - var minY = origin[1] + - tileRange.minY * tilePixelSize[1] * tilePixelResolution; - framebufferExtent = [ - minX, minY, - minX + framebufferExtentDimension, minY + framebufferExtentDimension - ]; - - this.bindFramebuffer(frameState, framebufferDimension); - gl.viewport(0, 0, framebufferDimension, framebufferDimension); - - gl.clearColor(0, 0, 0, 0); - gl.clear(ol.webgl.COLOR_BUFFER_BIT); - gl.disable(ol.webgl.BLEND); - - var program = context.getProgram(this.fragmentShader_, this.vertexShader_); - context.useProgram(program); - if (!this.locations_) { - this.locations_ = new ol.renderer.webgl.tilelayershader.Locations(gl, program); - } - - context.bindBuffer(ol.webgl.ARRAY_BUFFER, this.renderArrayBuffer_); - gl.enableVertexAttribArray(this.locations_.a_position); - gl.vertexAttribPointer( - this.locations_.a_position, 2, ol.webgl.FLOAT, false, 16, 0); - gl.enableVertexAttribArray(this.locations_.a_texCoord); - gl.vertexAttribPointer( - this.locations_.a_texCoord, 2, ol.webgl.FLOAT, false, 16, 8); - gl.uniform1i(this.locations_.u_texture, 0); - - /** - * @type {Object.<number, Object.<string, ol.Tile>>} - */ - var tilesToDrawByZ = {}; - tilesToDrawByZ[z] = {}; - - var findLoadedTiles = this.createLoadedTileFinder( - tileSource, projection, tilesToDrawByZ); - - var useInterimTilesOnError = tileLayer.getUseInterimTilesOnError(); - var allTilesLoaded = true; - var tmpExtent = ol.extent.createEmpty(); - var tmpTileRange = new ol.TileRange(0, 0, 0, 0); - var childTileRange, drawable, fullyLoaded, tile, tileState; - var x, y, tileExtent; - for (x = tileRange.minX; x <= tileRange.maxX; ++x) { - for (y = tileRange.minY; y <= tileRange.maxY; ++y) { - - tile = tileSource.getTile(z, x, y, pixelRatio, projection); - if (layerState.extent !== undefined) { - // ignore tiles outside layer extent - tileExtent = tileGrid.getTileCoordExtent(tile.tileCoord, tmpExtent); - if (!ol.extent.intersects(tileExtent, layerState.extent)) { - continue; - } - } - tileState = tile.getState(); - drawable = tileState == ol.TileState.LOADED || - tileState == ol.TileState.EMPTY || - tileState == ol.TileState.ERROR && !useInterimTilesOnError; - if (!drawable) { - tile = tile.getInterimTile(); - } - tileState = tile.getState(); - if (tileState == ol.TileState.LOADED) { - if (mapRenderer.isTileTextureLoaded(tile)) { - tilesToDrawByZ[z][tile.tileCoord.toString()] = tile; - continue; - } - } else if (tileState == ol.TileState.EMPTY || - (tileState == ol.TileState.ERROR && - !useInterimTilesOnError)) { - continue; - } - - allTilesLoaded = false; - fullyLoaded = tileGrid.forEachTileCoordParentTileRange( - tile.tileCoord, findLoadedTiles, null, tmpTileRange, tmpExtent); - if (!fullyLoaded) { - childTileRange = tileGrid.getTileCoordChildTileRange( - tile.tileCoord, tmpTileRange, tmpExtent); - if (childTileRange) { - findLoadedTiles(z + 1, childTileRange); - } - } - - } - - } - - /** @type {Array.<number>} */ - var zs = Object.keys(tilesToDrawByZ).map(Number); - zs.sort(ol.array.numberSafeCompareFunction); - var u_tileOffset = new Float32Array(4); - var i, ii, tileKey, tilesToDraw; - for (i = 0, ii = zs.length; i < ii; ++i) { - tilesToDraw = tilesToDrawByZ[zs[i]]; - for (tileKey in tilesToDraw) { - tile = tilesToDraw[tileKey]; - tileExtent = tileGrid.getTileCoordExtent(tile.tileCoord, tmpExtent); - u_tileOffset[0] = 2 * (tileExtent[2] - tileExtent[0]) / - framebufferExtentDimension; - u_tileOffset[1] = 2 * (tileExtent[3] - tileExtent[1]) / - framebufferExtentDimension; - u_tileOffset[2] = 2 * (tileExtent[0] - framebufferExtent[0]) / - framebufferExtentDimension - 1; - u_tileOffset[3] = 2 * (tileExtent[1] - framebufferExtent[1]) / - framebufferExtentDimension - 1; - gl.uniform4fv(this.locations_.u_tileOffset, u_tileOffset); - mapRenderer.bindTileTexture(tile, tilePixelSize, - tileGutter * pixelRatio, ol.webgl.LINEAR, ol.webgl.LINEAR); - gl.drawArrays(ol.webgl.TRIANGLE_STRIP, 0, 4); - } - } - - if (allTilesLoaded) { - this.renderedTileRange_ = tileRange; - this.renderedFramebufferExtent_ = framebufferExtent; - this.renderedRevision_ = tileSource.getRevision(); - } else { - this.renderedTileRange_ = null; - this.renderedFramebufferExtent_ = null; - this.renderedRevision_ = -1; - frameState.animate = true; - } - - } - - this.updateUsedTiles(frameState.usedTiles, tileSource, z, tileRange); - var tileTextureQueue = mapRenderer.getTileTextureQueue(); - this.manageTilePyramid( - frameState, tileSource, tileGrid, pixelRatio, projection, extent, z, - tileLayer.getPreload(), - /** - * @param {ol.Tile} tile Tile. - */ - function(tile) { - if (tile.getState() == ol.TileState.LOADED && - !mapRenderer.isTileTextureLoaded(tile) && - !tileTextureQueue.isKeyQueued(tile.getKey())) { - tileTextureQueue.enqueue([ - tile, - tileGrid.getTileCoordCenter(tile.tileCoord), - tileGrid.getResolution(tile.tileCoord[0]), - tilePixelSize, tileGutter * pixelRatio - ]); - } - }, this); - this.scheduleExpireCache(frameState, tileSource); - this.updateLogos(frameState, tileSource); - - var texCoordMatrix = this.texCoordMatrix; - ol.transform.reset(texCoordMatrix); - ol.transform.translate(texCoordMatrix, - (Math.round(center[0] / tileResolution) * tileResolution - framebufferExtent[0]) / - (framebufferExtent[2] - framebufferExtent[0]), - (Math.round(center[1] / tileResolution) * tileResolution - framebufferExtent[1]) / - (framebufferExtent[3] - framebufferExtent[1])); - if (viewState.rotation !== 0) { - ol.transform.rotate(texCoordMatrix, viewState.rotation); - } - ol.transform.scale(texCoordMatrix, - frameState.size[0] * viewState.resolution / - (framebufferExtent[2] - framebufferExtent[0]), - frameState.size[1] * viewState.resolution / - (framebufferExtent[3] - framebufferExtent[1])); - ol.transform.translate(texCoordMatrix, -0.5, -0.5); - - return true; -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.TileLayer.prototype.forEachLayerAtPixel = function(pixel, frameState, callback, thisArg) { - if (!this.framebuffer) { - return undefined; - } - - var pixelOnMapScaled = [ - pixel[0] / frameState.size[0], - (frameState.size[1] - pixel[1]) / frameState.size[1]]; - - var pixelOnFrameBufferScaled = ol.transform.apply( - this.texCoordMatrix, pixelOnMapScaled.slice()); - var pixelOnFrameBuffer = [ - pixelOnFrameBufferScaled[0] * this.framebufferDimension, - pixelOnFrameBufferScaled[1] * this.framebufferDimension]; - - var gl = this.mapRenderer.getContext().getGL(); - gl.bindFramebuffer(gl.FRAMEBUFFER, this.framebuffer); - var imageData = new Uint8Array(4); - gl.readPixels(pixelOnFrameBuffer[0], pixelOnFrameBuffer[1], 1, 1, - gl.RGBA, gl.UNSIGNED_BYTE, imageData); - - if (imageData[3] > 0) { - return callback.call(thisArg, this.getLayer(), imageData); - } else { - return undefined; - } -}; - -goog.provide('ol.renderer.webgl.VectorLayer'); - -goog.require('ol'); -goog.require('ol.LayerType'); -goog.require('ol.ViewHint'); -goog.require('ol.extent'); -goog.require('ol.render.webgl.ReplayGroup'); -goog.require('ol.renderer.Type'); -goog.require('ol.renderer.vector'); -goog.require('ol.renderer.webgl.Layer'); -goog.require('ol.transform'); - - -/** - * @constructor - * @extends {ol.renderer.webgl.Layer} - * @param {ol.renderer.webgl.Map} mapRenderer Map renderer. - * @param {ol.layer.Vector} vectorLayer Vector layer. - * @api - */ -ol.renderer.webgl.VectorLayer = function(mapRenderer, vectorLayer) { - - ol.renderer.webgl.Layer.call(this, mapRenderer, vectorLayer); - - /** - * @private - * @type {boolean} - */ - this.dirty_ = false; - - /** - * @private - * @type {number} - */ - this.renderedRevision_ = -1; - - /** - * @private - * @type {number} - */ - this.renderedResolution_ = NaN; - - /** - * @private - * @type {ol.Extent} - */ - this.renderedExtent_ = ol.extent.createEmpty(); - - /** - * @private - * @type {function(ol.Feature, ol.Feature): number|null} - */ - this.renderedRenderOrder_ = null; - - /** - * @private - * @type {ol.render.webgl.ReplayGroup} - */ - this.replayGroup_ = null; - - /** - * The last layer state. - * @private - * @type {?ol.LayerState} - */ - this.layerState_ = null; - -}; -ol.inherits(ol.renderer.webgl.VectorLayer, ol.renderer.webgl.Layer); - - -/** - * Determine if this renderer handles the provided layer. - * @param {ol.renderer.Type} type The renderer type. - * @param {ol.layer.Layer} layer The candidate layer. - * @return {boolean} The renderer can render the layer. - */ -ol.renderer.webgl.VectorLayer['handles'] = function(type, layer) { - return type === ol.renderer.Type.WEBGL && layer.getType() === ol.LayerType.VECTOR; -}; - - -/** - * Create a layer renderer. - * @param {ol.renderer.Map} mapRenderer The map renderer. - * @param {ol.layer.Layer} layer The layer to be rendererd. - * @return {ol.renderer.webgl.VectorLayer} The layer renderer. - */ -ol.renderer.webgl.VectorLayer['create'] = function(mapRenderer, layer) { - return new ol.renderer.webgl.VectorLayer( - /** @type {ol.renderer.webgl.Map} */ (mapRenderer), - /** @type {ol.layer.Vector} */ (layer) - ); -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.VectorLayer.prototype.composeFrame = function(frameState, layerState, context) { - this.layerState_ = layerState; - var viewState = frameState.viewState; - var replayGroup = this.replayGroup_; - var size = frameState.size; - var pixelRatio = frameState.pixelRatio; - var gl = this.mapRenderer.getGL(); - if (replayGroup && !replayGroup.isEmpty()) { - gl.enable(gl.SCISSOR_TEST); - gl.scissor(0, 0, size[0] * pixelRatio, size[1] * pixelRatio); - replayGroup.replay(context, - viewState.center, viewState.resolution, viewState.rotation, - size, pixelRatio, layerState.opacity, - layerState.managed ? frameState.skippedFeatureUids : {}); - gl.disable(gl.SCISSOR_TEST); - } - -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.VectorLayer.prototype.disposeInternal = function() { - var replayGroup = this.replayGroup_; - if (replayGroup) { - var context = this.mapRenderer.getContext(); - replayGroup.getDeleteResourcesFunction(context)(); - this.replayGroup_ = null; - } - ol.renderer.webgl.Layer.prototype.disposeInternal.call(this); -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.VectorLayer.prototype.forEachFeatureAtCoordinate = function(coordinate, frameState, hitTolerance, callback, thisArg) { - if (!this.replayGroup_ || !this.layerState_) { - return undefined; - } else { - var context = this.mapRenderer.getContext(); - var viewState = frameState.viewState; - var layer = this.getLayer(); - var layerState = this.layerState_; - /** @type {Object.<string, boolean>} */ - var features = {}; - return this.replayGroup_.forEachFeatureAtCoordinate(coordinate, - context, viewState.center, viewState.resolution, viewState.rotation, - frameState.size, frameState.pixelRatio, layerState.opacity, - {}, - /** - * @param {ol.Feature|ol.render.Feature} feature Feature. - * @return {?} Callback result. - */ - function(feature) { - var key = ol.getUid(feature).toString(); - if (!(key in features)) { - features[key] = true; - return callback.call(thisArg, feature, layer); - } - }); - } -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.VectorLayer.prototype.hasFeatureAtCoordinate = function(coordinate, frameState) { - if (!this.replayGroup_ || !this.layerState_) { - return false; - } else { - var context = this.mapRenderer.getContext(); - var viewState = frameState.viewState; - var layerState = this.layerState_; - return this.replayGroup_.hasFeatureAtCoordinate(coordinate, - context, viewState.center, viewState.resolution, viewState.rotation, - frameState.size, frameState.pixelRatio, layerState.opacity, - frameState.skippedFeatureUids); - } -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.VectorLayer.prototype.forEachLayerAtPixel = function(pixel, frameState, callback, thisArg) { - var coordinate = ol.transform.apply( - frameState.pixelToCoordinateTransform, pixel.slice()); - var hasFeature = this.hasFeatureAtCoordinate(coordinate, frameState); - - if (hasFeature) { - return callback.call(thisArg, this.getLayer(), null); - } else { - return undefined; - } -}; - - -/** - * Handle changes in image style state. - * @param {ol.events.Event} event Image style change event. - * @private - */ -ol.renderer.webgl.VectorLayer.prototype.handleStyleImageChange_ = function(event) { - this.renderIfReadyAndVisible(); -}; - - -/** - * @inheritDoc - */ -ol.renderer.webgl.VectorLayer.prototype.prepareFrame = function(frameState, layerState, context) { - - var vectorLayer = /** @type {ol.layer.Vector} */ (this.getLayer()); - var vectorSource = vectorLayer.getSource(); - - this.updateAttributions( - frameState.attributions, vectorSource.getAttributions()); - this.updateLogos(frameState, vectorSource); - - var animating = frameState.viewHints[ol.ViewHint.ANIMATING]; - var interacting = frameState.viewHints[ol.ViewHint.INTERACTING]; - var updateWhileAnimating = vectorLayer.getUpdateWhileAnimating(); - var updateWhileInteracting = vectorLayer.getUpdateWhileInteracting(); - - if (!this.dirty_ && (!updateWhileAnimating && animating) || - (!updateWhileInteracting && interacting)) { - return true; - } - - var frameStateExtent = frameState.extent; - var viewState = frameState.viewState; - var projection = viewState.projection; - var resolution = viewState.resolution; - var pixelRatio = frameState.pixelRatio; - var vectorLayerRevision = vectorLayer.getRevision(); - var vectorLayerRenderBuffer = vectorLayer.getRenderBuffer(); - var vectorLayerRenderOrder = vectorLayer.getRenderOrder(); - - if (vectorLayerRenderOrder === undefined) { - vectorLayerRenderOrder = ol.renderer.vector.defaultOrder; - } - - var extent = ol.extent.buffer(frameStateExtent, - vectorLayerRenderBuffer * resolution); - - if (!this.dirty_ && - this.renderedResolution_ == resolution && - this.renderedRevision_ == vectorLayerRevision && - this.renderedRenderOrder_ == vectorLayerRenderOrder && - ol.extent.containsExtent(this.renderedExtent_, extent)) { - return true; - } - - if (this.replayGroup_) { - frameState.postRenderFunctions.push( - this.replayGroup_.getDeleteResourcesFunction(context)); - } - - this.dirty_ = false; - - var replayGroup = new ol.render.webgl.ReplayGroup( - ol.renderer.vector.getTolerance(resolution, pixelRatio), - extent, vectorLayer.getRenderBuffer()); - vectorSource.loadFeatures(extent, resolution, projection); - /** - * @param {ol.Feature} feature Feature. - * @this {ol.renderer.webgl.VectorLayer} - */ - var renderFeature = function(feature) { - var styles; - var styleFunction = feature.getStyleFunction(); - if (styleFunction) { - styles = styleFunction.call(feature, resolution); - } else { - styleFunction = vectorLayer.getStyleFunction(); - if (styleFunction) { - styles = styleFunction(feature, resolution); - } - } - if (styles) { - var dirty = this.renderFeature( - feature, resolution, pixelRatio, styles, replayGroup); - this.dirty_ = this.dirty_ || dirty; - } - }; - if (vectorLayerRenderOrder) { - /** @type {Array.<ol.Feature>} */ - var features = []; - vectorSource.forEachFeatureInExtent(extent, - /** - * @param {ol.Feature} feature Feature. - */ - function(feature) { - features.push(feature); - }, this); - features.sort(vectorLayerRenderOrder); - features.forEach(renderFeature, this); - } else { - vectorSource.forEachFeatureInExtent(extent, renderFeature, this); - } - replayGroup.finish(context); - - this.renderedResolution_ = resolution; - this.renderedRevision_ = vectorLayerRevision; - this.renderedRenderOrder_ = vectorLayerRenderOrder; - this.renderedExtent_ = extent; - this.replayGroup_ = replayGroup; - - return true; -}; - - -/** - * @param {ol.Feature} feature Feature. - * @param {number} resolution Resolution. - * @param {number} pixelRatio Pixel ratio. - * @param {(ol.style.Style|Array.<ol.style.Style>)} styles The style or array of - * styles. - * @param {ol.render.webgl.ReplayGroup} replayGroup Replay group. - * @return {boolean} `true` if an image is loading. - */ -ol.renderer.webgl.VectorLayer.prototype.renderFeature = function(feature, resolution, pixelRatio, styles, replayGroup) { - if (!styles) { - return false; - } - var loading = false; - if (Array.isArray(styles)) { - for (var i = styles.length - 1, ii = 0; i >= ii; --i) { - loading = ol.renderer.vector.renderFeature( - replayGroup, feature, styles[i], - ol.renderer.vector.getSquaredTolerance(resolution, pixelRatio), - this.handleStyleImageChange_, this) || loading; - } - } else { - loading = ol.renderer.vector.renderFeature( - replayGroup, feature, styles, - ol.renderer.vector.getSquaredTolerance(resolution, pixelRatio), - this.handleStyleImageChange_, this) || loading; - } - return loading; -}; - -goog.provide('ol.Map'); - -goog.require('ol'); -goog.require('ol.PluggableMap'); -goog.require('ol.PluginType'); -goog.require('ol.control'); -goog.require('ol.interaction'); -goog.require('ol.obj'); -goog.require('ol.plugins'); -goog.require('ol.renderer.canvas.ImageLayer'); -goog.require('ol.renderer.canvas.Map'); -goog.require('ol.renderer.canvas.TileLayer'); -goog.require('ol.renderer.canvas.VectorLayer'); -goog.require('ol.renderer.canvas.VectorTileLayer'); -goog.require('ol.renderer.webgl.ImageLayer'); -goog.require('ol.renderer.webgl.Map'); -goog.require('ol.renderer.webgl.TileLayer'); -goog.require('ol.renderer.webgl.VectorLayer'); - - -if (ol.ENABLE_CANVAS) { - ol.plugins.register(ol.PluginType.MAP_RENDERER, ol.renderer.canvas.Map); - ol.plugins.registerMultiple(ol.PluginType.LAYER_RENDERER, [ - ol.renderer.canvas.ImageLayer, - ol.renderer.canvas.TileLayer, - ol.renderer.canvas.VectorLayer, - ol.renderer.canvas.VectorTileLayer - ]); -} - -if (ol.ENABLE_WEBGL) { - ol.plugins.register(ol.PluginType.MAP_RENDERER, ol.renderer.webgl.Map); - ol.plugins.registerMultiple(ol.PluginType.LAYER_RENDERER, [ - ol.renderer.webgl.ImageLayer, - ol.renderer.webgl.TileLayer, - ol.renderer.webgl.VectorLayer - ]); -} - - -/** - * @classdesc - * The map is the core component of OpenLayers. For a map to render, a view, - * one or more layers, and a target container are needed: - * - * var map = new ol.Map({ - * view: new ol.View({ - * center: [0, 0], - * zoom: 1 - * }), - * layers: [ - * new ol.layer.Tile({ - * source: new ol.source.OSM() - * }) - * ], - * target: 'map' - * }); - * - * The above snippet creates a map using a {@link ol.layer.Tile} to display - * {@link ol.source.OSM} OSM data and render it to a DOM element with the - * id `map`. - * - * The constructor places a viewport container (with CSS class name - * `ol-viewport`) in the target element (see `getViewport()`), and then two - * further elements within the viewport: one with CSS class name - * `ol-overlaycontainer-stopevent` for controls and some overlays, and one with - * CSS class name `ol-overlaycontainer` for other overlays (see the `stopEvent` - * option of {@link ol.Overlay} for the difference). The map itself is placed in - * a further element within the viewport. - * - * Layers are stored as a `ol.Collection` in layerGroups. A top-level group is - * provided by the library. This is what is accessed by `getLayerGroup` and - * `setLayerGroup`. Layers entered in the options are added to this group, and - * `addLayer` and `removeLayer` change the layer collection in the group. - * `getLayers` is a convenience function for `getLayerGroup().getLayers()`. - * Note that `ol.layer.Group` is a subclass of `ol.layer.Base`, so layers - * entered in the options or added with `addLayer` can be groups, which can - * contain further groups, and so on. - * - * @constructor - * @extends {ol.PluggableMap} - * @param {olx.MapOptions} options Map options. - * @fires ol.MapBrowserEvent - * @fires ol.MapEvent - * @fires ol.render.Event#postcompose - * @fires ol.render.Event#precompose - * @api - */ -ol.Map = function(options) { - options = ol.obj.assign({}, options); - if (!options.controls) { - options.controls = ol.control.defaults(); - } - if (!options.interactions) { - options.interactions = ol.interaction.defaults(); - } - - ol.PluggableMap.call(this, options); -}; -ol.inherits(ol.Map, ol.PluggableMap); - -goog.provide('ol.net'); - -goog.require('ol'); - - -/** - * Simple JSONP helper. Supports error callbacks and a custom callback param. - * The error callback will be called when no JSONP is executed after 10 seconds. - * - * @param {string} url Request url. A 'callback' query parameter will be - * appended. - * @param {Function} callback Callback on success. - * @param {function()=} opt_errback Callback on error. - * @param {string=} opt_callbackParam Custom query parameter for the JSONP - * callback. Default is 'callback'. - */ -ol.net.jsonp = function(url, callback, opt_errback, opt_callbackParam) { - var script = document.createElement('script'); - var key = 'olc_' + ol.getUid(callback); - function cleanup() { - delete window[key]; - script.parentNode.removeChild(script); - } - script.async = true; - script.src = url + (url.indexOf('?') == -1 ? '?' : '&') + - (opt_callbackParam || 'callback') + '=' + key; - var timer = setTimeout(function() { - cleanup(); - if (opt_errback) { - opt_errback(); - } - }, 10000); - window[key] = function(data) { - clearTimeout(timer); - cleanup(); - callback(data); - }; - document.getElementsByTagName('head')[0].appendChild(script); -}; - -goog.provide('ol.proj.common'); - -goog.require('ol.proj'); - - -/** - * Deprecated. Transforms between EPSG:4326 and EPSG:3857 are now included by - * default. There is no need to call this function in application code and it - * will be removed in a future major release. - * @deprecated This function is no longer necessary. - * @api - */ -ol.proj.common.add = ol.proj.addCommon; - -goog.provide('ol.render'); - -goog.require('ol.has'); -goog.require('ol.transform'); -goog.require('ol.render.canvas.Immediate'); - - -/** - * Binds a Canvas Immediate API to a canvas context, to allow drawing geometries - * to the context's canvas. - * - * The units for geometry coordinates are css pixels relative to the top left - * corner of the canvas element. - * ```js - * var canvas = document.createElement('canvas'); - * var render = ol.render.toContext(canvas.getContext('2d'), - * { size: [100, 100] }); - * render.setFillStrokeStyle(new ol.style.Fill({ color: blue })); - * render.drawPolygon( - * new ol.geom.Polygon([[[0, 0], [100, 100], [100, 0], [0, 0]]])); - * ``` - * - * @param {CanvasRenderingContext2D} context Canvas context. - * @param {olx.render.ToContextOptions=} opt_options Options. - * @return {ol.render.canvas.Immediate} Canvas Immediate. - * @api - */ -ol.render.toContext = function(context, opt_options) { - var canvas = context.canvas; - var options = opt_options ? opt_options : {}; - var pixelRatio = options.pixelRatio || ol.has.DEVICE_PIXEL_RATIO; - var size = options.size; - if (size) { - canvas.width = size[0] * pixelRatio; - canvas.height = size[1] * pixelRatio; - canvas.style.width = size[0] + 'px'; - canvas.style.height = size[1] + 'px'; - } - var extent = [0, 0, canvas.width, canvas.height]; - var transform = ol.transform.scale(ol.transform.create(), pixelRatio, pixelRatio); - return new ol.render.canvas.Immediate(context, pixelRatio, extent, transform, - 0); -}; - -goog.provide('ol.reproj.Tile'); - -goog.require('ol'); -goog.require('ol.Tile'); -goog.require('ol.TileState'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.extent'); -goog.require('ol.math'); -goog.require('ol.reproj'); -goog.require('ol.reproj.Triangulation'); - - -/** - * @classdesc - * Class encapsulating single reprojected tile. - * See {@link ol.source.TileImage}. - * - * @constructor - * @extends {ol.Tile} - * @param {ol.proj.Projection} sourceProj Source projection. - * @param {ol.tilegrid.TileGrid} sourceTileGrid Source tile grid. - * @param {ol.proj.Projection} targetProj Target projection. - * @param {ol.tilegrid.TileGrid} targetTileGrid Target tile grid. - * @param {ol.TileCoord} tileCoord Coordinate of the tile. - * @param {ol.TileCoord} wrappedTileCoord Coordinate of the tile wrapped in X. - * @param {number} pixelRatio Pixel ratio. - * @param {number} gutter Gutter of the source tiles. - * @param {ol.ReprojTileFunctionType} getTileFunction - * Function returning source tiles (z, x, y, pixelRatio). - * @param {number=} opt_errorThreshold Acceptable reprojection error (in px). - * @param {boolean=} opt_renderEdges Render reprojection edges. - */ -ol.reproj.Tile = function(sourceProj, sourceTileGrid, - targetProj, targetTileGrid, tileCoord, wrappedTileCoord, - pixelRatio, gutter, getTileFunction, - opt_errorThreshold, opt_renderEdges) { - ol.Tile.call(this, tileCoord, ol.TileState.IDLE); - - /** - * @private - * @type {boolean} - */ - this.renderEdges_ = opt_renderEdges !== undefined ? opt_renderEdges : false; - - /** - * @private - * @type {number} - */ - this.pixelRatio_ = pixelRatio; - - /** - * @private - * @type {number} - */ - this.gutter_ = gutter; - - /** - * @private - * @type {HTMLCanvasElement} - */ - this.canvas_ = null; - - /** - * @private - * @type {ol.tilegrid.TileGrid} - */ - this.sourceTileGrid_ = sourceTileGrid; - - /** - * @private - * @type {ol.tilegrid.TileGrid} - */ - this.targetTileGrid_ = targetTileGrid; - - /** - * @private - * @type {ol.TileCoord} - */ - this.wrappedTileCoord_ = wrappedTileCoord ? wrappedTileCoord : tileCoord; - - /** - * @private - * @type {!Array.<ol.Tile>} - */ - this.sourceTiles_ = []; - - /** - * @private - * @type {Array.<ol.EventsKey>} - */ - this.sourcesListenerKeys_ = null; - - /** - * @private - * @type {number} - */ - this.sourceZ_ = 0; - - var targetExtent = targetTileGrid.getTileCoordExtent(this.wrappedTileCoord_); - var maxTargetExtent = this.targetTileGrid_.getExtent(); - var maxSourceExtent = this.sourceTileGrid_.getExtent(); - - var limitedTargetExtent = maxTargetExtent ? - ol.extent.getIntersection(targetExtent, maxTargetExtent) : targetExtent; - - if (ol.extent.getArea(limitedTargetExtent) === 0) { - // Tile is completely outside range -> EMPTY - // TODO: is it actually correct that the source even creates the tile ? - this.state = ol.TileState.EMPTY; - return; - } - - var sourceProjExtent = sourceProj.getExtent(); - if (sourceProjExtent) { - if (!maxSourceExtent) { - maxSourceExtent = sourceProjExtent; - } else { - maxSourceExtent = ol.extent.getIntersection( - maxSourceExtent, sourceProjExtent); - } - } - - var targetResolution = targetTileGrid.getResolution( - this.wrappedTileCoord_[0]); - - var targetCenter = ol.extent.getCenter(limitedTargetExtent); - var sourceResolution = ol.reproj.calculateSourceResolution( - sourceProj, targetProj, targetCenter, targetResolution); - - if (!isFinite(sourceResolution) || sourceResolution <= 0) { - // invalid sourceResolution -> EMPTY - // probably edges of the projections when no extent is defined - this.state = ol.TileState.EMPTY; - return; - } - - var errorThresholdInPixels = opt_errorThreshold !== undefined ? - opt_errorThreshold : ol.DEFAULT_RASTER_REPROJECTION_ERROR_THRESHOLD; - - /** - * @private - * @type {!ol.reproj.Triangulation} - */ - this.triangulation_ = new ol.reproj.Triangulation( - sourceProj, targetProj, limitedTargetExtent, maxSourceExtent, - sourceResolution * errorThresholdInPixels); - - if (this.triangulation_.getTriangles().length === 0) { - // no valid triangles -> EMPTY - this.state = ol.TileState.EMPTY; - return; - } - - this.sourceZ_ = sourceTileGrid.getZForResolution(sourceResolution); - var sourceExtent = this.triangulation_.calculateSourceExtent(); - - if (maxSourceExtent) { - if (sourceProj.canWrapX()) { - sourceExtent[1] = ol.math.clamp( - sourceExtent[1], maxSourceExtent[1], maxSourceExtent[3]); - sourceExtent[3] = ol.math.clamp( - sourceExtent[3], maxSourceExtent[1], maxSourceExtent[3]); - } else { - sourceExtent = ol.extent.getIntersection(sourceExtent, maxSourceExtent); - } - } - - if (!ol.extent.getArea(sourceExtent)) { - this.state = ol.TileState.EMPTY; - } else { - var sourceRange = sourceTileGrid.getTileRangeForExtentAndZ( - sourceExtent, this.sourceZ_); - - for (var srcX = sourceRange.minX; srcX <= sourceRange.maxX; srcX++) { - for (var srcY = sourceRange.minY; srcY <= sourceRange.maxY; srcY++) { - var tile = getTileFunction(this.sourceZ_, srcX, srcY, pixelRatio); - if (tile) { - this.sourceTiles_.push(tile); - } - } - } - - if (this.sourceTiles_.length === 0) { - this.state = ol.TileState.EMPTY; - } - } -}; -ol.inherits(ol.reproj.Tile, ol.Tile); - - -/** - * @inheritDoc - */ -ol.reproj.Tile.prototype.disposeInternal = function() { - if (this.state == ol.TileState.LOADING) { - this.unlistenSources_(); - } - ol.Tile.prototype.disposeInternal.call(this); -}; - - -/** - * Get the HTML Canvas element for this tile. - * @return {HTMLCanvasElement} Canvas. - */ -ol.reproj.Tile.prototype.getImage = function() { - return this.canvas_; -}; - - -/** - * @private - */ -ol.reproj.Tile.prototype.reproject_ = function() { - var sources = []; - this.sourceTiles_.forEach(function(tile, i, arr) { - if (tile && tile.getState() == ol.TileState.LOADED) { - sources.push({ - extent: this.sourceTileGrid_.getTileCoordExtent(tile.tileCoord), - image: tile.getImage() - }); - } - }, this); - this.sourceTiles_.length = 0; - - if (sources.length === 0) { - this.state = ol.TileState.ERROR; - } else { - var z = this.wrappedTileCoord_[0]; - var size = this.targetTileGrid_.getTileSize(z); - var width = typeof size === 'number' ? size : size[0]; - var height = typeof size === 'number' ? size : size[1]; - var targetResolution = this.targetTileGrid_.getResolution(z); - var sourceResolution = this.sourceTileGrid_.getResolution(this.sourceZ_); - - var targetExtent = this.targetTileGrid_.getTileCoordExtent( - this.wrappedTileCoord_); - this.canvas_ = ol.reproj.render(width, height, this.pixelRatio_, - sourceResolution, this.sourceTileGrid_.getExtent(), - targetResolution, targetExtent, this.triangulation_, sources, - this.gutter_, this.renderEdges_); - - this.state = ol.TileState.LOADED; - } - this.changed(); -}; - - -/** - * @inheritDoc - */ -ol.reproj.Tile.prototype.load = function() { - if (this.state == ol.TileState.IDLE) { - this.state = ol.TileState.LOADING; - this.changed(); - - var leftToLoad = 0; - - this.sourcesListenerKeys_ = []; - this.sourceTiles_.forEach(function(tile, i, arr) { - var state = tile.getState(); - if (state == ol.TileState.IDLE || state == ol.TileState.LOADING) { - leftToLoad++; - - var sourceListenKey; - sourceListenKey = ol.events.listen(tile, ol.events.EventType.CHANGE, - function(e) { - var state = tile.getState(); - if (state == ol.TileState.LOADED || - state == ol.TileState.ERROR || - state == ol.TileState.EMPTY) { - ol.events.unlistenByKey(sourceListenKey); - leftToLoad--; - if (leftToLoad === 0) { - this.unlistenSources_(); - this.reproject_(); - } - } - }, this); - this.sourcesListenerKeys_.push(sourceListenKey); - } - }, this); - - this.sourceTiles_.forEach(function(tile, i, arr) { - var state = tile.getState(); - if (state == ol.TileState.IDLE) { - tile.load(); - } - }); - - if (leftToLoad === 0) { - setTimeout(this.reproject_.bind(this), 0); - } - } -}; - - -/** - * @private - */ -ol.reproj.Tile.prototype.unlistenSources_ = function() { - this.sourcesListenerKeys_.forEach(ol.events.unlistenByKey); - this.sourcesListenerKeys_ = null; -}; - -goog.provide('ol.TileUrlFunction'); - -goog.require('ol.asserts'); -goog.require('ol.math'); -goog.require('ol.tilecoord'); - - -/** - * @param {string} template Template. - * @param {ol.tilegrid.TileGrid} tileGrid Tile grid. - * @return {ol.TileUrlFunctionType} Tile URL function. - */ -ol.TileUrlFunction.createFromTemplate = function(template, tileGrid) { - var zRegEx = /\{z\}/g; - var xRegEx = /\{x\}/g; - var yRegEx = /\{y\}/g; - var dashYRegEx = /\{-y\}/g; - return ( - /** - * @param {ol.TileCoord} tileCoord Tile Coordinate. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.proj.Projection} projection Projection. - * @return {string|undefined} Tile URL. - */ - function(tileCoord, pixelRatio, projection) { - if (!tileCoord) { - return undefined; - } else { - return template.replace(zRegEx, tileCoord[0].toString()) - .replace(xRegEx, tileCoord[1].toString()) - .replace(yRegEx, function() { - var y = -tileCoord[2] - 1; - return y.toString(); - }) - .replace(dashYRegEx, function() { - var z = tileCoord[0]; - var range = tileGrid.getFullTileRange(z); - ol.asserts.assert(range, 55); // The {-y} placeholder requires a tile grid with extent - var y = range.getHeight() + tileCoord[2]; - return y.toString(); - }); - } - }); -}; - - -/** - * @param {Array.<string>} templates Templates. - * @param {ol.tilegrid.TileGrid} tileGrid Tile grid. - * @return {ol.TileUrlFunctionType} Tile URL function. - */ -ol.TileUrlFunction.createFromTemplates = function(templates, tileGrid) { - var len = templates.length; - var tileUrlFunctions = new Array(len); - for (var i = 0; i < len; ++i) { - tileUrlFunctions[i] = ol.TileUrlFunction.createFromTemplate( - templates[i], tileGrid); - } - return ol.TileUrlFunction.createFromTileUrlFunctions(tileUrlFunctions); -}; - - -/** - * @param {Array.<ol.TileUrlFunctionType>} tileUrlFunctions Tile URL Functions. - * @return {ol.TileUrlFunctionType} Tile URL function. - */ -ol.TileUrlFunction.createFromTileUrlFunctions = function(tileUrlFunctions) { - if (tileUrlFunctions.length === 1) { - return tileUrlFunctions[0]; - } - return ( - /** - * @param {ol.TileCoord} tileCoord Tile Coordinate. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.proj.Projection} projection Projection. - * @return {string|undefined} Tile URL. - */ - function(tileCoord, pixelRatio, projection) { - if (!tileCoord) { - return undefined; - } else { - var h = ol.tilecoord.hash(tileCoord); - var index = ol.math.modulo(h, tileUrlFunctions.length); - return tileUrlFunctions[index](tileCoord, pixelRatio, projection); - } - }); -}; - - -/** - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.proj.Projection} projection Projection. - * @return {string|undefined} Tile URL. - */ -ol.TileUrlFunction.nullTileUrlFunction = function(tileCoord, pixelRatio, projection) { - return undefined; -}; - - -/** - * @param {string} url URL. - * @return {Array.<string>} Array of urls. - */ -ol.TileUrlFunction.expandUrl = function(url) { - var urls = []; - var match = /\{([a-z])-([a-z])\}/.exec(url); - if (match) { - // char range - var startCharCode = match[1].charCodeAt(0); - var stopCharCode = match[2].charCodeAt(0); - var charCode; - for (charCode = startCharCode; charCode <= stopCharCode; ++charCode) { - urls.push(url.replace(match[0], String.fromCharCode(charCode))); - } - return urls; - } - match = match = /\{(\d+)-(\d+)\}/.exec(url); - if (match) { - // number range - var stop = parseInt(match[2], 10); - for (var i = parseInt(match[1], 10); i <= stop; i++) { - urls.push(url.replace(match[0], i.toString())); - } - return urls; - } - urls.push(url); - return urls; -}; - -goog.provide('ol.TileCache'); - -goog.require('ol'); -goog.require('ol.structs.LRUCache'); -goog.require('ol.tilecoord'); - - -/** - * @constructor - * @extends {ol.structs.LRUCache.<ol.Tile>} - * @param {number=} opt_highWaterMark High water mark. - * @struct - */ -ol.TileCache = function(opt_highWaterMark) { - - ol.structs.LRUCache.call(this, opt_highWaterMark); - -}; -ol.inherits(ol.TileCache, ol.structs.LRUCache); - - -/** - * @param {Object.<string, ol.TileRange>} usedTiles Used tiles. - */ -ol.TileCache.prototype.expireCache = function(usedTiles) { - var tile, zKey; - while (this.canExpireCache()) { - tile = this.peekLast(); - zKey = tile.tileCoord[0].toString(); - if (zKey in usedTiles && usedTiles[zKey].contains(tile.tileCoord)) { - break; - } else { - this.pop().dispose(); - } - } -}; - - -/** - * Prune all tiles from the cache that don't have the same z as the newest tile. - */ -ol.TileCache.prototype.pruneExceptNewestZ = function() { - if (this.getCount() === 0) { - return; - } - var key = this.peekFirstKey(); - var tileCoord = ol.tilecoord.fromKey(key); - var z = tileCoord[0]; - this.forEach(function(tile) { - if (tile.tileCoord[0] !== z) { - this.remove(ol.tilecoord.getKey(tile.tileCoord)); - tile.dispose(); - } - }, this); -}; - -goog.provide('ol.source.Tile'); - -goog.require('ol'); -goog.require('ol.TileCache'); -goog.require('ol.TileState'); -goog.require('ol.events.Event'); -goog.require('ol.proj'); -goog.require('ol.size'); -goog.require('ol.source.Source'); -goog.require('ol.tilecoord'); -goog.require('ol.tilegrid'); - - -/** - * @classdesc - * Abstract base class; normally only used for creating subclasses and not - * instantiated in apps. - * Base class for sources providing images divided into a tile grid. - * - * @constructor - * @abstract - * @extends {ol.source.Source} - * @param {ol.SourceTileOptions} options Tile source options. - * @api - */ -ol.source.Tile = function(options) { - - ol.source.Source.call(this, { - attributions: options.attributions, - extent: options.extent, - logo: options.logo, - projection: options.projection, - state: options.state, - wrapX: options.wrapX - }); - - /** - * @private - * @type {boolean} - */ - this.opaque_ = options.opaque !== undefined ? options.opaque : false; - - /** - * @private - * @type {number} - */ - this.tilePixelRatio_ = options.tilePixelRatio !== undefined ? - options.tilePixelRatio : 1; - - /** - * @protected - * @type {ol.tilegrid.TileGrid} - */ - this.tileGrid = options.tileGrid !== undefined ? options.tileGrid : null; - - /** - * @protected - * @type {ol.TileCache} - */ - this.tileCache = new ol.TileCache(options.cacheSize); - - /** - * @protected - * @type {ol.Size} - */ - this.tmpSize = [0, 0]; - - /** - * @private - * @type {string} - */ - this.key_ = ''; - - /** - * @protected - * @type {olx.TileOptions} - */ - this.tileOptions = {transition: options.transition}; - -}; -ol.inherits(ol.source.Tile, ol.source.Source); - - -/** - * @return {boolean} Can expire cache. - */ -ol.source.Tile.prototype.canExpireCache = function() { - return this.tileCache.canExpireCache(); -}; - - -/** - * @param {ol.proj.Projection} projection Projection. - * @param {Object.<string, ol.TileRange>} usedTiles Used tiles. - */ -ol.source.Tile.prototype.expireCache = function(projection, usedTiles) { - var tileCache = this.getTileCacheForProjection(projection); - if (tileCache) { - tileCache.expireCache(usedTiles); - } -}; - - -/** - * @param {ol.proj.Projection} projection Projection. - * @param {number} z Zoom level. - * @param {ol.TileRange} tileRange Tile range. - * @param {function(ol.Tile):(boolean|undefined)} callback Called with each - * loaded tile. If the callback returns `false`, the tile will not be - * considered loaded. - * @return {boolean} The tile range is fully covered with loaded tiles. - */ -ol.source.Tile.prototype.forEachLoadedTile = function(projection, z, tileRange, callback) { - var tileCache = this.getTileCacheForProjection(projection); - if (!tileCache) { - return false; - } - - var covered = true; - var tile, tileCoordKey, loaded; - for (var x = tileRange.minX; x <= tileRange.maxX; ++x) { - for (var y = tileRange.minY; y <= tileRange.maxY; ++y) { - tileCoordKey = ol.tilecoord.getKeyZXY(z, x, y); - loaded = false; - if (tileCache.containsKey(tileCoordKey)) { - tile = /** @type {!ol.Tile} */ (tileCache.get(tileCoordKey)); - loaded = tile.getState() === ol.TileState.LOADED; - if (loaded) { - loaded = (callback(tile) !== false); - } - } - if (!loaded) { - covered = false; - } - } - } - return covered; -}; - - -/** - * @param {ol.proj.Projection} projection Projection. - * @return {number} Gutter. - */ -ol.source.Tile.prototype.getGutter = function(projection) { - return 0; -}; - - -/** - * Return the key to be used for all tiles in the source. - * @return {string} The key for all tiles. - * @protected - */ -ol.source.Tile.prototype.getKey = function() { - return this.key_; -}; - - -/** - * Set the value to be used as the key for all tiles in the source. - * @param {string} key The key for tiles. - * @protected - */ -ol.source.Tile.prototype.setKey = function(key) { - if (this.key_ !== key) { - this.key_ = key; - this.changed(); - } -}; - - -/** - * @param {ol.proj.Projection} projection Projection. - * @return {boolean} Opaque. - */ -ol.source.Tile.prototype.getOpaque = function(projection) { - return this.opaque_; -}; - - -/** - * @inheritDoc - */ -ol.source.Tile.prototype.getResolutions = function() { - return this.tileGrid.getResolutions(); -}; - - -/** - * @abstract - * @param {number} z Tile coordinate z. - * @param {number} x Tile coordinate x. - * @param {number} y Tile coordinate y. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.proj.Projection} projection Projection. - * @return {!ol.Tile} Tile. - */ -ol.source.Tile.prototype.getTile = function(z, x, y, pixelRatio, projection) {}; - - -/** - * Return the tile grid of the tile source. - * @return {ol.tilegrid.TileGrid} Tile grid. - * @api - */ -ol.source.Tile.prototype.getTileGrid = function() { - return this.tileGrid; -}; - - -/** - * @param {ol.proj.Projection} projection Projection. - * @return {!ol.tilegrid.TileGrid} Tile grid. - */ -ol.source.Tile.prototype.getTileGridForProjection = function(projection) { - if (!this.tileGrid) { - return ol.tilegrid.getForProjection(projection); - } else { - return this.tileGrid; - } -}; - - -/** - * @param {ol.proj.Projection} projection Projection. - * @return {ol.TileCache} Tile cache. - * @protected - */ -ol.source.Tile.prototype.getTileCacheForProjection = function(projection) { - var thisProj = this.getProjection(); - if (thisProj && !ol.proj.equivalent(thisProj, projection)) { - return null; - } else { - return this.tileCache; - } -}; - - -/** - * Get the tile pixel ratio for this source. Subclasses may override this - * method, which is meant to return a supported pixel ratio that matches the - * provided `pixelRatio` as close as possible. - * @param {number} pixelRatio Pixel ratio. - * @return {number} Tile pixel ratio. - */ -ol.source.Tile.prototype.getTilePixelRatio = function(pixelRatio) { - return this.tilePixelRatio_; -}; - - -/** - * @param {number} z Z. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.proj.Projection} projection Projection. - * @return {ol.Size} Tile size. - */ -ol.source.Tile.prototype.getTilePixelSize = function(z, pixelRatio, projection) { - var tileGrid = this.getTileGridForProjection(projection); - var tilePixelRatio = this.getTilePixelRatio(pixelRatio); - var tileSize = ol.size.toSize(tileGrid.getTileSize(z), this.tmpSize); - if (tilePixelRatio == 1) { - return tileSize; - } else { - return ol.size.scale(tileSize, tilePixelRatio, this.tmpSize); - } -}; - - -/** - * Returns a tile coordinate wrapped around the x-axis. When the tile coordinate - * is outside the resolution and extent range of the tile grid, `null` will be - * returned. - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {ol.proj.Projection=} opt_projection Projection. - * @return {ol.TileCoord} Tile coordinate to be passed to the tileUrlFunction or - * null if no tile URL should be created for the passed `tileCoord`. - */ -ol.source.Tile.prototype.getTileCoordForTileUrlFunction = function(tileCoord, opt_projection) { - var projection = opt_projection !== undefined ? - opt_projection : this.getProjection(); - var tileGrid = this.getTileGridForProjection(projection); - if (this.getWrapX() && projection.isGlobal()) { - tileCoord = ol.tilegrid.wrapX(tileGrid, tileCoord, projection); - } - return ol.tilecoord.withinExtentAndZ(tileCoord, tileGrid) ? tileCoord : null; -}; - - -/** - * @inheritDoc - */ -ol.source.Tile.prototype.refresh = function() { - this.tileCache.clear(); - this.changed(); -}; - - -/** - * Marks a tile coord as being used, without triggering a load. - * @param {number} z Tile coordinate z. - * @param {number} x Tile coordinate x. - * @param {number} y Tile coordinate y. - * @param {ol.proj.Projection} projection Projection. - */ -ol.source.Tile.prototype.useTile = ol.nullFunction; - - -/** - * @classdesc - * Events emitted by {@link ol.source.Tile} instances are instances of this - * type. - * - * @constructor - * @extends {ol.events.Event} - * @implements {oli.source.Tile.Event} - * @param {string} type Type. - * @param {ol.Tile} tile The tile. - */ -ol.source.Tile.Event = function(type, tile) { - - ol.events.Event.call(this, type); - - /** - * The tile related to the event. - * @type {ol.Tile} - * @api - */ - this.tile = tile; - -}; -ol.inherits(ol.source.Tile.Event, ol.events.Event); - -goog.provide('ol.source.TileEventType'); - -/** - * @enum {string} - */ -ol.source.TileEventType = { - - /** - * Triggered when a tile starts loading. - * @event ol.source.Tile.Event#tileloadstart - * @api - */ - TILELOADSTART: 'tileloadstart', - - /** - * Triggered when a tile finishes loading, either when its data is loaded, - * or when loading was aborted because the tile is no longer needed. - * @event ol.source.Tile.Event#tileloadend - * @api - */ - TILELOADEND: 'tileloadend', - - /** - * Triggered if tile loading results in an error. - * @event ol.source.Tile.Event#tileloaderror - * @api - */ - TILELOADERROR: 'tileloaderror' - -}; - -goog.provide('ol.source.UrlTile'); - -goog.require('ol'); -goog.require('ol.TileState'); -goog.require('ol.TileUrlFunction'); -goog.require('ol.source.Tile'); -goog.require('ol.source.TileEventType'); -goog.require('ol.tilecoord'); - - -/** - * @classdesc - * Base class for sources providing tiles divided into a tile grid over http. - * - * @constructor - * @abstract - * @fires ol.source.Tile.Event - * @extends {ol.source.Tile} - * @param {ol.SourceUrlTileOptions} options Image tile options. - */ -ol.source.UrlTile = function(options) { - - ol.source.Tile.call(this, { - attributions: options.attributions, - cacheSize: options.cacheSize, - extent: options.extent, - logo: options.logo, - opaque: options.opaque, - projection: options.projection, - state: options.state, - tileGrid: options.tileGrid, - tilePixelRatio: options.tilePixelRatio, - wrapX: options.wrapX, - transition: options.transition - }); - - /** - * @protected - * @type {ol.TileLoadFunctionType} - */ - this.tileLoadFunction = options.tileLoadFunction; - - /** - * @protected - * @type {ol.TileUrlFunctionType} - */ - this.tileUrlFunction = this.fixedTileUrlFunction ? - this.fixedTileUrlFunction.bind(this) : - ol.TileUrlFunction.nullTileUrlFunction; - - /** - * @protected - * @type {!Array.<string>|null} - */ - this.urls = null; - - if (options.urls) { - this.setUrls(options.urls); - } else if (options.url) { - this.setUrl(options.url); - } - if (options.tileUrlFunction) { - this.setTileUrlFunction(options.tileUrlFunction); - } - - /** - * @private - * @type {Object.<number, boolean>} - */ - this.tileLoadingKeys_ = {}; - -}; -ol.inherits(ol.source.UrlTile, ol.source.Tile); - - -/** - * @type {ol.TileUrlFunctionType|undefined} - * @protected - */ -ol.source.UrlTile.prototype.fixedTileUrlFunction; - -/** - * Return the tile load function of the source. - * @return {ol.TileLoadFunctionType} TileLoadFunction - * @api - */ -ol.source.UrlTile.prototype.getTileLoadFunction = function() { - return this.tileLoadFunction; -}; - - -/** - * Return the tile URL function of the source. - * @return {ol.TileUrlFunctionType} TileUrlFunction - * @api - */ -ol.source.UrlTile.prototype.getTileUrlFunction = function() { - return this.tileUrlFunction; -}; - - -/** - * Return the URLs used for this source. - * When a tileUrlFunction is used instead of url or urls, - * null will be returned. - * @return {!Array.<string>|null} URLs. - * @api - */ -ol.source.UrlTile.prototype.getUrls = function() { - return this.urls; -}; - - -/** - * Handle tile change events. - * @param {ol.events.Event} event Event. - * @protected - */ -ol.source.UrlTile.prototype.handleTileChange = function(event) { - var tile = /** @type {ol.Tile} */ (event.target); - var uid = ol.getUid(tile); - var tileState = tile.getState(); - var type; - if (tileState == ol.TileState.LOADING) { - this.tileLoadingKeys_[uid] = true; - type = ol.source.TileEventType.TILELOADSTART; - } else if (uid in this.tileLoadingKeys_) { - delete this.tileLoadingKeys_[uid]; - type = tileState == ol.TileState.ERROR ? ol.source.TileEventType.TILELOADERROR : - (tileState == ol.TileState.LOADED || tileState == ol.TileState.ABORT) ? - ol.source.TileEventType.TILELOADEND : undefined; - } - if (type != undefined) { - this.dispatchEvent(new ol.source.Tile.Event(type, tile)); - } -}; - - -/** - * Set the tile load function of the source. - * @param {ol.TileLoadFunctionType} tileLoadFunction Tile load function. - * @api - */ -ol.source.UrlTile.prototype.setTileLoadFunction = function(tileLoadFunction) { - this.tileCache.clear(); - this.tileLoadFunction = tileLoadFunction; - this.changed(); -}; - - -/** - * Set the tile URL function of the source. - * @param {ol.TileUrlFunctionType} tileUrlFunction Tile URL function. - * @param {string=} opt_key Optional new tile key for the source. - * @api - */ -ol.source.UrlTile.prototype.setTileUrlFunction = function(tileUrlFunction, opt_key) { - this.tileUrlFunction = tileUrlFunction; - this.tileCache.pruneExceptNewestZ(); - if (typeof opt_key !== 'undefined') { - this.setKey(opt_key); - } else { - this.changed(); - } -}; - - -/** - * Set the URL to use for requests. - * @param {string} url URL. - * @api - */ -ol.source.UrlTile.prototype.setUrl = function(url) { - var urls = this.urls = ol.TileUrlFunction.expandUrl(url); - this.setTileUrlFunction(this.fixedTileUrlFunction ? - this.fixedTileUrlFunction.bind(this) : - ol.TileUrlFunction.createFromTemplates(urls, this.tileGrid), url); -}; - - -/** - * Set the URLs to use for requests. - * @param {Array.<string>} urls URLs. - * @api - */ -ol.source.UrlTile.prototype.setUrls = function(urls) { - this.urls = urls; - var key = urls.join('\n'); - this.setTileUrlFunction(this.fixedTileUrlFunction ? - this.fixedTileUrlFunction.bind(this) : - ol.TileUrlFunction.createFromTemplates(urls, this.tileGrid), key); -}; - - -/** - * @inheritDoc - */ -ol.source.UrlTile.prototype.useTile = function(z, x, y) { - var tileCoordKey = ol.tilecoord.getKeyZXY(z, x, y); - if (this.tileCache.containsKey(tileCoordKey)) { - this.tileCache.get(tileCoordKey); - } -}; - -goog.provide('ol.source.TileImage'); - -goog.require('ol'); -goog.require('ol.ImageTile'); -goog.require('ol.TileCache'); -goog.require('ol.TileState'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.proj'); -goog.require('ol.reproj.Tile'); -goog.require('ol.source.UrlTile'); -goog.require('ol.tilecoord'); -goog.require('ol.tilegrid'); - - -/** - * @classdesc - * Base class for sources providing images divided into a tile grid. - * - * @constructor - * @fires ol.source.Tile.Event - * @extends {ol.source.UrlTile} - * @param {olx.source.TileImageOptions} options Image tile options. - * @api - */ -ol.source.TileImage = function(options) { - - ol.source.UrlTile.call(this, { - attributions: options.attributions, - cacheSize: options.cacheSize, - extent: options.extent, - logo: options.logo, - opaque: options.opaque, - projection: options.projection, - state: options.state, - tileGrid: options.tileGrid, - tileLoadFunction: options.tileLoadFunction ? - options.tileLoadFunction : ol.source.TileImage.defaultTileLoadFunction, - tilePixelRatio: options.tilePixelRatio, - tileUrlFunction: options.tileUrlFunction, - url: options.url, - urls: options.urls, - wrapX: options.wrapX, - transition: options.transition - }); - - /** - * @protected - * @type {?string} - */ - this.crossOrigin = - options.crossOrigin !== undefined ? options.crossOrigin : null; - - /** - * @protected - * @type {function(new: ol.ImageTile, ol.TileCoord, ol.TileState, string, - * ?string, ol.TileLoadFunctionType, olx.TileOptions=)} - */ - this.tileClass = options.tileClass !== undefined ? - options.tileClass : ol.ImageTile; - - /** - * @protected - * @type {Object.<string, ol.TileCache>} - */ - this.tileCacheForProjection = {}; - - /** - * @protected - * @type {Object.<string, ol.tilegrid.TileGrid>} - */ - this.tileGridForProjection = {}; - - /** - * @private - * @type {number|undefined} - */ - this.reprojectionErrorThreshold_ = options.reprojectionErrorThreshold; - - /** - * @private - * @type {boolean} - */ - this.renderReprojectionEdges_ = false; -}; -ol.inherits(ol.source.TileImage, ol.source.UrlTile); - - -/** - * @inheritDoc - */ -ol.source.TileImage.prototype.canExpireCache = function() { - if (!ol.ENABLE_RASTER_REPROJECTION) { - return ol.source.UrlTile.prototype.canExpireCache.call(this); - } - if (this.tileCache.canExpireCache()) { - return true; - } else { - for (var key in this.tileCacheForProjection) { - if (this.tileCacheForProjection[key].canExpireCache()) { - return true; - } - } - } - return false; -}; - - -/** - * @inheritDoc - */ -ol.source.TileImage.prototype.expireCache = function(projection, usedTiles) { - if (!ol.ENABLE_RASTER_REPROJECTION) { - ol.source.UrlTile.prototype.expireCache.call(this, projection, usedTiles); - return; - } - var usedTileCache = this.getTileCacheForProjection(projection); - - this.tileCache.expireCache(this.tileCache == usedTileCache ? usedTiles : {}); - for (var id in this.tileCacheForProjection) { - var tileCache = this.tileCacheForProjection[id]; - tileCache.expireCache(tileCache == usedTileCache ? usedTiles : {}); - } -}; - - -/** - * @inheritDoc - */ -ol.source.TileImage.prototype.getGutter = function(projection) { - if (ol.ENABLE_RASTER_REPROJECTION && - this.getProjection() && projection && - !ol.proj.equivalent(this.getProjection(), projection)) { - return 0; - } else { - return this.getGutterInternal(); - } -}; - - -/** - * @protected - * @return {number} Gutter. - */ -ol.source.TileImage.prototype.getGutterInternal = function() { - return 0; -}; - - -/** - * @inheritDoc - */ -ol.source.TileImage.prototype.getOpaque = function(projection) { - if (ol.ENABLE_RASTER_REPROJECTION && - this.getProjection() && projection && - !ol.proj.equivalent(this.getProjection(), projection)) { - return false; - } else { - return ol.source.UrlTile.prototype.getOpaque.call(this, projection); - } -}; - - -/** - * @inheritDoc - */ -ol.source.TileImage.prototype.getTileGridForProjection = function(projection) { - if (!ol.ENABLE_RASTER_REPROJECTION) { - return ol.source.UrlTile.prototype.getTileGridForProjection.call(this, projection); - } - var thisProj = this.getProjection(); - if (this.tileGrid && - (!thisProj || ol.proj.equivalent(thisProj, projection))) { - return this.tileGrid; - } else { - var projKey = ol.getUid(projection).toString(); - if (!(projKey in this.tileGridForProjection)) { - this.tileGridForProjection[projKey] = - ol.tilegrid.getForProjection(projection); - } - return /** @type {!ol.tilegrid.TileGrid} */ (this.tileGridForProjection[projKey]); - } -}; - - -/** - * @inheritDoc - */ -ol.source.TileImage.prototype.getTileCacheForProjection = function(projection) { - if (!ol.ENABLE_RASTER_REPROJECTION) { - return ol.source.UrlTile.prototype.getTileCacheForProjection.call(this, projection); - } - var thisProj = this.getProjection(); - if (!thisProj || ol.proj.equivalent(thisProj, projection)) { - return this.tileCache; - } else { - var projKey = ol.getUid(projection).toString(); - if (!(projKey in this.tileCacheForProjection)) { - this.tileCacheForProjection[projKey] = new ol.TileCache(this.tileCache.highWaterMark); - } - return this.tileCacheForProjection[projKey]; - } -}; - - -/** - * @param {number} z Tile coordinate z. - * @param {number} x Tile coordinate x. - * @param {number} y Tile coordinate y. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.proj.Projection} projection Projection. - * @param {string} key The key set on the tile. - * @return {!ol.Tile} Tile. - * @private - */ -ol.source.TileImage.prototype.createTile_ = function(z, x, y, pixelRatio, projection, key) { - var tileCoord = [z, x, y]; - var urlTileCoord = this.getTileCoordForTileUrlFunction( - tileCoord, projection); - var tileUrl = urlTileCoord ? - this.tileUrlFunction(urlTileCoord, pixelRatio, projection) : undefined; - var tile = new this.tileClass( - tileCoord, - tileUrl !== undefined ? ol.TileState.IDLE : ol.TileState.EMPTY, - tileUrl !== undefined ? tileUrl : '', - this.crossOrigin, - this.tileLoadFunction, - this.tileOptions); - tile.key = key; - ol.events.listen(tile, ol.events.EventType.CHANGE, - this.handleTileChange, this); - return tile; -}; - - -/** - * @inheritDoc - */ -ol.source.TileImage.prototype.getTile = function(z, x, y, pixelRatio, projection) { - if (!ol.ENABLE_RASTER_REPROJECTION || - !this.getProjection() || - !projection || - ol.proj.equivalent(this.getProjection(), projection)) { - return this.getTileInternal(z, x, y, pixelRatio, /** @type {!ol.proj.Projection} */ (projection)); - } else { - var cache = this.getTileCacheForProjection(projection); - var tileCoord = [z, x, y]; - var tile; - var tileCoordKey = ol.tilecoord.getKey(tileCoord); - if (cache.containsKey(tileCoordKey)) { - tile = /** @type {!ol.Tile} */ (cache.get(tileCoordKey)); - } - var key = this.getKey(); - if (tile && tile.key == key) { - return tile; - } else { - var sourceProjection = /** @type {!ol.proj.Projection} */ (this.getProjection()); - var sourceTileGrid = this.getTileGridForProjection(sourceProjection); - var targetTileGrid = this.getTileGridForProjection(projection); - var wrappedTileCoord = - this.getTileCoordForTileUrlFunction(tileCoord, projection); - var newTile = new ol.reproj.Tile( - sourceProjection, sourceTileGrid, - projection, targetTileGrid, - tileCoord, wrappedTileCoord, this.getTilePixelRatio(pixelRatio), - this.getGutterInternal(), - function(z, x, y, pixelRatio) { - return this.getTileInternal(z, x, y, pixelRatio, sourceProjection); - }.bind(this), this.reprojectionErrorThreshold_, - this.renderReprojectionEdges_); - newTile.key = key; - - if (tile) { - newTile.interimTile = tile; - newTile.refreshInterimChain(); - cache.replace(tileCoordKey, newTile); - } else { - cache.set(tileCoordKey, newTile); - } - return newTile; - } - } -}; - - -/** - * @param {number} z Tile coordinate z. - * @param {number} x Tile coordinate x. - * @param {number} y Tile coordinate y. - * @param {number} pixelRatio Pixel ratio. - * @param {!ol.proj.Projection} projection Projection. - * @return {!ol.Tile} Tile. - * @protected - */ -ol.source.TileImage.prototype.getTileInternal = function(z, x, y, pixelRatio, projection) { - var tile = null; - var tileCoordKey = ol.tilecoord.getKeyZXY(z, x, y); - var key = this.getKey(); - if (!this.tileCache.containsKey(tileCoordKey)) { - tile = this.createTile_(z, x, y, pixelRatio, projection, key); - this.tileCache.set(tileCoordKey, tile); - } else { - tile = this.tileCache.get(tileCoordKey); - if (tile.key != key) { - // The source's params changed. If the tile has an interim tile and if we - // can use it then we use it. Otherwise we create a new tile. In both - // cases we attempt to assign an interim tile to the new tile. - var interimTile = tile; - tile = this.createTile_(z, x, y, pixelRatio, projection, key); - - //make the new tile the head of the list, - if (interimTile.getState() == ol.TileState.IDLE) { - //the old tile hasn't begun loading yet, and is now outdated, so we can simply discard it - tile.interimTile = interimTile.interimTile; - } else { - tile.interimTile = interimTile; - } - tile.refreshInterimChain(); - this.tileCache.replace(tileCoordKey, tile); - } - } - return tile; -}; - - -/** - * Sets whether to render reprojection edges or not (usually for debugging). - * @param {boolean} render Render the edges. - * @api - */ -ol.source.TileImage.prototype.setRenderReprojectionEdges = function(render) { - if (!ol.ENABLE_RASTER_REPROJECTION || - this.renderReprojectionEdges_ == render) { - return; - } - this.renderReprojectionEdges_ = render; - for (var id in this.tileCacheForProjection) { - this.tileCacheForProjection[id].clear(); - } - this.changed(); -}; - - -/** - * Sets the tile grid to use when reprojecting the tiles to the given - * projection instead of the default tile grid for the projection. - * - * This can be useful when the default tile grid cannot be created - * (e.g. projection has no extent defined) or - * for optimization reasons (custom tile size, resolutions, ...). - * - * @param {ol.ProjectionLike} projection Projection. - * @param {ol.tilegrid.TileGrid} tilegrid Tile grid to use for the projection. - * @api - */ -ol.source.TileImage.prototype.setTileGridForProjection = function(projection, tilegrid) { - if (ol.ENABLE_RASTER_REPROJECTION) { - var proj = ol.proj.get(projection); - if (proj) { - var projKey = ol.getUid(proj).toString(); - if (!(projKey in this.tileGridForProjection)) { - this.tileGridForProjection[projKey] = tilegrid; - } - } - } -}; - - -/** - * @param {ol.ImageTile} imageTile Image tile. - * @param {string} src Source. - */ -ol.source.TileImage.defaultTileLoadFunction = function(imageTile, src) { - imageTile.getImage().src = src; -}; - -goog.provide('ol.source.BingMaps'); - -goog.require('ol'); -goog.require('ol.Attribution'); -goog.require('ol.TileUrlFunction'); -goog.require('ol.extent'); -goog.require('ol.net'); -goog.require('ol.proj'); -goog.require('ol.source.State'); -goog.require('ol.source.TileImage'); -goog.require('ol.tilecoord'); -goog.require('ol.tilegrid'); - - -/** - * @classdesc - * Layer source for Bing Maps tile data. - * - * @constructor - * @extends {ol.source.TileImage} - * @param {olx.source.BingMapsOptions} options Bing Maps options. - * @api - */ -ol.source.BingMaps = function(options) { - - /** - * @private - * @type {boolean} - */ - this.hidpi_ = options.hidpi !== undefined ? options.hidpi : false; - - ol.source.TileImage.call(this, { - cacheSize: options.cacheSize, - crossOrigin: 'anonymous', - opaque: true, - projection: ol.proj.get('EPSG:3857'), - reprojectionErrorThreshold: options.reprojectionErrorThreshold, - state: ol.source.State.LOADING, - tileLoadFunction: options.tileLoadFunction, - tilePixelRatio: this.hidpi_ ? 2 : 1, - wrapX: options.wrapX !== undefined ? options.wrapX : true, - transition: options.transition - }); - - /** - * @private - * @type {string} - */ - this.culture_ = options.culture !== undefined ? options.culture : 'en-us'; - - /** - * @private - * @type {number} - */ - this.maxZoom_ = options.maxZoom !== undefined ? options.maxZoom : -1; - - /** - * @private - * @type {string} - */ - this.apiKey_ = options.key; - - /** - * @private - * @type {string} - */ - this.imagerySet_ = options.imagerySet; - - var url = 'https://dev.virtualearth.net/REST/v1/Imagery/Metadata/' + - this.imagerySet_ + - '?uriScheme=https&include=ImageryProviders&key=' + this.apiKey_; - - ol.net.jsonp(url, this.handleImageryMetadataResponse.bind(this), undefined, - 'jsonp'); - -}; -ol.inherits(ol.source.BingMaps, ol.source.TileImage); - - -/** - * The attribution containing a link to the Microsoft® Bingâ„¢ Maps Platform APIs’ - * Terms Of Use. - * @const - * @type {ol.Attribution} - * @api - */ -ol.source.BingMaps.TOS_ATTRIBUTION = new ol.Attribution({ - html: '<a class="ol-attribution-bing-tos" ' + - 'href="https://www.microsoft.com/maps/product/terms.html">' + - 'Terms of Use</a>' -}); - - -/** - * Get the api key used for this source. - * - * @return {string} The api key. - * @api - */ -ol.source.BingMaps.prototype.getApiKey = function() { - return this.apiKey_; -}; - - -/** - * Get the imagery set associated with this source. - * - * @return {string} The imagery set. - * @api - */ -ol.source.BingMaps.prototype.getImagerySet = function() { - return this.imagerySet_; -}; - - -/** - * @param {BingMapsImageryMetadataResponse} response Response. - */ -ol.source.BingMaps.prototype.handleImageryMetadataResponse = function(response) { - if (response.statusCode != 200 || - response.statusDescription != 'OK' || - response.authenticationResultCode != 'ValidCredentials' || - response.resourceSets.length != 1 || - response.resourceSets[0].resources.length != 1) { - this.setState(ol.source.State.ERROR); - return; - } - - var brandLogoUri = response.brandLogoUri; - if (brandLogoUri.indexOf('https') == -1) { - brandLogoUri = brandLogoUri.replace('http', 'https'); - } - //var copyright = response.copyright; // FIXME do we need to display this? - var resource = response.resourceSets[0].resources[0]; - var maxZoom = this.maxZoom_ == -1 ? resource.zoomMax : this.maxZoom_; - - var sourceProjection = this.getProjection(); - var extent = ol.tilegrid.extentFromProjection(sourceProjection); - var tileSize = resource.imageWidth == resource.imageHeight ? - resource.imageWidth : [resource.imageWidth, resource.imageHeight]; - var tileGrid = ol.tilegrid.createXYZ({ - extent: extent, - minZoom: resource.zoomMin, - maxZoom: maxZoom, - tileSize: tileSize / (this.hidpi_ ? 2 : 1) - }); - this.tileGrid = tileGrid; - - var culture = this.culture_; - var hidpi = this.hidpi_; - this.tileUrlFunction = ol.TileUrlFunction.createFromTileUrlFunctions( - resource.imageUrlSubdomains.map(function(subdomain) { - var quadKeyTileCoord = [0, 0, 0]; - var imageUrl = resource.imageUrl - .replace('{subdomain}', subdomain) - .replace('{culture}', culture); - return ( - /** - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.proj.Projection} projection Projection. - * @return {string|undefined} Tile URL. - */ - function(tileCoord, pixelRatio, projection) { - if (!tileCoord) { - return undefined; - } else { - ol.tilecoord.createOrUpdate(tileCoord[0], tileCoord[1], - -tileCoord[2] - 1, quadKeyTileCoord); - var url = imageUrl; - if (hidpi) { - url += '&dpi=d1&device=mobile'; - } - return url.replace('{quadkey}', ol.tilecoord.quadKey( - quadKeyTileCoord)); - } - }); - })); - - if (resource.imageryProviders) { - var transform = ol.proj.getTransformFromProjections( - ol.proj.get('EPSG:4326'), this.getProjection()); - - var attributions = resource.imageryProviders.map(function(imageryProvider) { - var html = imageryProvider.attribution; - /** @type {Object.<string, Array.<ol.TileRange>>} */ - var tileRanges = {}; - imageryProvider.coverageAreas.forEach(function(coverageArea) { - var minZ = coverageArea.zoomMin; - var maxZ = Math.min(coverageArea.zoomMax, maxZoom); - var bbox = coverageArea.bbox; - var epsg4326Extent = [bbox[1], bbox[0], bbox[3], bbox[2]]; - var extent = ol.extent.applyTransform(epsg4326Extent, transform); - var tileRange, z, zKey; - for (z = minZ; z <= maxZ; ++z) { - zKey = z.toString(); - tileRange = tileGrid.getTileRangeForExtentAndZ(extent, z); - if (zKey in tileRanges) { - tileRanges[zKey].push(tileRange); - } else { - tileRanges[zKey] = [tileRange]; - } - } - }); - return new ol.Attribution({html: html, tileRanges: tileRanges}); - }); - attributions.push(ol.source.BingMaps.TOS_ATTRIBUTION); - this.setAttributions(attributions); - } - - this.setLogo(brandLogoUri); - - this.setState(ol.source.State.READY); -}; - -goog.provide('ol.source.XYZ'); - -goog.require('ol'); -goog.require('ol.source.TileImage'); -goog.require('ol.tilegrid'); - - -/** - * @classdesc - * Layer source for tile data with URLs in a set XYZ format that are - * defined in a URL template. By default, this follows the widely-used - * Google grid where `x` 0 and `y` 0 are in the top left. Grids like - * TMS where `x` 0 and `y` 0 are in the bottom left can be used by - * using the `{-y}` placeholder in the URL template, so long as the - * source does not have a custom tile grid. In this case, - * {@link ol.source.TileImage} can be used with a `tileUrlFunction` - * such as: - * - * tileUrlFunction: function(coordinate) { - * return 'http://mapserver.com/' + coordinate[0] + '/' + - * coordinate[1] + '/' + coordinate[2] + '.png'; - * } - * - * - * @constructor - * @extends {ol.source.TileImage} - * @param {olx.source.XYZOptions=} opt_options XYZ options. - * @api - */ -ol.source.XYZ = function(opt_options) { - var options = opt_options || {}; - var projection = options.projection !== undefined ? - options.projection : 'EPSG:3857'; - - var tileGrid = options.tileGrid !== undefined ? options.tileGrid : - ol.tilegrid.createXYZ({ - extent: ol.tilegrid.extentFromProjection(projection), - maxZoom: options.maxZoom, - minZoom: options.minZoom, - tileSize: options.tileSize - }); - - ol.source.TileImage.call(this, { - attributions: options.attributions, - cacheSize: options.cacheSize, - crossOrigin: options.crossOrigin, - logo: options.logo, - opaque: options.opaque, - projection: projection, - reprojectionErrorThreshold: options.reprojectionErrorThreshold, - tileGrid: tileGrid, - tileLoadFunction: options.tileLoadFunction, - tilePixelRatio: options.tilePixelRatio, - tileUrlFunction: options.tileUrlFunction, - url: options.url, - urls: options.urls, - wrapX: options.wrapX !== undefined ? options.wrapX : true, - transition: options.transition - }); - -}; -ol.inherits(ol.source.XYZ, ol.source.TileImage); - -goog.provide('ol.source.CartoDB'); - -goog.require('ol'); -goog.require('ol.obj'); -goog.require('ol.source.State'); -goog.require('ol.source.XYZ'); - - -/** - * @classdesc - * Layer source for the CartoDB Maps API. - * - * @constructor - * @extends {ol.source.XYZ} - * @param {olx.source.CartoDBOptions} options CartoDB options. - * @api - */ -ol.source.CartoDB = function(options) { - - /** - * @type {string} - * @private - */ - this.account_ = options.account; - - /** - * @type {string} - * @private - */ - this.mapId_ = options.map || ''; - - /** - * @type {!Object} - * @private - */ - this.config_ = options.config || {}; - - /** - * @type {!Object.<string, CartoDBLayerInfo>} - * @private - */ - this.templateCache_ = {}; - - ol.source.XYZ.call(this, { - attributions: options.attributions, - cacheSize: options.cacheSize, - crossOrigin: options.crossOrigin, - logo: options.logo, - maxZoom: options.maxZoom !== undefined ? options.maxZoom : 18, - minZoom: options.minZoom, - projection: options.projection, - state: ol.source.State.LOADING, - wrapX: options.wrapX - }); - this.initializeMap_(); -}; -ol.inherits(ol.source.CartoDB, ol.source.XYZ); - - -/** - * Returns the current config. - * @return {!Object} The current configuration. - * @api - */ -ol.source.CartoDB.prototype.getConfig = function() { - return this.config_; -}; - - -/** - * Updates the carto db config. - * @param {Object} config a key-value lookup. Values will replace current values - * in the config. - * @api - */ -ol.source.CartoDB.prototype.updateConfig = function(config) { - ol.obj.assign(this.config_, config); - this.initializeMap_(); -}; - - -/** - * Sets the CartoDB config - * @param {Object} config In the case of anonymous maps, a CartoDB configuration - * object. - * If using named maps, a key-value lookup with the template parameters. - * @api - */ -ol.source.CartoDB.prototype.setConfig = function(config) { - this.config_ = config || {}; - this.initializeMap_(); -}; - - -/** - * Issue a request to initialize the CartoDB map. - * @private - */ -ol.source.CartoDB.prototype.initializeMap_ = function() { - var paramHash = JSON.stringify(this.config_); - if (this.templateCache_[paramHash]) { - this.applyTemplate_(this.templateCache_[paramHash]); - return; - } - var mapUrl = 'https://' + this.account_ + '.carto.com/api/v1/map'; - - if (this.mapId_) { - mapUrl += '/named/' + this.mapId_; - } - - var client = new XMLHttpRequest(); - client.addEventListener('load', this.handleInitResponse_.bind(this, paramHash)); - client.addEventListener('error', this.handleInitError_.bind(this)); - client.open('POST', mapUrl); - client.setRequestHeader('Content-type', 'application/json'); - client.send(JSON.stringify(this.config_)); -}; - - -/** - * Handle map initialization response. - * @param {string} paramHash a hash representing the parameter set that was used - * for the request - * @param {Event} event Event. - * @private - */ -ol.source.CartoDB.prototype.handleInitResponse_ = function(paramHash, event) { - var client = /** @type {XMLHttpRequest} */ (event.target); - // status will be 0 for file:// urls - if (!client.status || client.status >= 200 && client.status < 300) { - var response; - try { - response = /** @type {CartoDBLayerInfo} */(JSON.parse(client.responseText)); - } catch (err) { - this.setState(ol.source.State.ERROR); - return; - } - this.applyTemplate_(response); - this.templateCache_[paramHash] = response; - this.setState(ol.source.State.READY); - } else { - this.setState(ol.source.State.ERROR); - } -}; - - -/** - * @private - * @param {Event} event Event. - */ -ol.source.CartoDB.prototype.handleInitError_ = function(event) { - this.setState(ol.source.State.ERROR); -}; - - -/** - * Apply the new tile urls returned by carto db - * @param {CartoDBLayerInfo} data Result of carto db call. - * @private - */ -ol.source.CartoDB.prototype.applyTemplate_ = function(data) { - var tilesUrl = 'https://' + data.cdn_url.https + '/' + this.account_ + - '/api/v1/map/' + data.layergroupid + '/{z}/{x}/{y}.png'; - this.setUrl(tilesUrl); -}; - -// FIXME keep cluster cache by resolution ? -// FIXME distance not respected because of the centroid - -goog.provide('ol.source.Cluster'); - -goog.require('ol'); -goog.require('ol.asserts'); -goog.require('ol.Feature'); -goog.require('ol.coordinate'); -goog.require('ol.events.EventType'); -goog.require('ol.extent'); -goog.require('ol.geom.Point'); -goog.require('ol.source.Vector'); - - -/** - * @classdesc - * Layer source to cluster vector data. Works out of the box with point - * geometries. For other geometry types, or if not all geometries should be - * considered for clustering, a custom `geometryFunction` can be defined. - * - * @constructor - * @param {olx.source.ClusterOptions} options Constructor options. - * @extends {ol.source.Vector} - * @api - */ -ol.source.Cluster = function(options) { - ol.source.Vector.call(this, { - attributions: options.attributions, - extent: options.extent, - logo: options.logo, - projection: options.projection, - wrapX: options.wrapX - }); - - /** - * @type {number|undefined} - * @protected - */ - this.resolution = undefined; - - /** - * @type {number} - * @protected - */ - this.distance = options.distance !== undefined ? options.distance : 20; - - /** - * @type {Array.<ol.Feature>} - * @protected - */ - this.features = []; - - /** - * @param {ol.Feature} feature Feature. - * @return {ol.geom.Point} Cluster calculation point. - * @protected - */ - this.geometryFunction = options.geometryFunction || function(feature) { - var geometry = /** @type {ol.geom.Point} */ (feature.getGeometry()); - ol.asserts.assert(geometry instanceof ol.geom.Point, - 10); // The default `geometryFunction` can only handle `ol.geom.Point` geometries - return geometry; - }; - - /** - * @type {ol.source.Vector} - * @protected - */ - this.source = options.source; - - this.source.on(ol.events.EventType.CHANGE, - ol.source.Cluster.prototype.refresh, this); -}; -ol.inherits(ol.source.Cluster, ol.source.Vector); - - -/** - * Get the distance in pixels between clusters. - * @return {number} Distance. - * @api - */ -ol.source.Cluster.prototype.getDistance = function() { - return this.distance; -}; - - -/** - * Get a reference to the wrapped source. - * @return {ol.source.Vector} Source. - * @api - */ -ol.source.Cluster.prototype.getSource = function() { - return this.source; -}; - - -/** - * @inheritDoc - */ -ol.source.Cluster.prototype.loadFeatures = function(extent, resolution, - projection) { - this.source.loadFeatures(extent, resolution, projection); - if (resolution !== this.resolution) { - this.clear(); - this.resolution = resolution; - this.cluster(); - this.addFeatures(this.features); - } -}; - - -/** - * Set the distance in pixels between clusters. - * @param {number} distance The distance in pixels. - * @api - */ -ol.source.Cluster.prototype.setDistance = function(distance) { - this.distance = distance; - this.refresh(); -}; - - -/** - * handle the source changing - * @override - */ -ol.source.Cluster.prototype.refresh = function() { - this.clear(); - this.cluster(); - this.addFeatures(this.features); - ol.source.Vector.prototype.refresh.call(this); -}; - - -/** - * @protected - */ -ol.source.Cluster.prototype.cluster = function() { - if (this.resolution === undefined) { - return; - } - this.features.length = 0; - var extent = ol.extent.createEmpty(); - var mapDistance = this.distance * this.resolution; - var features = this.source.getFeatures(); - - /** - * @type {!Object.<string, boolean>} - */ - var clustered = {}; - - for (var i = 0, ii = features.length; i < ii; i++) { - var feature = features[i]; - if (!(ol.getUid(feature).toString() in clustered)) { - var geometry = this.geometryFunction(feature); - if (geometry) { - var coordinates = geometry.getCoordinates(); - ol.extent.createOrUpdateFromCoordinate(coordinates, extent); - ol.extent.buffer(extent, mapDistance, extent); - - var neighbors = this.source.getFeaturesInExtent(extent); - neighbors = neighbors.filter(function(neighbor) { - var uid = ol.getUid(neighbor).toString(); - if (!(uid in clustered)) { - clustered[uid] = true; - return true; - } else { - return false; - } - }); - this.features.push(this.createCluster(neighbors)); - } - } - } -}; - - -/** - * @param {Array.<ol.Feature>} features Features - * @return {ol.Feature} The cluster feature. - * @protected - */ -ol.source.Cluster.prototype.createCluster = function(features) { - var centroid = [0, 0]; - for (var i = features.length - 1; i >= 0; --i) { - var geometry = this.geometryFunction(features[i]); - if (geometry) { - ol.coordinate.add(centroid, geometry.getCoordinates()); - } else { - features.splice(i, 1); - } - } - ol.coordinate.scale(centroid, 1 / features.length); - - var cluster = new ol.Feature(new ol.geom.Point(centroid)); - cluster.set('features', features); - return cluster; -}; - -goog.provide('ol.uri'); - - -/** - * Appends query parameters to a URI. - * - * @param {string} uri The original URI, which may already have query data. - * @param {!Object} params An object where keys are URI-encoded parameter keys, - * and the values are arbitrary types or arrays. - * @return {string} The new URI. - */ -ol.uri.appendParams = function(uri, params) { - var keyParams = []; - // Skip any null or undefined parameter values - Object.keys(params).forEach(function(k) { - if (params[k] !== null && params[k] !== undefined) { - keyParams.push(k + '=' + encodeURIComponent(params[k])); - } - }); - var qs = keyParams.join('&'); - // remove any trailing ? or & - uri = uri.replace(/[?&]$/, ''); - // append ? or & depending on whether uri has existing parameters - uri = uri.indexOf('?') === -1 ? uri + '?' : uri + '&'; - return uri + qs; -}; - -goog.provide('ol.source.ImageArcGISRest'); - -goog.require('ol'); -goog.require('ol.Image'); -goog.require('ol.asserts'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.extent'); -goog.require('ol.obj'); -goog.require('ol.source.Image'); -goog.require('ol.uri'); - - -/** - * @classdesc - * Source for data from ArcGIS Rest services providing single, untiled images. - * Useful when underlying map service has labels. - * - * If underlying map service is not using labels, - * take advantage of ol image caching and use - * {@link ol.source.TileArcGISRest} data source. - * - * @constructor - * @fires ol.source.Image.Event - * @extends {ol.source.Image} - * @param {olx.source.ImageArcGISRestOptions=} opt_options Image ArcGIS Rest Options. - * @api - */ -ol.source.ImageArcGISRest = function(opt_options) { - - var options = opt_options || {}; - - ol.source.Image.call(this, { - attributions: options.attributions, - logo: options.logo, - projection: options.projection, - resolutions: options.resolutions - }); - - /** - * @private - * @type {?string} - */ - this.crossOrigin_ = - options.crossOrigin !== undefined ? options.crossOrigin : null; - - /** - * @private - * @type {boolean} - */ - this.hidpi_ = options.hidpi !== undefined ? options.hidpi : true; - - /** - * @private - * @type {string|undefined} - */ - this.url_ = options.url; - - /** - * @private - * @type {ol.ImageLoadFunctionType} - */ - this.imageLoadFunction_ = options.imageLoadFunction !== undefined ? - options.imageLoadFunction : ol.source.Image.defaultImageLoadFunction; - - - /** - * @private - * @type {!Object} - */ - this.params_ = options.params || {}; - - /** - * @private - * @type {ol.Image} - */ - this.image_ = null; - - /** - * @private - * @type {ol.Size} - */ - this.imageSize_ = [0, 0]; - - - /** - * @private - * @type {number} - */ - this.renderedRevision_ = 0; - - /** - * @private - * @type {number} - */ - this.ratio_ = options.ratio !== undefined ? options.ratio : 1.5; - -}; -ol.inherits(ol.source.ImageArcGISRest, ol.source.Image); - - -/** - * Get the user-provided params, i.e. those passed to the constructor through - * the "params" option, and possibly updated using the updateParams method. - * @return {Object} Params. - * @api - */ -ol.source.ImageArcGISRest.prototype.getParams = function() { - return this.params_; -}; - - -/** - * @inheritDoc - */ -ol.source.ImageArcGISRest.prototype.getImageInternal = function(extent, resolution, pixelRatio, projection) { - - if (this.url_ === undefined) { - return null; - } - - resolution = this.findNearestResolution(resolution); - pixelRatio = this.hidpi_ ? pixelRatio : 1; - - var image = this.image_; - if (image && - this.renderedRevision_ == this.getRevision() && - image.getResolution() == resolution && - image.getPixelRatio() == pixelRatio && - ol.extent.containsExtent(image.getExtent(), extent)) { - return image; - } - - var params = { - 'F': 'image', - 'FORMAT': 'PNG32', - 'TRANSPARENT': true - }; - ol.obj.assign(params, this.params_); - - extent = extent.slice(); - var centerX = (extent[0] + extent[2]) / 2; - var centerY = (extent[1] + extent[3]) / 2; - if (this.ratio_ != 1) { - var halfWidth = this.ratio_ * ol.extent.getWidth(extent) / 2; - var halfHeight = this.ratio_ * ol.extent.getHeight(extent) / 2; - extent[0] = centerX - halfWidth; - extent[1] = centerY - halfHeight; - extent[2] = centerX + halfWidth; - extent[3] = centerY + halfHeight; - } - - var imageResolution = resolution / pixelRatio; - - // Compute an integer width and height. - var width = Math.ceil(ol.extent.getWidth(extent) / imageResolution); - var height = Math.ceil(ol.extent.getHeight(extent) / imageResolution); - - // Modify the extent to match the integer width and height. - extent[0] = centerX - imageResolution * width / 2; - extent[2] = centerX + imageResolution * width / 2; - extent[1] = centerY - imageResolution * height / 2; - extent[3] = centerY + imageResolution * height / 2; - - this.imageSize_[0] = width; - this.imageSize_[1] = height; - - var url = this.getRequestUrl_(extent, this.imageSize_, pixelRatio, - projection, params); - - this.image_ = new ol.Image(extent, resolution, pixelRatio, - this.getAttributions(), url, this.crossOrigin_, this.imageLoadFunction_); - - this.renderedRevision_ = this.getRevision(); - - ol.events.listen(this.image_, ol.events.EventType.CHANGE, - this.handleImageChange, this); - - return this.image_; - -}; - - -/** - * Return the image load function of the source. - * @return {ol.ImageLoadFunctionType} The image load function. - * @api - */ -ol.source.ImageArcGISRest.prototype.getImageLoadFunction = function() { - return this.imageLoadFunction_; -}; - - -/** - * @param {ol.Extent} extent Extent. - * @param {ol.Size} size Size. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.proj.Projection} projection Projection. - * @param {Object} params Params. - * @return {string} Request URL. - * @private - */ -ol.source.ImageArcGISRest.prototype.getRequestUrl_ = function(extent, size, pixelRatio, projection, params) { - // ArcGIS Server only wants the numeric portion of the projection ID. - var srid = projection.getCode().split(':').pop(); - - params['SIZE'] = size[0] + ',' + size[1]; - params['BBOX'] = extent.join(','); - params['BBOXSR'] = srid; - params['IMAGESR'] = srid; - params['DPI'] = Math.round(90 * pixelRatio); - - var url = this.url_; - - var modifiedUrl = url - .replace(/MapServer\/?$/, 'MapServer/export') - .replace(/ImageServer\/?$/, 'ImageServer/exportImage'); - if (modifiedUrl == url) { - ol.asserts.assert(false, 50); // `options.featureTypes` should be an Array - } - return ol.uri.appendParams(modifiedUrl, params); -}; - - -/** - * Return the URL used for this ArcGIS source. - * @return {string|undefined} URL. - * @api - */ -ol.source.ImageArcGISRest.prototype.getUrl = function() { - return this.url_; -}; - - -/** - * Set the image load function of the source. - * @param {ol.ImageLoadFunctionType} imageLoadFunction Image load function. - * @api - */ -ol.source.ImageArcGISRest.prototype.setImageLoadFunction = function(imageLoadFunction) { - this.image_ = null; - this.imageLoadFunction_ = imageLoadFunction; - this.changed(); -}; - - -/** - * Set the URL to use for requests. - * @param {string|undefined} url URL. - * @api - */ -ol.source.ImageArcGISRest.prototype.setUrl = function(url) { - if (url != this.url_) { - this.url_ = url; - this.image_ = null; - this.changed(); - } -}; - - -/** - * Update the user-provided params. - * @param {Object} params Params. - * @api - */ -ol.source.ImageArcGISRest.prototype.updateParams = function(params) { - ol.obj.assign(this.params_, params); - this.image_ = null; - this.changed(); -}; - -goog.provide('ol.source.ImageMapGuide'); - -goog.require('ol'); -goog.require('ol.Image'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.extent'); -goog.require('ol.obj'); -goog.require('ol.source.Image'); -goog.require('ol.uri'); - - -/** - * @classdesc - * Source for images from Mapguide servers - * - * @constructor - * @fires ol.source.Image.Event - * @extends {ol.source.Image} - * @param {olx.source.ImageMapGuideOptions} options Options. - * @api - */ -ol.source.ImageMapGuide = function(options) { - - ol.source.Image.call(this, { - projection: options.projection, - resolutions: options.resolutions - }); - - /** - * @private - * @type {?string} - */ - this.crossOrigin_ = - options.crossOrigin !== undefined ? options.crossOrigin : null; - - /** - * @private - * @type {number} - */ - this.displayDpi_ = options.displayDpi !== undefined ? - options.displayDpi : 96; - - /** - * @private - * @type {!Object} - */ - this.params_ = options.params || {}; - - /** - * @private - * @type {string|undefined} - */ - this.url_ = options.url; - - /** - * @private - * @type {ol.ImageLoadFunctionType} - */ - this.imageLoadFunction_ = options.imageLoadFunction !== undefined ? - options.imageLoadFunction : ol.source.Image.defaultImageLoadFunction; - - /** - * @private - * @type {boolean} - */ - this.hidpi_ = options.hidpi !== undefined ? options.hidpi : true; - - /** - * @private - * @type {number} - */ - this.metersPerUnit_ = options.metersPerUnit !== undefined ? - options.metersPerUnit : 1; - - /** - * @private - * @type {number} - */ - this.ratio_ = options.ratio !== undefined ? options.ratio : 1; - - /** - * @private - * @type {boolean} - */ - this.useOverlay_ = options.useOverlay !== undefined ? - options.useOverlay : false; - - /** - * @private - * @type {ol.Image} - */ - this.image_ = null; - - /** - * @private - * @type {number} - */ - this.renderedRevision_ = 0; - -}; -ol.inherits(ol.source.ImageMapGuide, ol.source.Image); - - -/** - * Get the user-provided params, i.e. those passed to the constructor through - * the "params" option, and possibly updated using the updateParams method. - * @return {Object} Params. - * @api - */ -ol.source.ImageMapGuide.prototype.getParams = function() { - return this.params_; -}; - - -/** - * @inheritDoc - */ -ol.source.ImageMapGuide.prototype.getImageInternal = function(extent, resolution, pixelRatio, projection) { - resolution = this.findNearestResolution(resolution); - pixelRatio = this.hidpi_ ? pixelRatio : 1; - - var image = this.image_; - if (image && - this.renderedRevision_ == this.getRevision() && - image.getResolution() == resolution && - image.getPixelRatio() == pixelRatio && - ol.extent.containsExtent(image.getExtent(), extent)) { - return image; - } - - if (this.ratio_ != 1) { - extent = extent.slice(); - ol.extent.scaleFromCenter(extent, this.ratio_); - } - var width = ol.extent.getWidth(extent) / resolution; - var height = ol.extent.getHeight(extent) / resolution; - var size = [width * pixelRatio, height * pixelRatio]; - - if (this.url_ !== undefined) { - var imageUrl = this.getUrl(this.url_, this.params_, extent, size, - projection); - image = new ol.Image(extent, resolution, pixelRatio, - this.getAttributions(), imageUrl, this.crossOrigin_, - this.imageLoadFunction_); - ol.events.listen(image, ol.events.EventType.CHANGE, - this.handleImageChange, this); - } else { - image = null; - } - this.image_ = image; - this.renderedRevision_ = this.getRevision(); - - return image; -}; - - -/** - * Return the image load function of the source. - * @return {ol.ImageLoadFunctionType} The image load function. - * @api - */ -ol.source.ImageMapGuide.prototype.getImageLoadFunction = function() { - return this.imageLoadFunction_; -}; - - -/** - * @param {ol.Extent} extent The map extents. - * @param {ol.Size} size The viewport size. - * @param {number} metersPerUnit The meters-per-unit value. - * @param {number} dpi The display resolution. - * @return {number} The computed map scale. - */ -ol.source.ImageMapGuide.getScale = function(extent, size, metersPerUnit, dpi) { - var mcsW = ol.extent.getWidth(extent); - var mcsH = ol.extent.getHeight(extent); - var devW = size[0]; - var devH = size[1]; - var mpp = 0.0254 / dpi; - if (devH * mcsW > devW * mcsH) { - return mcsW * metersPerUnit / (devW * mpp); // width limited - } else { - return mcsH * metersPerUnit / (devH * mpp); // height limited - } -}; - - -/** - * Update the user-provided params. - * @param {Object} params Params. - * @api - */ -ol.source.ImageMapGuide.prototype.updateParams = function(params) { - ol.obj.assign(this.params_, params); - this.changed(); -}; - - -/** - * @param {string} baseUrl The mapagent url. - * @param {Object.<string, string|number>} params Request parameters. - * @param {ol.Extent} extent Extent. - * @param {ol.Size} size Size. - * @param {ol.proj.Projection} projection Projection. - * @return {string} The mapagent map image request URL. - */ -ol.source.ImageMapGuide.prototype.getUrl = function(baseUrl, params, extent, size, projection) { - var scale = ol.source.ImageMapGuide.getScale(extent, size, - this.metersPerUnit_, this.displayDpi_); - var center = ol.extent.getCenter(extent); - var baseParams = { - 'OPERATION': this.useOverlay_ ? 'GETDYNAMICMAPOVERLAYIMAGE' : 'GETMAPIMAGE', - 'VERSION': '2.0.0', - 'LOCALE': 'en', - 'CLIENTAGENT': 'ol.source.ImageMapGuide source', - 'CLIP': '1', - 'SETDISPLAYDPI': this.displayDpi_, - 'SETDISPLAYWIDTH': Math.round(size[0]), - 'SETDISPLAYHEIGHT': Math.round(size[1]), - 'SETVIEWSCALE': scale, - 'SETVIEWCENTERX': center[0], - 'SETVIEWCENTERY': center[1] - }; - ol.obj.assign(baseParams, params); - return ol.uri.appendParams(baseUrl, baseParams); -}; - - -/** - * Set the image load function of the MapGuide source. - * @param {ol.ImageLoadFunctionType} imageLoadFunction Image load function. - * @api - */ -ol.source.ImageMapGuide.prototype.setImageLoadFunction = function( - imageLoadFunction) { - this.image_ = null; - this.imageLoadFunction_ = imageLoadFunction; - this.changed(); -}; - -goog.provide('ol.source.ImageStatic'); - -goog.require('ol'); -goog.require('ol.Image'); -goog.require('ol.ImageState'); -goog.require('ol.dom'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.extent'); -goog.require('ol.proj'); -goog.require('ol.source.Image'); - - -/** - * @classdesc - * A layer source for displaying a single, static image. - * - * @constructor - * @extends {ol.source.Image} - * @param {olx.source.ImageStaticOptions} options Options. - * @api - */ -ol.source.ImageStatic = function(options) { - var imageExtent = options.imageExtent; - - var crossOrigin = options.crossOrigin !== undefined ? - options.crossOrigin : null; - - var /** @type {ol.ImageLoadFunctionType} */ imageLoadFunction = - options.imageLoadFunction !== undefined ? - options.imageLoadFunction : ol.source.Image.defaultImageLoadFunction; - - ol.source.Image.call(this, { - attributions: options.attributions, - logo: options.logo, - projection: ol.proj.get(options.projection) - }); - - /** - * @private - * @type {ol.Image} - */ - this.image_ = new ol.Image(imageExtent, undefined, 1, this.getAttributions(), - options.url, crossOrigin, imageLoadFunction); - - /** - * @private - * @type {ol.Size} - */ - this.imageSize_ = options.imageSize ? options.imageSize : null; - - ol.events.listen(this.image_, ol.events.EventType.CHANGE, - this.handleImageChange, this); - -}; -ol.inherits(ol.source.ImageStatic, ol.source.Image); - - -/** - * @inheritDoc - */ -ol.source.ImageStatic.prototype.getImageInternal = function(extent, resolution, pixelRatio, projection) { - if (ol.extent.intersects(extent, this.image_.getExtent())) { - return this.image_; - } - return null; -}; - - -/** - * @inheritDoc - */ -ol.source.ImageStatic.prototype.handleImageChange = function(evt) { - if (this.image_.getState() == ol.ImageState.LOADED) { - var imageExtent = this.image_.getExtent(); - var image = this.image_.getImage(); - var imageWidth, imageHeight; - if (this.imageSize_) { - imageWidth = this.imageSize_[0]; - imageHeight = this.imageSize_[1]; - } else { - imageWidth = image.width; - imageHeight = image.height; - } - var resolution = ol.extent.getHeight(imageExtent) / imageHeight; - var targetWidth = Math.ceil(ol.extent.getWidth(imageExtent) / resolution); - if (targetWidth != imageWidth) { - var context = ol.dom.createCanvasContext2D(targetWidth, imageHeight); - var canvas = context.canvas; - context.drawImage(image, 0, 0, imageWidth, imageHeight, - 0, 0, canvas.width, canvas.height); - this.image_.setImage(canvas); - } - } - ol.source.Image.prototype.handleImageChange.call(this, evt); -}; - -goog.provide('ol.source.WMSServerType'); - - -/** - * Available server types: `'carmentaserver'`, `'geoserver'`, `'mapserver'`, - * `'qgis'`. These are servers that have vendor parameters beyond the WMS - * specification that OpenLayers can make use of. - * @enum {string} - */ -ol.source.WMSServerType = { - CARMENTA_SERVER: 'carmentaserver', - GEOSERVER: 'geoserver', - MAPSERVER: 'mapserver', - QGIS: 'qgis' -}; - -// FIXME cannot be shared between maps with different projections - -goog.provide('ol.source.ImageWMS'); - -goog.require('ol'); -goog.require('ol.Image'); -goog.require('ol.asserts'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.extent'); -goog.require('ol.obj'); -goog.require('ol.proj'); -goog.require('ol.source.Image'); -goog.require('ol.source.WMSServerType'); -goog.require('ol.string'); -goog.require('ol.uri'); - - -/** - * @classdesc - * Source for WMS servers providing single, untiled images. - * - * @constructor - * @fires ol.source.Image.Event - * @extends {ol.source.Image} - * @param {olx.source.ImageWMSOptions=} opt_options Options. - * @api - */ -ol.source.ImageWMS = function(opt_options) { - - var options = opt_options || {}; - - ol.source.Image.call(this, { - attributions: options.attributions, - logo: options.logo, - projection: options.projection, - resolutions: options.resolutions - }); - - /** - * @private - * @type {?string} - */ - this.crossOrigin_ = - options.crossOrigin !== undefined ? options.crossOrigin : null; - - /** - * @private - * @type {string|undefined} - */ - this.url_ = options.url; - - /** - * @private - * @type {ol.ImageLoadFunctionType} - */ - this.imageLoadFunction_ = options.imageLoadFunction !== undefined ? - options.imageLoadFunction : ol.source.Image.defaultImageLoadFunction; - - /** - * @private - * @type {!Object} - */ - this.params_ = options.params || {}; - - /** - * @private - * @type {boolean} - */ - this.v13_ = true; - this.updateV13_(); - - /** - * @private - * @type {ol.source.WMSServerType|undefined} - */ - this.serverType_ = /** @type {ol.source.WMSServerType|undefined} */ (options.serverType); - - /** - * @private - * @type {boolean} - */ - this.hidpi_ = options.hidpi !== undefined ? options.hidpi : true; - - /** - * @private - * @type {ol.Image} - */ - this.image_ = null; - - /** - * @private - * @type {ol.Size} - */ - this.imageSize_ = [0, 0]; - - /** - * @private - * @type {number} - */ - this.renderedRevision_ = 0; - - /** - * @private - * @type {number} - */ - this.ratio_ = options.ratio !== undefined ? options.ratio : 1.5; - -}; -ol.inherits(ol.source.ImageWMS, ol.source.Image); - - -/** - * @const - * @type {ol.Size} - * @private - */ -ol.source.ImageWMS.GETFEATUREINFO_IMAGE_SIZE_ = [101, 101]; - - -/** - * Return the GetFeatureInfo URL for the passed coordinate, resolution, and - * projection. Return `undefined` if the GetFeatureInfo URL cannot be - * constructed. - * @param {ol.Coordinate} coordinate Coordinate. - * @param {number} resolution Resolution. - * @param {ol.ProjectionLike} projection Projection. - * @param {!Object} params GetFeatureInfo params. `INFO_FORMAT` at least should - * be provided. If `QUERY_LAYERS` is not provided then the layers specified - * in the `LAYERS` parameter will be used. `VERSION` should not be - * specified here. - * @return {string|undefined} GetFeatureInfo URL. - * @api - */ -ol.source.ImageWMS.prototype.getGetFeatureInfoUrl = function(coordinate, resolution, projection, params) { - if (this.url_ === undefined) { - return undefined; - } - - var extent = ol.extent.getForViewAndSize( - coordinate, resolution, 0, - ol.source.ImageWMS.GETFEATUREINFO_IMAGE_SIZE_); - - var baseParams = { - 'SERVICE': 'WMS', - 'VERSION': ol.DEFAULT_WMS_VERSION, - 'REQUEST': 'GetFeatureInfo', - 'FORMAT': 'image/png', - 'TRANSPARENT': true, - 'QUERY_LAYERS': this.params_['LAYERS'] - }; - ol.obj.assign(baseParams, this.params_, params); - - var x = Math.floor((coordinate[0] - extent[0]) / resolution); - var y = Math.floor((extent[3] - coordinate[1]) / resolution); - baseParams[this.v13_ ? 'I' : 'X'] = x; - baseParams[this.v13_ ? 'J' : 'Y'] = y; - - return this.getRequestUrl_( - extent, ol.source.ImageWMS.GETFEATUREINFO_IMAGE_SIZE_, - 1, ol.proj.get(projection), baseParams); -}; - - -/** - * Get the user-provided params, i.e. those passed to the constructor through - * the "params" option, and possibly updated using the updateParams method. - * @return {Object} Params. - * @api - */ -ol.source.ImageWMS.prototype.getParams = function() { - return this.params_; -}; - - -/** - * @inheritDoc - */ -ol.source.ImageWMS.prototype.getImageInternal = function(extent, resolution, pixelRatio, projection) { - - if (this.url_ === undefined) { - return null; - } - - resolution = this.findNearestResolution(resolution); - - if (pixelRatio != 1 && (!this.hidpi_ || this.serverType_ === undefined)) { - pixelRatio = 1; - } - - var imageResolution = resolution / pixelRatio; - - var center = ol.extent.getCenter(extent); - var viewWidth = Math.ceil(ol.extent.getWidth(extent) / imageResolution); - var viewHeight = Math.ceil(ol.extent.getHeight(extent) / imageResolution); - var viewExtent = ol.extent.getForViewAndSize(center, imageResolution, 0, - [viewWidth, viewHeight]); - var requestWidth = Math.ceil(this.ratio_ * ol.extent.getWidth(extent) / imageResolution); - var requestHeight = Math.ceil(this.ratio_ * ol.extent.getHeight(extent) / imageResolution); - var requestExtent = ol.extent.getForViewAndSize(center, imageResolution, 0, - [requestWidth, requestHeight]); - - var image = this.image_; - if (image && - this.renderedRevision_ == this.getRevision() && - image.getResolution() == resolution && - image.getPixelRatio() == pixelRatio && - ol.extent.containsExtent(image.getExtent(), viewExtent)) { - return image; - } - - var params = { - 'SERVICE': 'WMS', - 'VERSION': ol.DEFAULT_WMS_VERSION, - 'REQUEST': 'GetMap', - 'FORMAT': 'image/png', - 'TRANSPARENT': true - }; - ol.obj.assign(params, this.params_); - - this.imageSize_[0] = Math.round(ol.extent.getWidth(requestExtent) / imageResolution); - this.imageSize_[1] = Math.round(ol.extent.getHeight(requestExtent) / imageResolution); - - var url = this.getRequestUrl_(requestExtent, this.imageSize_, pixelRatio, - projection, params); - - this.image_ = new ol.Image(requestExtent, resolution, pixelRatio, - this.getAttributions(), url, this.crossOrigin_, this.imageLoadFunction_); - - this.renderedRevision_ = this.getRevision(); - - ol.events.listen(this.image_, ol.events.EventType.CHANGE, - this.handleImageChange, this); - - return this.image_; - -}; - - -/** - * Return the image load function of the source. - * @return {ol.ImageLoadFunctionType} The image load function. - * @api - */ -ol.source.ImageWMS.prototype.getImageLoadFunction = function() { - return this.imageLoadFunction_; -}; - - -/** - * @param {ol.Extent} extent Extent. - * @param {ol.Size} size Size. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.proj.Projection} projection Projection. - * @param {Object} params Params. - * @return {string} Request URL. - * @private - */ -ol.source.ImageWMS.prototype.getRequestUrl_ = function(extent, size, pixelRatio, projection, params) { - - ol.asserts.assert(this.url_ !== undefined, 9); // `url` must be configured or set using `#setUrl()` - - params[this.v13_ ? 'CRS' : 'SRS'] = projection.getCode(); - - if (!('STYLES' in this.params_)) { - params['STYLES'] = ''; - } - - if (pixelRatio != 1) { - switch (this.serverType_) { - case ol.source.WMSServerType.GEOSERVER: - var dpi = (90 * pixelRatio + 0.5) | 0; - if ('FORMAT_OPTIONS' in params) { - params['FORMAT_OPTIONS'] += ';dpi:' + dpi; - } else { - params['FORMAT_OPTIONS'] = 'dpi:' + dpi; - } - break; - case ol.source.WMSServerType.MAPSERVER: - params['MAP_RESOLUTION'] = 90 * pixelRatio; - break; - case ol.source.WMSServerType.CARMENTA_SERVER: - case ol.source.WMSServerType.QGIS: - params['DPI'] = 90 * pixelRatio; - break; - default: - ol.asserts.assert(false, 8); // Unknown `serverType` configured - break; - } - } - - params['WIDTH'] = size[0]; - params['HEIGHT'] = size[1]; - - var axisOrientation = projection.getAxisOrientation(); - var bbox; - if (this.v13_ && axisOrientation.substr(0, 2) == 'ne') { - bbox = [extent[1], extent[0], extent[3], extent[2]]; - } else { - bbox = extent; - } - params['BBOX'] = bbox.join(','); - - return ol.uri.appendParams(/** @type {string} */ (this.url_), params); -}; - - -/** - * Return the URL used for this WMS source. - * @return {string|undefined} URL. - * @api - */ -ol.source.ImageWMS.prototype.getUrl = function() { - return this.url_; -}; - - -/** - * Set the image load function of the source. - * @param {ol.ImageLoadFunctionType} imageLoadFunction Image load function. - * @api - */ -ol.source.ImageWMS.prototype.setImageLoadFunction = function( - imageLoadFunction) { - this.image_ = null; - this.imageLoadFunction_ = imageLoadFunction; - this.changed(); -}; - - -/** - * Set the URL to use for requests. - * @param {string|undefined} url URL. - * @api - */ -ol.source.ImageWMS.prototype.setUrl = function(url) { - if (url != this.url_) { - this.url_ = url; - this.image_ = null; - this.changed(); - } -}; - - -/** - * Update the user-provided params. - * @param {Object} params Params. - * @api - */ -ol.source.ImageWMS.prototype.updateParams = function(params) { - ol.obj.assign(this.params_, params); - this.updateV13_(); - this.image_ = null; - this.changed(); -}; - - -/** - * @private - */ -ol.source.ImageWMS.prototype.updateV13_ = function() { - var version = this.params_['VERSION'] || ol.DEFAULT_WMS_VERSION; - this.v13_ = ol.string.compareVersions(version, '1.3') >= 0; -}; - -goog.provide('ol.source.OSM'); - -goog.require('ol'); -goog.require('ol.Attribution'); -goog.require('ol.source.XYZ'); - - -/** - * @classdesc - * Layer source for the OpenStreetMap tile server. - * - * @constructor - * @extends {ol.source.XYZ} - * @param {olx.source.OSMOptions=} opt_options Open Street Map options. - * @api - */ -ol.source.OSM = function(opt_options) { - - var options = opt_options || {}; - - var attributions; - if (options.attributions !== undefined) { - attributions = options.attributions; - } else { - attributions = [ol.source.OSM.ATTRIBUTION]; - } - - var crossOrigin = options.crossOrigin !== undefined ? - options.crossOrigin : 'anonymous'; - - var url = options.url !== undefined ? - options.url : 'https://{a-c}.tile.openstreetmap.org/{z}/{x}/{y}.png'; - - ol.source.XYZ.call(this, { - attributions: attributions, - cacheSize: options.cacheSize, - crossOrigin: crossOrigin, - opaque: options.opaque !== undefined ? options.opaque : true, - maxZoom: options.maxZoom !== undefined ? options.maxZoom : 19, - reprojectionErrorThreshold: options.reprojectionErrorThreshold, - tileLoadFunction: options.tileLoadFunction, - url: url, - wrapX: options.wrapX - }); - -}; -ol.inherits(ol.source.OSM, ol.source.XYZ); - - -/** - * The attribution containing a link to the OpenStreetMap Copyright and License - * page. - * @const - * @type {ol.Attribution} - * @api - */ -ol.source.OSM.ATTRIBUTION = new ol.Attribution({ - html: '© ' + - '<a href="https://www.openstreetmap.org/copyright">OpenStreetMap</a> ' + - 'contributors.' -}); - - -/** - * @fileoverview - * @suppress {accessControls, ambiguousFunctionDecl, checkDebuggerStatement, checkRegExp, checkTypes, checkVars, const, constantProperty, deprecated, duplicate, es5Strict, fileoverviewTags, missingProperties, nonStandardJsDocs, strictModuleDepCheck, suspiciousCode, undefinedNames, undefinedVars, unknownDefines, unusedLocalVariables, uselessCode, visibility} - */ -goog.provide('ol.ext.pixelworks.Processor'); - -/** @typedef {function(*)} */ -ol.ext.pixelworks.Processor = function() {}; - -(function() {(function (exports) { -'use strict'; - -var hasImageData = true; -try { - new ImageData(10, 10); -} catch (_) { - hasImageData = false; -} -var context = document.createElement('canvas').getContext('2d'); -function newImageData$1(data, width, height) { - if (hasImageData) { - return new ImageData(data, width, height); - } else { - var imageData = context.createImageData(width, height); - imageData.data.set(data); - return imageData; - } -} -var newImageData_1 = newImageData$1; -var util = { - newImageData: newImageData_1 -}; - -var newImageData = util.newImageData; -function createMinion(operation) { - var workerHasImageData = true; - try { - new ImageData(10, 10); - } catch (_) { - workerHasImageData = false; - } - function newWorkerImageData(data, width, height) { - if (workerHasImageData) { - return new ImageData(data, width, height); - } else { - return {data: data, width: width, height: height}; - } - } - return function(data) { - var buffers = data['buffers']; - var meta = data['meta']; - var imageOps = data['imageOps']; - var width = data['width']; - var height = data['height']; - var numBuffers = buffers.length; - var numBytes = buffers[0].byteLength; - var output, b; - if (imageOps) { - var images = new Array(numBuffers); - for (b = 0; b < numBuffers; ++b) { - images[b] = newWorkerImageData( - new Uint8ClampedArray(buffers[b]), width, height); - } - output = operation(images, meta).data; - } else { - output = new Uint8ClampedArray(numBytes); - var arrays = new Array(numBuffers); - var pixels = new Array(numBuffers); - for (b = 0; b < numBuffers; ++b) { - arrays[b] = new Uint8ClampedArray(buffers[b]); - pixels[b] = [0, 0, 0, 0]; - } - for (var i = 0; i < numBytes; i += 4) { - for (var j = 0; j < numBuffers; ++j) { - var array = arrays[j]; - pixels[j][0] = array[i]; - pixels[j][1] = array[i + 1]; - pixels[j][2] = array[i + 2]; - pixels[j][3] = array[i + 3]; - } - var pixel = operation(pixels, meta); - output[i] = pixel[0]; - output[i + 1] = pixel[1]; - output[i + 2] = pixel[2]; - output[i + 3] = pixel[3]; - } - } - return output.buffer; - }; -} -function createWorker(config, onMessage) { - var lib = Object.keys(config.lib || {}).map(function(name) { - return 'var ' + name + ' = ' + config.lib[name].toString() + ';'; - }); - var lines = lib.concat([ - 'var __minion__ = (' + createMinion.toString() + ')(', config.operation.toString(), ');', - 'self.addEventListener("message", function(event) {', - ' var buffer = __minion__(event.data);', - ' self.postMessage({buffer: buffer, meta: event.data.meta}, [buffer]);', - '});' - ]); - var blob = new Blob(lines, {type: 'text/javascript'}); - var source = URL.createObjectURL(blob); - var worker = new Worker(source); - worker.addEventListener('message', onMessage); - return worker; -} -function createFauxWorker(config, onMessage) { - var minion = createMinion(config.operation); - return { - postMessage: function(data) { - setTimeout(function() { - onMessage({'data': {'buffer': minion(data), 'meta': data['meta']}}); - }, 0); - } - }; -} -function Processor(config) { - this._imageOps = !!config.imageOps; - var threads; - if (config.threads === 0) { - threads = 0; - } else if (this._imageOps) { - threads = 1; - } else { - threads = config.threads || 1; - } - var workers = []; - if (threads) { - for (var i = 0; i < threads; ++i) { - workers[i] = createWorker(config, this._onWorkerMessage.bind(this, i)); - } - } else { - workers[0] = createFauxWorker(config, this._onWorkerMessage.bind(this, 0)); - } - this._workers = workers; - this._queue = []; - this._maxQueueLength = config.queue || Infinity; - this._running = 0; - this._dataLookup = {}; - this._job = null; -} -Processor.prototype.process = function(inputs, meta, callback) { - this._enqueue({ - inputs: inputs, - meta: meta, - callback: callback - }); - this._dispatch(); -}; -Processor.prototype.destroy = function() { - for (var key in this) { - this[key] = null; - } - this._destroyed = true; -}; -Processor.prototype._enqueue = function(job) { - this._queue.push(job); - while (this._queue.length > this._maxQueueLength) { - this._queue.shift().callback(null, null); - } -}; -Processor.prototype._dispatch = function() { - if (this._running === 0 && this._queue.length > 0) { - var job = this._job = this._queue.shift(); - var width = job.inputs[0].width; - var height = job.inputs[0].height; - var buffers = job.inputs.map(function(input) { - return input.data.buffer; - }); - var threads = this._workers.length; - this._running = threads; - if (threads === 1) { - this._workers[0].postMessage({ - 'buffers': buffers, - 'meta': job.meta, - 'imageOps': this._imageOps, - 'width': width, - 'height': height - }, buffers); - } else { - var length = job.inputs[0].data.length; - var segmentLength = 4 * Math.ceil(length / 4 / threads); - for (var i = 0; i < threads; ++i) { - var offset = i * segmentLength; - var slices = []; - for (var j = 0, jj = buffers.length; j < jj; ++j) { - slices.push(buffers[i].slice(offset, offset + segmentLength)); - } - this._workers[i].postMessage({ - 'buffers': slices, - 'meta': job.meta, - 'imageOps': this._imageOps, - 'width': width, - 'height': height - }, slices); - } - } - } -}; -Processor.prototype._onWorkerMessage = function(index, event) { - if (this._destroyed) { - return; - } - this._dataLookup[index] = event.data; - --this._running; - if (this._running === 0) { - this._resolveJob(); - } -}; -Processor.prototype._resolveJob = function() { - var job = this._job; - var threads = this._workers.length; - var data, meta; - if (threads === 1) { - data = new Uint8ClampedArray(this._dataLookup[0]['buffer']); - meta = this._dataLookup[0]['meta']; - } else { - var length = job.inputs[0].data.length; - data = new Uint8ClampedArray(length); - meta = new Array(length); - var segmentLength = 4 * Math.ceil(length / 4 / threads); - for (var i = 0; i < threads; ++i) { - var buffer = this._dataLookup[i]['buffer']; - var offset = i * segmentLength; - data.set(new Uint8ClampedArray(buffer), offset); - meta[i] = this._dataLookup[i]['meta']; - } - } - this._job = null; - this._dataLookup = {}; - job.callback(null, - newImageData(data, job.inputs[0].width, job.inputs[0].height), meta); - this._dispatch(); -}; -var processor = Processor; - -var Processor_1 = processor; -var lib = { - Processor: Processor_1 -}; - -exports['default'] = lib; -exports.Processor = Processor_1; - -}((this.pixelworks = this.pixelworks || {})));}).call(ol.ext); - -goog.provide('ol.source.RasterOperationType'); - -/** - * Raster operation type. Supported values are `'pixel'` and `'image'`. - * @enum {string} - */ -ol.source.RasterOperationType = { - PIXEL: 'pixel', - IMAGE: 'image' -}; - -goog.provide('ol.source.Raster'); - -goog.require('ol'); -goog.require('ol.ImageCanvas'); -goog.require('ol.TileQueue'); -goog.require('ol.dom'); -goog.require('ol.events'); -goog.require('ol.events.Event'); -goog.require('ol.events.EventType'); -goog.require('ol.ext.pixelworks.Processor'); -goog.require('ol.extent'); -goog.require('ol.layer.Image'); -goog.require('ol.layer.Tile'); -goog.require('ol.obj'); -goog.require('ol.renderer.canvas.ImageLayer'); -goog.require('ol.renderer.canvas.TileLayer'); -goog.require('ol.source.Image'); -goog.require('ol.source.RasterOperationType'); -goog.require('ol.source.State'); -goog.require('ol.source.Tile'); -goog.require('ol.transform'); - - -/** - * @classdesc - * A source that transforms data from any number of input sources using an array - * of {@link ol.RasterOperation} functions to transform input pixel values into - * output pixel values. - * - * @constructor - * @extends {ol.source.Image} - * @fires ol.source.Raster.Event - * @param {olx.source.RasterOptions} options Options. - * @api - */ -ol.source.Raster = function(options) { - - /** - * @private - * @type {*} - */ - this.worker_ = null; - - /** - * @private - * @type {ol.source.RasterOperationType} - */ - this.operationType_ = options.operationType !== undefined ? - options.operationType : ol.source.RasterOperationType.PIXEL; - - /** - * @private - * @type {number} - */ - this.threads_ = options.threads !== undefined ? options.threads : 1; - - /** - * @private - * @type {Array.<ol.renderer.canvas.Layer>} - */ - this.renderers_ = ol.source.Raster.createRenderers_(options.sources); - - for (var r = 0, rr = this.renderers_.length; r < rr; ++r) { - ol.events.listen(this.renderers_[r], ol.events.EventType.CHANGE, - this.changed, this); - } - - /** - * @private - * @type {ol.TileQueue} - */ - this.tileQueue_ = new ol.TileQueue( - function() { - return 1; - }, - this.changed.bind(this)); - - var layerStatesArray = ol.source.Raster.getLayerStatesArray_(this.renderers_); - var layerStates = {}; - for (var i = 0, ii = layerStatesArray.length; i < ii; ++i) { - layerStates[ol.getUid(layerStatesArray[i].layer)] = layerStatesArray[i]; - } - - /** - * The most recently requested frame state. - * @type {olx.FrameState} - * @private - */ - this.requestedFrameState_; - - /** - * The most recently rendered image canvas. - * @type {ol.ImageCanvas} - * @private - */ - this.renderedImageCanvas_ = null; - - /** - * The most recently rendered revision. - * @type {number} - */ - this.renderedRevision_; - - /** - * @private - * @type {olx.FrameState} - */ - this.frameState_ = { - animate: false, - attributions: {}, - coordinateToPixelTransform: ol.transform.create(), - extent: null, - focus: null, - index: 0, - layerStates: layerStates, - layerStatesArray: layerStatesArray, - logos: {}, - pixelRatio: 1, - pixelToCoordinateTransform: ol.transform.create(), - postRenderFunctions: [], - size: [0, 0], - skippedFeatureUids: {}, - tileQueue: this.tileQueue_, - time: Date.now(), - usedTiles: {}, - viewState: /** @type {olx.ViewState} */ ({ - rotation: 0 - }), - viewHints: [], - wantedTiles: {} - }; - - ol.source.Image.call(this, {}); - - if (options.operation !== undefined) { - this.setOperation(options.operation, options.lib); - } - -}; -ol.inherits(ol.source.Raster, ol.source.Image); - - -/** - * Set the operation. - * @param {ol.RasterOperation} operation New operation. - * @param {Object=} opt_lib Functions that will be available to operations run - * in a worker. - * @api - */ -ol.source.Raster.prototype.setOperation = function(operation, opt_lib) { - this.worker_ = new ol.ext.pixelworks.Processor({ - operation: operation, - imageOps: this.operationType_ === ol.source.RasterOperationType.IMAGE, - queue: 1, - lib: opt_lib, - threads: this.threads_ - }); - this.changed(); -}; - - -/** - * Update the stored frame state. - * @param {ol.Extent} extent The view extent (in map units). - * @param {number} resolution The view resolution. - * @param {ol.proj.Projection} projection The view projection. - * @return {olx.FrameState} The updated frame state. - * @private - */ -ol.source.Raster.prototype.updateFrameState_ = function(extent, resolution, projection) { - - var frameState = /** @type {olx.FrameState} */ ( - ol.obj.assign({}, this.frameState_)); - - frameState.viewState = /** @type {olx.ViewState} */ ( - ol.obj.assign({}, frameState.viewState)); - - var center = ol.extent.getCenter(extent); - - frameState.extent = extent.slice(); - frameState.focus = center; - frameState.size[0] = Math.round(ol.extent.getWidth(extent) / resolution); - frameState.size[1] = Math.round(ol.extent.getHeight(extent) / resolution); - frameState.time = Date.now(); - frameState.animate = false; - - var viewState = frameState.viewState; - viewState.center = center; - viewState.projection = projection; - viewState.resolution = resolution; - return frameState; -}; - - -/** - * Determine if all sources are ready. - * @return {boolean} All sources are ready. - * @private - */ -ol.source.Raster.prototype.allSourcesReady_ = function() { - var ready = true; - var source; - for (var i = 0, ii = this.renderers_.length; i < ii; ++i) { - source = this.renderers_[i].getLayer().getSource(); - if (source.getState() !== ol.source.State.READY) { - ready = false; - break; - } - } - return ready; -}; - - -/** - * @inheritDoc - */ -ol.source.Raster.prototype.getImage = function(extent, resolution, pixelRatio, projection) { - if (!this.allSourcesReady_()) { - return null; - } - - var frameState = this.updateFrameState_(extent, resolution, projection); - this.requestedFrameState_ = frameState; - - // check if we can't reuse the existing ol.ImageCanvas - if (this.renderedImageCanvas_) { - var renderedResolution = this.renderedImageCanvas_.getResolution(); - var renderedExtent = this.renderedImageCanvas_.getExtent(); - if (resolution !== renderedResolution || !ol.extent.equals(extent, renderedExtent)) { - this.renderedImageCanvas_ = null; - } - } - - if (!this.renderedImageCanvas_ || this.getRevision() !== this.renderedRevision_) { - this.processSources_(); - } - - frameState.tileQueue.loadMoreTiles(16, 16); - - if (frameState.animate) { - requestAnimationFrame(this.changed.bind(this)); - } - - return this.renderedImageCanvas_; -}; - - -/** - * Start processing source data. - * @private - */ -ol.source.Raster.prototype.processSources_ = function() { - var frameState = this.requestedFrameState_; - var len = this.renderers_.length; - var imageDatas = new Array(len); - for (var i = 0; i < len; ++i) { - var imageData = ol.source.Raster.getImageData_( - this.renderers_[i], frameState, frameState.layerStatesArray[i]); - if (imageData) { - imageDatas[i] = imageData; - } else { - return; - } - } - - var data = {}; - this.dispatchEvent(new ol.source.Raster.Event( - ol.source.Raster.EventType_.BEFOREOPERATIONS, frameState, data)); - this.worker_.process(imageDatas, data, - this.onWorkerComplete_.bind(this, frameState)); -}; - - -/** - * Called when pixel processing is complete. - * @param {olx.FrameState} frameState The frame state. - * @param {Error} err Any error during processing. - * @param {ImageData} output The output image data. - * @param {Object} data The user data. - * @private - */ -ol.source.Raster.prototype.onWorkerComplete_ = function(frameState, err, output, data) { - if (err || !output) { - return; - } - - // do nothing if extent or resolution changed - var extent = frameState.extent; - var resolution = frameState.viewState.resolution; - if (resolution !== this.requestedFrameState_.viewState.resolution || - !ol.extent.equals(extent, this.requestedFrameState_.extent)) { - return; - } - - var context; - if (this.renderedImageCanvas_) { - context = this.renderedImageCanvas_.getImage().getContext('2d'); - } else { - var width = Math.round(ol.extent.getWidth(extent) / resolution); - var height = Math.round(ol.extent.getHeight(extent) / resolution); - context = ol.dom.createCanvasContext2D(width, height); - this.renderedImageCanvas_ = new ol.ImageCanvas( - extent, resolution, 1, this.getAttributions(), context.canvas); - } - context.putImageData(output, 0, 0); - - this.changed(); - this.renderedRevision_ = this.getRevision(); - - this.dispatchEvent(new ol.source.Raster.Event( - ol.source.Raster.EventType_.AFTEROPERATIONS, frameState, data)); -}; - - -/** - * Get image data from a renderer. - * @param {ol.renderer.canvas.Layer} renderer Layer renderer. - * @param {olx.FrameState} frameState The frame state. - * @param {ol.LayerState} layerState The layer state. - * @return {ImageData} The image data. - * @private - */ -ol.source.Raster.getImageData_ = function(renderer, frameState, layerState) { - if (!renderer.prepareFrame(frameState, layerState)) { - return null; - } - var width = frameState.size[0]; - var height = frameState.size[1]; - if (!ol.source.Raster.context_) { - ol.source.Raster.context_ = ol.dom.createCanvasContext2D(width, height); - } else { - var canvas = ol.source.Raster.context_.canvas; - if (canvas.width !== width || canvas.height !== height) { - ol.source.Raster.context_ = ol.dom.createCanvasContext2D(width, height); - } else { - ol.source.Raster.context_.clearRect(0, 0, width, height); - } - } - renderer.composeFrame(frameState, layerState, ol.source.Raster.context_); - return ol.source.Raster.context_.getImageData(0, 0, width, height); -}; - - -/** - * A reusable canvas context. - * @type {CanvasRenderingContext2D} - * @private - */ -ol.source.Raster.context_ = null; - - -/** - * Get a list of layer states from a list of renderers. - * @param {Array.<ol.renderer.canvas.Layer>} renderers Layer renderers. - * @return {Array.<ol.LayerState>} The layer states. - * @private - */ -ol.source.Raster.getLayerStatesArray_ = function(renderers) { - return renderers.map(function(renderer) { - return renderer.getLayer().getLayerState(); - }); -}; - - -/** - * Create renderers for all sources. - * @param {Array.<ol.source.Source>} sources The sources. - * @return {Array.<ol.renderer.canvas.Layer>} Array of layer renderers. - * @private - */ -ol.source.Raster.createRenderers_ = function(sources) { - var len = sources.length; - var renderers = new Array(len); - for (var i = 0; i < len; ++i) { - renderers[i] = ol.source.Raster.createRenderer_(sources[i]); - } - return renderers; -}; - - -/** - * Create a renderer for the provided source. - * @param {ol.source.Source} source The source. - * @return {ol.renderer.canvas.Layer} The renderer. - * @private - */ -ol.source.Raster.createRenderer_ = function(source) { - var renderer = null; - if (source instanceof ol.source.Tile) { - renderer = ol.source.Raster.createTileRenderer_(source); - } else if (source instanceof ol.source.Image) { - renderer = ol.source.Raster.createImageRenderer_(source); - } - return renderer; -}; - - -/** - * Create an image renderer for the provided source. - * @param {ol.source.Image} source The source. - * @return {ol.renderer.canvas.Layer} The renderer. - * @private - */ -ol.source.Raster.createImageRenderer_ = function(source) { - var layer = new ol.layer.Image({source: source}); - return new ol.renderer.canvas.ImageLayer(layer); -}; - - -/** - * Create a tile renderer for the provided source. - * @param {ol.source.Tile} source The source. - * @return {ol.renderer.canvas.Layer} The renderer. - * @private - */ -ol.source.Raster.createTileRenderer_ = function(source) { - var layer = new ol.layer.Tile({source: source}); - return new ol.renderer.canvas.TileLayer(layer); -}; - - -/** - * @classdesc - * Events emitted by {@link ol.source.Raster} instances are instances of this - * type. - * - * @constructor - * @extends {ol.events.Event} - * @implements {oli.source.RasterEvent} - * @param {string} type Type. - * @param {olx.FrameState} frameState The frame state. - * @param {Object} data An object made available to operations. - */ -ol.source.Raster.Event = function(type, frameState, data) { - ol.events.Event.call(this, type); - - /** - * The raster extent. - * @type {ol.Extent} - * @api - */ - this.extent = frameState.extent; - - /** - * The pixel resolution (map units per pixel). - * @type {number} - * @api - */ - this.resolution = frameState.viewState.resolution / frameState.pixelRatio; - - /** - * An object made available to all operations. This can be used by operations - * as a storage object (e.g. for calculating statistics). - * @type {Object} - * @api - */ - this.data = data; - -}; -ol.inherits(ol.source.Raster.Event, ol.events.Event); - - -/** - * @override - */ -ol.source.Raster.prototype.getImageInternal = function() { - return null; // not implemented -}; - - -/** - * @enum {string} - * @private - */ -ol.source.Raster.EventType_ = { - /** - * Triggered before operations are run. - * @event ol.source.Raster.Event#beforeoperations - * @api - */ - BEFOREOPERATIONS: 'beforeoperations', - - /** - * Triggered after operations are run. - * @event ol.source.Raster.Event#afteroperations - * @api - */ - AFTEROPERATIONS: 'afteroperations' -}; - -goog.provide('ol.source.Stamen'); - -goog.require('ol'); -goog.require('ol.Attribution'); -goog.require('ol.source.OSM'); -goog.require('ol.source.XYZ'); - - -/** - * @classdesc - * Layer source for the Stamen tile server. - * - * @constructor - * @extends {ol.source.XYZ} - * @param {olx.source.StamenOptions} options Stamen options. - * @api - */ -ol.source.Stamen = function(options) { - var i = options.layer.indexOf('-'); - var provider = i == -1 ? options.layer : options.layer.slice(0, i); - var providerConfig = ol.source.Stamen.ProviderConfig[provider]; - - var layerConfig = ol.source.Stamen.LayerConfig[options.layer]; - - var url = options.url !== undefined ? options.url : - 'https://stamen-tiles-{a-d}.a.ssl.fastly.net/' + options.layer + - '/{z}/{x}/{y}.' + layerConfig.extension; - - ol.source.XYZ.call(this, { - attributions: ol.source.Stamen.ATTRIBUTIONS, - cacheSize: options.cacheSize, - crossOrigin: 'anonymous', - maxZoom: options.maxZoom != undefined ? options.maxZoom : providerConfig.maxZoom, - minZoom: options.minZoom != undefined ? options.minZoom : providerConfig.minZoom, - opaque: layerConfig.opaque, - reprojectionErrorThreshold: options.reprojectionErrorThreshold, - tileLoadFunction: options.tileLoadFunction, - url: url, - wrapX: options.wrapX - }); -}; -ol.inherits(ol.source.Stamen, ol.source.XYZ); - - -/** - * @const - * @type {Array.<ol.Attribution>} - */ -ol.source.Stamen.ATTRIBUTIONS = [ - new ol.Attribution({ - html: 'Map tiles by <a href="https://stamen.com/">Stamen Design</a>, ' + - 'under <a href="https://creativecommons.org/licenses/by/3.0/">CC BY' + - ' 3.0</a>.' - }), - ol.source.OSM.ATTRIBUTION -]; - -/** - * @type {Object.<string, {extension: string, opaque: boolean}>} - */ -ol.source.Stamen.LayerConfig = { - 'terrain': { - extension: 'jpg', - opaque: true - }, - 'terrain-background': { - extension: 'jpg', - opaque: true - }, - 'terrain-labels': { - extension: 'png', - opaque: false - }, - 'terrain-lines': { - extension: 'png', - opaque: false - }, - 'toner-background': { - extension: 'png', - opaque: true - }, - 'toner': { - extension: 'png', - opaque: true - }, - 'toner-hybrid': { - extension: 'png', - opaque: false - }, - 'toner-labels': { - extension: 'png', - opaque: false - }, - 'toner-lines': { - extension: 'png', - opaque: false - }, - 'toner-lite': { - extension: 'png', - opaque: true - }, - 'watercolor': { - extension: 'jpg', - opaque: true - } -}; - -/** - * @type {Object.<string, {minZoom: number, maxZoom: number}>} - */ -ol.source.Stamen.ProviderConfig = { - 'terrain': { - minZoom: 4, - maxZoom: 18 - }, - 'toner': { - minZoom: 0, - maxZoom: 20 - }, - 'watercolor': { - minZoom: 1, - maxZoom: 16 - } -}; - -goog.provide('ol.source.TileArcGISRest'); - -goog.require('ol'); -goog.require('ol.extent'); -goog.require('ol.math'); -goog.require('ol.obj'); -goog.require('ol.size'); -goog.require('ol.source.TileImage'); -goog.require('ol.tilecoord'); -goog.require('ol.uri'); - - -/** - * @classdesc - * Layer source for tile data from ArcGIS Rest services. Map and Image - * Services are supported. - * - * For cached ArcGIS services, better performance is available using the - * {@link ol.source.XYZ} data source. - * - * @constructor - * @extends {ol.source.TileImage} - * @param {olx.source.TileArcGISRestOptions=} opt_options Tile ArcGIS Rest - * options. - * @api - */ -ol.source.TileArcGISRest = function(opt_options) { - - var options = opt_options || {}; - - ol.source.TileImage.call(this, { - attributions: options.attributions, - cacheSize: options.cacheSize, - crossOrigin: options.crossOrigin, - logo: options.logo, - projection: options.projection, - reprojectionErrorThreshold: options.reprojectionErrorThreshold, - tileGrid: options.tileGrid, - tileLoadFunction: options.tileLoadFunction, - url: options.url, - urls: options.urls, - wrapX: options.wrapX !== undefined ? options.wrapX : true, - transition: options.transition - }); - - /** - * @private - * @type {!Object} - */ - this.params_ = options.params || {}; - - /** - * @private - * @type {ol.Extent} - */ - this.tmpExtent_ = ol.extent.createEmpty(); - - this.setKey(this.getKeyForParams_()); -}; -ol.inherits(ol.source.TileArcGISRest, ol.source.TileImage); - - -/** - * @private - * @return {string} The key for the current params. - */ -ol.source.TileArcGISRest.prototype.getKeyForParams_ = function() { - var i = 0; - var res = []; - for (var key in this.params_) { - res[i++] = key + '-' + this.params_[key]; - } - return res.join('/'); -}; - - -/** - * Get the user-provided params, i.e. those passed to the constructor through - * the "params" option, and possibly updated using the updateParams method. - * @return {Object} Params. - * @api - */ -ol.source.TileArcGISRest.prototype.getParams = function() { - return this.params_; -}; - - -/** - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {ol.Size} tileSize Tile size. - * @param {ol.Extent} tileExtent Tile extent. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.proj.Projection} projection Projection. - * @param {Object} params Params. - * @return {string|undefined} Request URL. - * @private - */ -ol.source.TileArcGISRest.prototype.getRequestUrl_ = function(tileCoord, tileSize, tileExtent, - pixelRatio, projection, params) { - - var urls = this.urls; - if (!urls) { - return undefined; - } - - // ArcGIS Server only wants the numeric portion of the projection ID. - var srid = projection.getCode().split(':').pop(); - - params['SIZE'] = tileSize[0] + ',' + tileSize[1]; - params['BBOX'] = tileExtent.join(','); - params['BBOXSR'] = srid; - params['IMAGESR'] = srid; - params['DPI'] = Math.round( - params['DPI'] ? params['DPI'] * pixelRatio : 90 * pixelRatio - ); - - var url; - if (urls.length == 1) { - url = urls[0]; - } else { - var index = ol.math.modulo(ol.tilecoord.hash(tileCoord), urls.length); - url = urls[index]; - } - - var modifiedUrl = url - .replace(/MapServer\/?$/, 'MapServer/export') - .replace(/ImageServer\/?$/, 'ImageServer/exportImage'); - return ol.uri.appendParams(modifiedUrl, params); -}; - - -/** - * @inheritDoc - */ -ol.source.TileArcGISRest.prototype.getTilePixelRatio = function(pixelRatio) { - return /** @type {number} */ (pixelRatio); -}; - - -/** - * @inheritDoc - */ -ol.source.TileArcGISRest.prototype.fixedTileUrlFunction = function(tileCoord, pixelRatio, projection) { - - var tileGrid = this.getTileGrid(); - if (!tileGrid) { - tileGrid = this.getTileGridForProjection(projection); - } - - if (tileGrid.getResolutions().length <= tileCoord[0]) { - return undefined; - } - - var tileExtent = tileGrid.getTileCoordExtent( - tileCoord, this.tmpExtent_); - var tileSize = ol.size.toSize( - tileGrid.getTileSize(tileCoord[0]), this.tmpSize); - - if (pixelRatio != 1) { - tileSize = ol.size.scale(tileSize, pixelRatio, this.tmpSize); - } - - // Apply default params and override with user specified values. - var baseParams = { - 'F': 'image', - 'FORMAT': 'PNG32', - 'TRANSPARENT': true - }; - ol.obj.assign(baseParams, this.params_); - - return this.getRequestUrl_(tileCoord, tileSize, tileExtent, - pixelRatio, projection, baseParams); -}; - - -/** - * Update the user-provided params. - * @param {Object} params Params. - * @api - */ -ol.source.TileArcGISRest.prototype.updateParams = function(params) { - ol.obj.assign(this.params_, params); - this.setKey(this.getKeyForParams_()); -}; - -goog.provide('ol.source.TileDebug'); - -goog.require('ol'); -goog.require('ol.Tile'); -goog.require('ol.TileState'); -goog.require('ol.dom'); -goog.require('ol.size'); -goog.require('ol.source.Tile'); -goog.require('ol.tilecoord'); - - -/** - * @classdesc - * A pseudo tile source, which does not fetch tiles from a server, but renders - * a grid outline for the tile grid/projection along with the coordinates for - * each tile. See examples/canvas-tiles for an example. - * - * Uses Canvas context2d, so requires Canvas support. - * - * @constructor - * @extends {ol.source.Tile} - * @param {olx.source.TileDebugOptions} options Debug tile options. - * @api - */ -ol.source.TileDebug = function(options) { - - ol.source.Tile.call(this, { - opaque: false, - projection: options.projection, - tileGrid: options.tileGrid, - wrapX: options.wrapX !== undefined ? options.wrapX : true - }); - -}; -ol.inherits(ol.source.TileDebug, ol.source.Tile); - - -/** - * @inheritDoc - */ -ol.source.TileDebug.prototype.getTile = function(z, x, y) { - var tileCoordKey = ol.tilecoord.getKeyZXY(z, x, y); - if (this.tileCache.containsKey(tileCoordKey)) { - return /** @type {!ol.source.TileDebug.Tile_} */ (this.tileCache.get(tileCoordKey)); - } else { - var tileSize = ol.size.toSize(this.tileGrid.getTileSize(z)); - var tileCoord = [z, x, y]; - var textTileCoord = this.getTileCoordForTileUrlFunction(tileCoord); - var text = !textTileCoord ? '' : - this.getTileCoordForTileUrlFunction(textTileCoord).toString(); - var tile = new ol.source.TileDebug.Tile_(tileCoord, tileSize, text); - this.tileCache.set(tileCoordKey, tile); - return tile; - } -}; - - -/** - * @constructor - * @extends {ol.Tile} - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {ol.Size} tileSize Tile size. - * @param {string} text Text. - * @private - */ -ol.source.TileDebug.Tile_ = function(tileCoord, tileSize, text) { - - ol.Tile.call(this, tileCoord, ol.TileState.LOADED); - - /** - * @private - * @type {ol.Size} - */ - this.tileSize_ = tileSize; - - /** - * @private - * @type {string} - */ - this.text_ = text; - - /** - * @private - * @type {HTMLCanvasElement} - */ - this.canvas_ = null; - -}; -ol.inherits(ol.source.TileDebug.Tile_, ol.Tile); - - -/** - * Get the image element for this tile. - * @return {HTMLCanvasElement} Image. - */ -ol.source.TileDebug.Tile_.prototype.getImage = function() { - if (this.canvas_) { - return this.canvas_; - } else { - var tileSize = this.tileSize_; - var context = ol.dom.createCanvasContext2D(tileSize[0], tileSize[1]); - - context.strokeStyle = 'black'; - context.strokeRect(0.5, 0.5, tileSize[0] + 0.5, tileSize[1] + 0.5); - - context.fillStyle = 'black'; - context.textAlign = 'center'; - context.textBaseline = 'middle'; - context.font = '24px sans-serif'; - context.fillText(this.text_, tileSize[0] / 2, tileSize[1] / 2); - - this.canvas_ = context.canvas; - return context.canvas; - } -}; - - -/** - * @override - */ -ol.source.TileDebug.Tile_.prototype.load = function() {}; - -// FIXME check order of async callbacks - -/** - * @see http://mapbox.com/developers/api/ - */ - -goog.provide('ol.source.TileJSON'); - -goog.require('ol'); -goog.require('ol.Attribution'); -goog.require('ol.TileUrlFunction'); -goog.require('ol.asserts'); -goog.require('ol.extent'); -goog.require('ol.net'); -goog.require('ol.proj'); -goog.require('ol.source.State'); -goog.require('ol.source.TileImage'); -goog.require('ol.tilegrid'); - - -/** - * @classdesc - * Layer source for tile data in TileJSON format. - * - * @constructor - * @extends {ol.source.TileImage} - * @param {olx.source.TileJSONOptions} options TileJSON options. - * @api - */ -ol.source.TileJSON = function(options) { - - /** - * @type {TileJSON} - * @private - */ - this.tileJSON_ = null; - - ol.source.TileImage.call(this, { - attributions: options.attributions, - cacheSize: options.cacheSize, - crossOrigin: options.crossOrigin, - projection: ol.proj.get('EPSG:3857'), - reprojectionErrorThreshold: options.reprojectionErrorThreshold, - state: ol.source.State.LOADING, - tileLoadFunction: options.tileLoadFunction, - wrapX: options.wrapX !== undefined ? options.wrapX : true, - transition: options.transition - }); - - if (options.url) { - if (options.jsonp) { - ol.net.jsonp(options.url, this.handleTileJSONResponse.bind(this), - this.handleTileJSONError.bind(this)); - } else { - var client = new XMLHttpRequest(); - client.addEventListener('load', this.onXHRLoad_.bind(this)); - client.addEventListener('error', this.onXHRError_.bind(this)); - client.open('GET', options.url); - client.send(); - } - } else if (options.tileJSON) { - this.handleTileJSONResponse(options.tileJSON); - } else { - ol.asserts.assert(false, 51); // Either `url` or `tileJSON` options must be provided - } - -}; -ol.inherits(ol.source.TileJSON, ol.source.TileImage); - - -/** - * @private - * @param {Event} event The load event. - */ -ol.source.TileJSON.prototype.onXHRLoad_ = function(event) { - var client = /** @type {XMLHttpRequest} */ (event.target); - // status will be 0 for file:// urls - if (!client.status || client.status >= 200 && client.status < 300) { - var response; - try { - response = /** @type {TileJSON} */(JSON.parse(client.responseText)); - } catch (err) { - this.handleTileJSONError(); - return; - } - this.handleTileJSONResponse(response); - } else { - this.handleTileJSONError(); - } -}; - - -/** - * @private - * @param {Event} event The error event. - */ -ol.source.TileJSON.prototype.onXHRError_ = function(event) { - this.handleTileJSONError(); -}; - - -/** - * @return {TileJSON} The tilejson object. - * @api - */ -ol.source.TileJSON.prototype.getTileJSON = function() { - return this.tileJSON_; -}; - - -/** - * @protected - * @param {TileJSON} tileJSON Tile JSON. - */ -ol.source.TileJSON.prototype.handleTileJSONResponse = function(tileJSON) { - - var epsg4326Projection = ol.proj.get('EPSG:4326'); - - var sourceProjection = this.getProjection(); - var extent; - if (tileJSON.bounds !== undefined) { - var transform = ol.proj.getTransformFromProjections( - epsg4326Projection, sourceProjection); - extent = ol.extent.applyTransform(tileJSON.bounds, transform); - } - - var minZoom = tileJSON.minzoom || 0; - var maxZoom = tileJSON.maxzoom || 22; - var tileGrid = ol.tilegrid.createXYZ({ - extent: ol.tilegrid.extentFromProjection(sourceProjection), - maxZoom: maxZoom, - minZoom: minZoom - }); - this.tileGrid = tileGrid; - - this.tileUrlFunction = - ol.TileUrlFunction.createFromTemplates(tileJSON.tiles, tileGrid); - - if (tileJSON.attribution !== undefined && !this.getAttributions()) { - var attributionExtent = extent !== undefined ? - extent : epsg4326Projection.getExtent(); - /** @type {Object.<string, Array.<ol.TileRange>>} */ - var tileRanges = {}; - var z, zKey; - for (z = minZoom; z <= maxZoom; ++z) { - zKey = z.toString(); - tileRanges[zKey] = - [tileGrid.getTileRangeForExtentAndZ(attributionExtent, z)]; - } - this.setAttributions([ - new ol.Attribution({ - html: tileJSON.attribution, - tileRanges: tileRanges - }) - ]); - } - this.tileJSON_ = tileJSON; - this.setState(ol.source.State.READY); - -}; - - -/** - * @protected - */ -ol.source.TileJSON.prototype.handleTileJSONError = function() { - this.setState(ol.source.State.ERROR); -}; - -goog.provide('ol.source.TileUTFGrid'); - -goog.require('ol'); -goog.require('ol.Attribution'); -goog.require('ol.Tile'); -goog.require('ol.TileState'); -goog.require('ol.TileUrlFunction'); -goog.require('ol.asserts'); -goog.require('ol.events'); -goog.require('ol.events.EventType'); -goog.require('ol.extent'); -goog.require('ol.net'); -goog.require('ol.proj'); -goog.require('ol.source.State'); -goog.require('ol.source.Tile'); -goog.require('ol.tilecoord'); -goog.require('ol.tilegrid'); - - -/** - * @classdesc - * Layer source for UTFGrid interaction data loaded from TileJSON format. - * - * @constructor - * @extends {ol.source.Tile} - * @param {olx.source.TileUTFGridOptions} options Source options. - * @api - */ -ol.source.TileUTFGrid = function(options) { - ol.source.Tile.call(this, { - projection: ol.proj.get('EPSG:3857'), - state: ol.source.State.LOADING - }); - - /** - * @private - * @type {boolean} - */ - this.preemptive_ = options.preemptive !== undefined ? - options.preemptive : true; - - /** - * @private - * @type {!ol.TileUrlFunctionType} - */ - this.tileUrlFunction_ = ol.TileUrlFunction.nullTileUrlFunction; - - /** - * @private - * @type {string|undefined} - */ - this.template_ = undefined; - - /** - * @private - * @type {boolean} - */ - this.jsonp_ = options.jsonp || false; - - if (options.url) { - if (this.jsonp_) { - ol.net.jsonp(options.url, this.handleTileJSONResponse.bind(this), - this.handleTileJSONError.bind(this)); - } else { - var client = new XMLHttpRequest(); - client.addEventListener('load', this.onXHRLoad_.bind(this)); - client.addEventListener('error', this.onXHRError_.bind(this)); - client.open('GET', options.url); - client.send(); - } - } else if (options.tileJSON) { - this.handleTileJSONResponse(options.tileJSON); - } else { - ol.asserts.assert(false, 51); // Either `url` or `tileJSON` options must be provided - } -}; -ol.inherits(ol.source.TileUTFGrid, ol.source.Tile); - - -/** - * @private - * @param {Event} event The load event. - */ -ol.source.TileUTFGrid.prototype.onXHRLoad_ = function(event) { - var client = /** @type {XMLHttpRequest} */ (event.target); - // status will be 0 for file:// urls - if (!client.status || client.status >= 200 && client.status < 300) { - var response; - try { - response = /** @type {TileJSON} */(JSON.parse(client.responseText)); - } catch (err) { - this.handleTileJSONError(); - return; - } - this.handleTileJSONResponse(response); - } else { - this.handleTileJSONError(); - } -}; - - -/** - * @private - * @param {Event} event The error event. - */ -ol.source.TileUTFGrid.prototype.onXHRError_ = function(event) { - this.handleTileJSONError(); -}; - - -/** - * Return the template from TileJSON. - * @return {string|undefined} The template from TileJSON. - * @api - */ -ol.source.TileUTFGrid.prototype.getTemplate = function() { - return this.template_; -}; - - -/** - * Calls the callback (synchronously by default) with the available data - * for given coordinate and resolution (or `null` if not yet loaded or - * in case of an error). - * @param {ol.Coordinate} coordinate Coordinate. - * @param {number} resolution Resolution. - * @param {function(this: T, *)} callback Callback. - * @param {T=} opt_this The object to use as `this` in the callback. - * @param {boolean=} opt_request If `true` the callback is always async. - * The tile data is requested if not yet loaded. - * @template T - * @api - */ -ol.source.TileUTFGrid.prototype.forDataAtCoordinateAndResolution = function( - coordinate, resolution, callback, opt_this, opt_request) { - if (this.tileGrid) { - var tileCoord = this.tileGrid.getTileCoordForCoordAndResolution( - coordinate, resolution); - var tile = /** @type {!ol.source.TileUTFGrid.Tile_} */(this.getTile( - tileCoord[0], tileCoord[1], tileCoord[2], 1, this.getProjection())); - tile.forDataAtCoordinate(coordinate, callback, opt_this, opt_request); - } else { - if (opt_request === true) { - setTimeout(function() { - callback.call(opt_this, null); - }, 0); - } else { - callback.call(opt_this, null); - } - } -}; - - -/** - * @protected - */ -ol.source.TileUTFGrid.prototype.handleTileJSONError = function() { - this.setState(ol.source.State.ERROR); -}; - - -/** - * TODO: very similar to ol.source.TileJSON#handleTileJSONResponse - * @protected - * @param {TileJSON} tileJSON Tile JSON. - */ -ol.source.TileUTFGrid.prototype.handleTileJSONResponse = function(tileJSON) { - - var epsg4326Projection = ol.proj.get('EPSG:4326'); - - var sourceProjection = this.getProjection(); - var extent; - if (tileJSON.bounds !== undefined) { - var transform = ol.proj.getTransformFromProjections( - epsg4326Projection, sourceProjection); - extent = ol.extent.applyTransform(tileJSON.bounds, transform); - } - - var minZoom = tileJSON.minzoom || 0; - var maxZoom = tileJSON.maxzoom || 22; - var tileGrid = ol.tilegrid.createXYZ({ - extent: ol.tilegrid.extentFromProjection(sourceProjection), - maxZoom: maxZoom, - minZoom: minZoom - }); - this.tileGrid = tileGrid; - - this.template_ = tileJSON.template; - - var grids = tileJSON.grids; - if (!grids) { - this.setState(ol.source.State.ERROR); - return; - } - - this.tileUrlFunction_ = - ol.TileUrlFunction.createFromTemplates(grids, tileGrid); - - if (tileJSON.attribution !== undefined) { - var attributionExtent = extent !== undefined ? - extent : epsg4326Projection.getExtent(); - /** @type {Object.<string, Array.<ol.TileRange>>} */ - var tileRanges = {}; - var z, zKey; - for (z = minZoom; z <= maxZoom; ++z) { - zKey = z.toString(); - tileRanges[zKey] = - [tileGrid.getTileRangeForExtentAndZ(attributionExtent, z)]; - } - this.setAttributions([ - new ol.Attribution({ - html: tileJSON.attribution, - tileRanges: tileRanges - }) - ]); - } - - this.setState(ol.source.State.READY); - -}; - - -/** - * @inheritDoc - */ -ol.source.TileUTFGrid.prototype.getTile = function(z, x, y, pixelRatio, projection) { - var tileCoordKey = ol.tilecoord.getKeyZXY(z, x, y); - if (this.tileCache.containsKey(tileCoordKey)) { - return /** @type {!ol.Tile} */ (this.tileCache.get(tileCoordKey)); - } else { - var tileCoord = [z, x, y]; - var urlTileCoord = - this.getTileCoordForTileUrlFunction(tileCoord, projection); - var tileUrl = this.tileUrlFunction_(urlTileCoord, pixelRatio, projection); - var tile = new ol.source.TileUTFGrid.Tile_( - tileCoord, - tileUrl !== undefined ? ol.TileState.IDLE : ol.TileState.EMPTY, - tileUrl !== undefined ? tileUrl : '', - this.tileGrid.getTileCoordExtent(tileCoord), - this.preemptive_, - this.jsonp_); - this.tileCache.set(tileCoordKey, tile); - return tile; - } -}; - - -/** - * @inheritDoc - */ -ol.source.TileUTFGrid.prototype.useTile = function(z, x, y) { - var tileCoordKey = ol.tilecoord.getKeyZXY(z, x, y); - if (this.tileCache.containsKey(tileCoordKey)) { - this.tileCache.get(tileCoordKey); - } -}; - - -/** - * @constructor - * @extends {ol.Tile} - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {ol.TileState} state State. - * @param {string} src Image source URI. - * @param {ol.Extent} extent Extent of the tile. - * @param {boolean} preemptive Load the tile when visible (before it's needed). - * @param {boolean} jsonp Load the tile as a script. - * @private - */ -ol.source.TileUTFGrid.Tile_ = function(tileCoord, state, src, extent, preemptive, jsonp) { - - ol.Tile.call(this, tileCoord, state); - - /** - * @private - * @type {string} - */ - this.src_ = src; - - /** - * @private - * @type {ol.Extent} - */ - this.extent_ = extent; - - /** - * @private - * @type {boolean} - */ - this.preemptive_ = preemptive; - - /** - * @private - * @type {Array.<string>} - */ - this.grid_ = null; - - /** - * @private - * @type {Array.<string>} - */ - this.keys_ = null; - - /** - * @private - * @type {Object.<string, Object>|undefined} - */ - this.data_ = null; - - - /** - * @private - * @type {boolean} - */ - this.jsonp_ = jsonp; - -}; -ol.inherits(ol.source.TileUTFGrid.Tile_, ol.Tile); - - -/** - * Get the image element for this tile. - * @return {Image} Image. - */ -ol.source.TileUTFGrid.Tile_.prototype.getImage = function() { - return null; -}; - - -/** - * Synchronously returns data at given coordinate (if available). - * @param {ol.Coordinate} coordinate Coordinate. - * @return {*} The data. - */ -ol.source.TileUTFGrid.Tile_.prototype.getData = function(coordinate) { - if (!this.grid_ || !this.keys_) { - return null; - } - var xRelative = (coordinate[0] - this.extent_[0]) / - (this.extent_[2] - this.extent_[0]); - var yRelative = (coordinate[1] - this.extent_[1]) / - (this.extent_[3] - this.extent_[1]); - - var row = this.grid_[Math.floor((1 - yRelative) * this.grid_.length)]; - - if (typeof row !== 'string') { - return null; - } - - var code = row.charCodeAt(Math.floor(xRelative * row.length)); - if (code >= 93) { - code--; - } - if (code >= 35) { - code--; - } - code -= 32; - - var data = null; - if (code in this.keys_) { - var id = this.keys_[code]; - if (this.data_ && id in this.data_) { - data = this.data_[id]; - } else { - data = id; - } - } - return data; -}; - - -/** - * Calls the callback (synchronously by default) with the available data - * for given coordinate (or `null` if not yet loaded). - * @param {ol.Coordinate} coordinate Coordinate. - * @param {function(this: T, *)} callback Callback. - * @param {T=} opt_this The object to use as `this` in the callback. - * @param {boolean=} opt_request If `true` the callback is always async. - * The tile data is requested if not yet loaded. - * @template T - */ -ol.source.TileUTFGrid.Tile_.prototype.forDataAtCoordinate = function(coordinate, callback, opt_this, opt_request) { - if (this.state == ol.TileState.IDLE && opt_request === true) { - ol.events.listenOnce(this, ol.events.EventType.CHANGE, function(e) { - callback.call(opt_this, this.getData(coordinate)); - }, this); - this.loadInternal_(); - } else { - if (opt_request === true) { - setTimeout(function() { - callback.call(opt_this, this.getData(coordinate)); - }.bind(this), 0); - } else { - callback.call(opt_this, this.getData(coordinate)); - } - } -}; - - -/** - * @inheritDoc - */ -ol.source.TileUTFGrid.Tile_.prototype.getKey = function() { - return this.src_; -}; - - -/** - * @private - */ -ol.source.TileUTFGrid.Tile_.prototype.handleError_ = function() { - this.state = ol.TileState.ERROR; - this.changed(); -}; - - -/** - * @param {!UTFGridJSON} json UTFGrid data. - * @private - */ -ol.source.TileUTFGrid.Tile_.prototype.handleLoad_ = function(json) { - this.grid_ = json.grid; - this.keys_ = json.keys; - this.data_ = json.data; - - this.state = ol.TileState.EMPTY; - this.changed(); -}; - - -/** - * @private - */ -ol.source.TileUTFGrid.Tile_.prototype.loadInternal_ = function() { - if (this.state == ol.TileState.IDLE) { - this.state = ol.TileState.LOADING; - if (this.jsonp_) { - ol.net.jsonp(this.src_, this.handleLoad_.bind(this), - this.handleError_.bind(this)); - } else { - var client = new XMLHttpRequest(); - client.addEventListener('load', this.onXHRLoad_.bind(this)); - client.addEventListener('error', this.onXHRError_.bind(this)); - client.open('GET', this.src_); - client.send(); - } - } -}; - - -/** - * @private - * @param {Event} event The load event. - */ -ol.source.TileUTFGrid.Tile_.prototype.onXHRLoad_ = function(event) { - var client = /** @type {XMLHttpRequest} */ (event.target); - // status will be 0 for file:// urls - if (!client.status || client.status >= 200 && client.status < 300) { - var response; - try { - response = /** @type {!UTFGridJSON} */(JSON.parse(client.responseText)); - } catch (err) { - this.handleError_(); - return; - } - this.handleLoad_(response); - } else { - this.handleError_(); - } -}; - - -/** - * @private - * @param {Event} event The error event. - */ -ol.source.TileUTFGrid.Tile_.prototype.onXHRError_ = function(event) { - this.handleError_(); -}; - - -/** - * @override - */ -ol.source.TileUTFGrid.Tile_.prototype.load = function() { - if (this.preemptive_) { - this.loadInternal_(); - } -}; - -// FIXME add minZoom support -// FIXME add date line wrap (tile coord transform) -// FIXME cannot be shared between maps with different projections - -goog.provide('ol.source.TileWMS'); - -goog.require('ol'); -goog.require('ol.asserts'); -goog.require('ol.extent'); -goog.require('ol.obj'); -goog.require('ol.math'); -goog.require('ol.proj'); -goog.require('ol.size'); -goog.require('ol.source.TileImage'); -goog.require('ol.source.WMSServerType'); -goog.require('ol.tilecoord'); -goog.require('ol.string'); -goog.require('ol.uri'); - -/** - * @classdesc - * Layer source for tile data from WMS servers. - * - * @constructor - * @extends {ol.source.TileImage} - * @param {olx.source.TileWMSOptions=} opt_options Tile WMS options. - * @api - */ -ol.source.TileWMS = function(opt_options) { - - var options = opt_options || {}; - - var params = options.params || {}; - - var transparent = 'TRANSPARENT' in params ? params['TRANSPARENT'] : true; - - ol.source.TileImage.call(this, { - attributions: options.attributions, - cacheSize: options.cacheSize, - crossOrigin: options.crossOrigin, - logo: options.logo, - opaque: !transparent, - projection: options.projection, - reprojectionErrorThreshold: options.reprojectionErrorThreshold, - tileClass: options.tileClass, - tileGrid: options.tileGrid, - tileLoadFunction: options.tileLoadFunction, - url: options.url, - urls: options.urls, - wrapX: options.wrapX !== undefined ? options.wrapX : true, - transition: options.transition - }); - - /** - * @private - * @type {number} - */ - this.gutter_ = options.gutter !== undefined ? options.gutter : 0; - - /** - * @private - * @type {!Object} - */ - this.params_ = params; - - /** - * @private - * @type {boolean} - */ - this.v13_ = true; - - /** - * @private - * @type {ol.source.WMSServerType|undefined} - */ - this.serverType_ = /** @type {ol.source.WMSServerType|undefined} */ (options.serverType); - - /** - * @private - * @type {boolean} - */ - this.hidpi_ = options.hidpi !== undefined ? options.hidpi : true; - - /** - * @private - * @type {ol.Extent} - */ - this.tmpExtent_ = ol.extent.createEmpty(); - - this.updateV13_(); - this.setKey(this.getKeyForParams_()); - -}; -ol.inherits(ol.source.TileWMS, ol.source.TileImage); - - -/** - * Return the GetFeatureInfo URL for the passed coordinate, resolution, and - * projection. Return `undefined` if the GetFeatureInfo URL cannot be - * constructed. - * @param {ol.Coordinate} coordinate Coordinate. - * @param {number} resolution Resolution. - * @param {ol.ProjectionLike} projection Projection. - * @param {!Object} params GetFeatureInfo params. `INFO_FORMAT` at least should - * be provided. If `QUERY_LAYERS` is not provided then the layers specified - * in the `LAYERS` parameter will be used. `VERSION` should not be - * specified here. - * @return {string|undefined} GetFeatureInfo URL. - * @api - */ -ol.source.TileWMS.prototype.getGetFeatureInfoUrl = function(coordinate, resolution, projection, params) { - var projectionObj = ol.proj.get(projection); - - var tileGrid = this.getTileGrid(); - if (!tileGrid) { - tileGrid = this.getTileGridForProjection(projectionObj); - } - - var tileCoord = tileGrid.getTileCoordForCoordAndResolution( - coordinate, resolution); - - if (tileGrid.getResolutions().length <= tileCoord[0]) { - return undefined; - } - - var tileResolution = tileGrid.getResolution(tileCoord[0]); - var tileExtent = tileGrid.getTileCoordExtent(tileCoord, this.tmpExtent_); - var tileSize = ol.size.toSize( - tileGrid.getTileSize(tileCoord[0]), this.tmpSize); - - var gutter = this.gutter_; - if (gutter !== 0) { - tileSize = ol.size.buffer(tileSize, gutter, this.tmpSize); - tileExtent = ol.extent.buffer(tileExtent, - tileResolution * gutter, tileExtent); - } - - var baseParams = { - 'SERVICE': 'WMS', - 'VERSION': ol.DEFAULT_WMS_VERSION, - 'REQUEST': 'GetFeatureInfo', - 'FORMAT': 'image/png', - 'TRANSPARENT': true, - 'QUERY_LAYERS': this.params_['LAYERS'] - }; - ol.obj.assign(baseParams, this.params_, params); - - var x = Math.floor((coordinate[0] - tileExtent[0]) / tileResolution); - var y = Math.floor((tileExtent[3] - coordinate[1]) / tileResolution); - - baseParams[this.v13_ ? 'I' : 'X'] = x; - baseParams[this.v13_ ? 'J' : 'Y'] = y; - - return this.getRequestUrl_(tileCoord, tileSize, tileExtent, - 1, projectionObj, baseParams); -}; - - -/** - * @inheritDoc - */ -ol.source.TileWMS.prototype.getGutterInternal = function() { - return this.gutter_; -}; - - -/** - * Get the user-provided params, i.e. those passed to the constructor through - * the "params" option, and possibly updated using the updateParams method. - * @return {Object} Params. - * @api - */ -ol.source.TileWMS.prototype.getParams = function() { - return this.params_; -}; - - -/** - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {ol.Size} tileSize Tile size. - * @param {ol.Extent} tileExtent Tile extent. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.proj.Projection} projection Projection. - * @param {Object} params Params. - * @return {string|undefined} Request URL. - * @private - */ -ol.source.TileWMS.prototype.getRequestUrl_ = function(tileCoord, tileSize, tileExtent, - pixelRatio, projection, params) { - - var urls = this.urls; - if (!urls) { - return undefined; - } - - params['WIDTH'] = tileSize[0]; - params['HEIGHT'] = tileSize[1]; - - params[this.v13_ ? 'CRS' : 'SRS'] = projection.getCode(); - - if (!('STYLES' in this.params_)) { - params['STYLES'] = ''; - } - - if (pixelRatio != 1) { - switch (this.serverType_) { - case ol.source.WMSServerType.GEOSERVER: - var dpi = (90 * pixelRatio + 0.5) | 0; - if ('FORMAT_OPTIONS' in params) { - params['FORMAT_OPTIONS'] += ';dpi:' + dpi; - } else { - params['FORMAT_OPTIONS'] = 'dpi:' + dpi; - } - break; - case ol.source.WMSServerType.MAPSERVER: - params['MAP_RESOLUTION'] = 90 * pixelRatio; - break; - case ol.source.WMSServerType.CARMENTA_SERVER: - case ol.source.WMSServerType.QGIS: - params['DPI'] = 90 * pixelRatio; - break; - default: - ol.asserts.assert(false, 52); // Unknown `serverType` configured - break; - } - } - - var axisOrientation = projection.getAxisOrientation(); - var bbox = tileExtent; - if (this.v13_ && axisOrientation.substr(0, 2) == 'ne') { - var tmp; - tmp = tileExtent[0]; - bbox[0] = tileExtent[1]; - bbox[1] = tmp; - tmp = tileExtent[2]; - bbox[2] = tileExtent[3]; - bbox[3] = tmp; - } - params['BBOX'] = bbox.join(','); - - var url; - if (urls.length == 1) { - url = urls[0]; - } else { - var index = ol.math.modulo(ol.tilecoord.hash(tileCoord), urls.length); - url = urls[index]; - } - return ol.uri.appendParams(url, params); -}; - - -/** - * @inheritDoc - */ -ol.source.TileWMS.prototype.getTilePixelRatio = function(pixelRatio) { - return (!this.hidpi_ || this.serverType_ === undefined) ? 1 : - /** @type {number} */ (pixelRatio); -}; - - -/** - * @private - * @return {string} The key for the current params. - */ -ol.source.TileWMS.prototype.getKeyForParams_ = function() { - var i = 0; - var res = []; - for (var key in this.params_) { - res[i++] = key + '-' + this.params_[key]; - } - return res.join('/'); -}; - - -/** - * @inheritDoc - */ -ol.source.TileWMS.prototype.fixedTileUrlFunction = function(tileCoord, pixelRatio, projection) { - - var tileGrid = this.getTileGrid(); - if (!tileGrid) { - tileGrid = this.getTileGridForProjection(projection); - } - - if (tileGrid.getResolutions().length <= tileCoord[0]) { - return undefined; - } - - if (pixelRatio != 1 && (!this.hidpi_ || this.serverType_ === undefined)) { - pixelRatio = 1; - } - - var tileResolution = tileGrid.getResolution(tileCoord[0]); - var tileExtent = tileGrid.getTileCoordExtent(tileCoord, this.tmpExtent_); - var tileSize = ol.size.toSize( - tileGrid.getTileSize(tileCoord[0]), this.tmpSize); - - var gutter = this.gutter_; - if (gutter !== 0) { - tileSize = ol.size.buffer(tileSize, gutter, this.tmpSize); - tileExtent = ol.extent.buffer(tileExtent, - tileResolution * gutter, tileExtent); - } - - if (pixelRatio != 1) { - tileSize = ol.size.scale(tileSize, pixelRatio, this.tmpSize); - } - - var baseParams = { - 'SERVICE': 'WMS', - 'VERSION': ol.DEFAULT_WMS_VERSION, - 'REQUEST': 'GetMap', - 'FORMAT': 'image/png', - 'TRANSPARENT': true - }; - ol.obj.assign(baseParams, this.params_); - - return this.getRequestUrl_(tileCoord, tileSize, tileExtent, - pixelRatio, projection, baseParams); -}; - -/** - * Update the user-provided params. - * @param {Object} params Params. - * @api - */ -ol.source.TileWMS.prototype.updateParams = function(params) { - ol.obj.assign(this.params_, params); - this.updateV13_(); - this.setKey(this.getKeyForParams_()); -}; - - -/** - * @private - */ -ol.source.TileWMS.prototype.updateV13_ = function() { - var version = this.params_['VERSION'] || ol.DEFAULT_WMS_VERSION; - this.v13_ = ol.string.compareVersions(version, '1.3') >= 0; -}; - -goog.provide('ol.VectorImageTile'); - -goog.require('ol'); -goog.require('ol.Tile'); -goog.require('ol.TileState'); -goog.require('ol.dom'); -goog.require('ol.events'); -goog.require('ol.extent'); -goog.require('ol.events.EventType'); -goog.require('ol.featureloader'); - - -/** - * @constructor - * @extends {ol.Tile} - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {ol.TileState} state State. - * @param {string} src Data source url. - * @param {ol.format.Feature} format Feature format. - * @param {ol.TileLoadFunctionType} tileLoadFunction Tile load function. - * @param {ol.TileCoord} urlTileCoord Wrapped tile coordinate for source urls. - * @param {ol.TileUrlFunctionType} tileUrlFunction Tile url function. - * @param {ol.tilegrid.TileGrid} sourceTileGrid Tile grid of the source. - * @param {ol.tilegrid.TileGrid} tileGrid Tile grid of the renderer. - * @param {Object.<string,ol.VectorTile>} sourceTiles Source tiles. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.proj.Projection} projection Projection. - * @param {function(new: ol.VectorTile, ol.TileCoord, ol.TileState, string, - * ol.format.Feature, ol.TileLoadFunctionType)} tileClass Class to - * instantiate for source tiles. - * @param {function(this: ol.source.VectorTile, ol.events.Event)} handleTileChange - * Function to call when a source tile's state changes. - * @param {olx.TileOptions=} opt_options Tile options. - */ -ol.VectorImageTile = function(tileCoord, state, src, format, tileLoadFunction, - urlTileCoord, tileUrlFunction, sourceTileGrid, tileGrid, sourceTiles, - pixelRatio, projection, tileClass, handleTileChange, opt_options) { - - ol.Tile.call(this, tileCoord, state, opt_options); - - /** - * @private - * @type {Object.<string, CanvasRenderingContext2D>} - */ - this.context_ = {}; - - /** - * @private - * @type {ol.FeatureLoader} - */ - this.loader_; - - /** - * @private - * @type {Object.<string, ol.TileReplayState>} - */ - this.replayState_ = {}; - - /** - * @private - * @type {Object.<string,ol.VectorTile>} - */ - this.sourceTiles_ = sourceTiles; - - /** - * Keys of source tiles used by this tile. Use with {@link #getTile}. - * @type {Array.<string>} - */ - this.tileKeys = []; - - /** - * @type {string} - */ - this.src_ = src; - - /** - * @type {ol.TileCoord} - */ - this.wrappedTileCoord = urlTileCoord; - - /** - * @type {Array.<ol.EventsKey>} - */ - this.loadListenerKeys_ = []; - - /** - * @type {Array.<ol.EventsKey>} - */ - this.sourceTileListenerKeys_ = []; - - if (urlTileCoord) { - var extent = tileGrid.getTileCoordExtent(urlTileCoord); - var resolution = tileGrid.getResolution(tileCoord[0]); - var sourceZ = sourceTileGrid.getZForResolution(resolution); - sourceTileGrid.forEachTileCoord(extent, sourceZ, function(sourceTileCoord) { - var sharedExtent = ol.extent.getIntersection(extent, - sourceTileGrid.getTileCoordExtent(sourceTileCoord)); - var sourceExtent = sourceTileGrid.getExtent(); - if (sourceExtent) { - sharedExtent = ol.extent.getIntersection(sharedExtent, sourceExtent); - } - if (ol.extent.getWidth(sharedExtent) / resolution >= 0.5 && - ol.extent.getHeight(sharedExtent) / resolution >= 0.5) { - // only include source tile if overlap is at least 1 pixel - var sourceTileKey = sourceTileCoord.toString(); - var sourceTile = sourceTiles[sourceTileKey]; - if (!sourceTile) { - var tileUrl = tileUrlFunction(sourceTileCoord, pixelRatio, projection); - sourceTile = sourceTiles[sourceTileKey] = new tileClass(sourceTileCoord, - tileUrl == undefined ? ol.TileState.EMPTY : ol.TileState.IDLE, - tileUrl == undefined ? '' : tileUrl, - format, tileLoadFunction); - this.sourceTileListenerKeys_.push( - ol.events.listen(sourceTile, ol.events.EventType.CHANGE, handleTileChange)); - } - sourceTile.consumers++; - this.tileKeys.push(sourceTileKey); - } - }.bind(this)); - } - -}; -ol.inherits(ol.VectorImageTile, ol.Tile); - - -/** - * @inheritDoc - */ -ol.VectorImageTile.prototype.disposeInternal = function() { - for (var i = 0, ii = this.tileKeys.length; i < ii; ++i) { - var sourceTileKey = this.tileKeys[i]; - var sourceTile = this.getTile(sourceTileKey); - sourceTile.consumers--; - if (sourceTile.consumers == 0) { - delete this.sourceTiles_[sourceTileKey]; - sourceTile.dispose(); - } - } - this.tileKeys.length = 0; - this.sourceTiles_ = null; - this.loadListenerKeys_.forEach(ol.events.unlistenByKey); - this.loadListenerKeys_.length = 0; - if (this.interimTile) { - this.interimTile.dispose(); - } - this.state = ol.TileState.ABORT; - this.changed(); - this.sourceTileListenerKeys_.forEach(ol.events.unlistenByKey); - this.sourceTileListenerKeys_.length = 0; - ol.Tile.prototype.disposeInternal.call(this); -}; - - -/** - * @param {ol.layer.Layer} layer Layer. - * @return {CanvasRenderingContext2D} The rendering context. - */ -ol.VectorImageTile.prototype.getContext = function(layer) { - var key = ol.getUid(layer).toString(); - if (!(key in this.context_)) { - this.context_[key] = ol.dom.createCanvasContext2D(); - } - return this.context_[key]; -}; - - -/** - * Get the Canvas for this tile. - * @param {ol.layer.Layer} layer Layer. - * @return {HTMLCanvasElement} Canvas. - */ -ol.VectorImageTile.prototype.getImage = function(layer) { - return this.getReplayState(layer).renderedTileRevision == -1 ? - null : this.getContext(layer).canvas; -}; - - -/** - * @param {ol.layer.Layer} layer Layer. - * @return {ol.TileReplayState} The replay state. - */ -ol.VectorImageTile.prototype.getReplayState = function(layer) { - var key = ol.getUid(layer).toString(); - if (!(key in this.replayState_)) { - this.replayState_[key] = { - dirty: false, - renderedRenderOrder: null, - renderedRevision: -1, - renderedTileRevision: -1 - }; - } - return this.replayState_[key]; -}; - - -/** - * @inheritDoc - */ -ol.VectorImageTile.prototype.getKey = function() { - return this.tileKeys.join('/') + '/' + this.src_; -}; - - -/** - * @param {string} tileKey Key (tileCoord) of the source tile. - * @return {ol.VectorTile} Source tile. - */ -ol.VectorImageTile.prototype.getTile = function(tileKey) { - return this.sourceTiles_[tileKey]; -}; - - -/** - * @inheritDoc - */ -ol.VectorImageTile.prototype.load = function() { - // Source tiles with LOADED state - we just count them because once they are - // loaded, we're no longer listening to state changes. - var leftToLoad = 0; - // Source tiles with ERROR state - we track them because they can still have - // an ERROR state after another load attempt. - var errorSourceTiles = {}; - - if (this.state == ol.TileState.IDLE) { - this.setState(ol.TileState.LOADING); - } - if (this.state == ol.TileState.LOADING) { - this.tileKeys.forEach(function(sourceTileKey) { - var sourceTile = this.getTile(sourceTileKey); - if (sourceTile.state == ol.TileState.IDLE) { - sourceTile.setLoader(this.loader_); - sourceTile.load(); - } - if (sourceTile.state == ol.TileState.LOADING) { - var key = ol.events.listen(sourceTile, ol.events.EventType.CHANGE, function(e) { - var state = sourceTile.getState(); - if (state == ol.TileState.LOADED || - state == ol.TileState.ERROR) { - var uid = ol.getUid(sourceTile); - if (state == ol.TileState.ERROR) { - errorSourceTiles[uid] = true; - } else { - --leftToLoad; - delete errorSourceTiles[uid]; - } - if (leftToLoad - Object.keys(errorSourceTiles).length == 0) { - this.finishLoading_(); - } - } - }.bind(this)); - this.loadListenerKeys_.push(key); - ++leftToLoad; - } - }.bind(this)); - } - if (leftToLoad - Object.keys(errorSourceTiles).length == 0) { - setTimeout(this.finishLoading_.bind(this), 0); - } -}; - - -/** - * @private - */ -ol.VectorImageTile.prototype.finishLoading_ = function() { - var loaded = this.tileKeys.length; - var empty = 0; - for (var i = loaded - 1; i >= 0; --i) { - var state = this.getTile(this.tileKeys[i]).getState(); - if (state != ol.TileState.LOADED) { - --loaded; - } - if (state == ol.TileState.EMPTY) { - ++empty; - } - } - if (loaded == this.tileKeys.length) { - this.loadListenerKeys_.forEach(ol.events.unlistenByKey); - this.loadListenerKeys_.length = 0; - this.setState(ol.TileState.LOADED); - } else { - this.setState(empty == this.tileKeys.length ? ol.TileState.EMPTY : ol.TileState.ERROR); - } -}; - - -/** - * Sets the loader for a tile. - * @param {ol.VectorTile} tile Vector tile. - * @param {string} url URL. - */ -ol.VectorImageTile.defaultLoadFunction = function(tile, url) { - var loader = ol.featureloader.loadFeaturesXhr( - url, tile.getFormat(), tile.onLoad.bind(tile), tile.onError.bind(tile)); - - tile.setLoader(loader); -}; - -goog.provide('ol.VectorTile'); - -goog.require('ol'); -goog.require('ol.Tile'); -goog.require('ol.TileState'); - - -/** - * @constructor - * @extends {ol.Tile} - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {ol.TileState} state State. - * @param {string} src Data source url. - * @param {ol.format.Feature} format Feature format. - * @param {ol.TileLoadFunctionType} tileLoadFunction Tile load function. - * @param {olx.TileOptions=} opt_options Tile options. - */ -ol.VectorTile = function(tileCoord, state, src, format, tileLoadFunction, opt_options) { - - ol.Tile.call(this, tileCoord, state, opt_options); - - /** - * @type {number} - */ - this.consumers = 0; - - /** - * @private - * @type {ol.Extent} - */ - this.extent_ = null; - - /** - * @private - * @type {ol.format.Feature} - */ - this.format_ = format; - - /** - * @private - * @type {Array.<ol.Feature>} - */ - this.features_ = null; - - /** - * @private - * @type {ol.FeatureLoader} - */ - this.loader_; - - /** - * Data projection - * @private - * @type {ol.proj.Projection} - */ - this.projection_; - - /** - * @private - * @type {Object.<string, ol.render.ReplayGroup>} - */ - this.replayGroups_ = {}; - - /** - * @private - * @type {ol.TileLoadFunctionType} - */ - this.tileLoadFunction_ = tileLoadFunction; - - /** - * @private - * @type {string} - */ - this.url_ = src; - -}; -ol.inherits(ol.VectorTile, ol.Tile); - - -/** - * @inheritDoc - */ -ol.VectorTile.prototype.disposeInternal = function() { - this.features_ = null; - this.replayGroups_ = {}; - this.state = ol.TileState.ABORT; - this.changed(); - ol.Tile.prototype.disposeInternal.call(this); -}; - - -/** - * Gets the extent of the vector tile. - * @return {ol.Extent} The extent. - */ -ol.VectorTile.prototype.getExtent = function() { - return this.extent_ || ol.VectorTile.DEFAULT_EXTENT; -}; - - -/** - * Get the feature format assigned for reading this tile's features. - * @return {ol.format.Feature} Feature format. - * @api - */ -ol.VectorTile.prototype.getFormat = function() { - return this.format_; -}; - - -/** - * Get the features for this tile. Geometries will be in the projection returned - * by {@link ol.VectorTile#getProjection}. - * @return {Array.<ol.Feature|ol.render.Feature>} Features. - * @api - */ -ol.VectorTile.prototype.getFeatures = function() { - return this.features_; -}; - - -/** - * @inheritDoc - */ -ol.VectorTile.prototype.getKey = function() { - return this.url_; -}; - - -/** - * Get the feature projection of features returned by - * {@link ol.VectorTile#getFeatures}. - * @return {ol.proj.Projection} Feature projection. - * @api - */ -ol.VectorTile.prototype.getProjection = function() { - return this.projection_; -}; - - -/** - * @param {ol.layer.Layer} layer Layer. - * @param {string} key Key. - * @return {ol.render.ReplayGroup} Replay group. - */ -ol.VectorTile.prototype.getReplayGroup = function(layer, key) { - return this.replayGroups_[ol.getUid(layer) + ',' + key]; -}; - - -/** - * @inheritDoc - */ -ol.VectorTile.prototype.load = function() { - if (this.state == ol.TileState.IDLE) { - this.setState(ol.TileState.LOADING); - this.tileLoadFunction_(this, this.url_); - this.loader_(null, NaN, null); - } -}; - - -/** - * Handler for successful tile load. - * @param {Array.<ol.Feature>} features The loaded features. - * @param {ol.proj.Projection} dataProjection Data projection. - * @param {ol.Extent} extent Extent. - */ -ol.VectorTile.prototype.onLoad = function(features, dataProjection, extent) { - this.setProjection(dataProjection); - this.setFeatures(features); - this.setExtent(extent); -}; - - -/** - * Handler for tile load errors. - */ -ol.VectorTile.prototype.onError = function() { - this.setState(ol.TileState.ERROR); -}; - - -/** - * Function for use in an {@link ol.source.VectorTile}'s `tileLoadFunction`. - * Sets the extent of the vector tile. This is only required for tiles in - * projections with `tile-pixels` as units. The extent should be set to - * `[0, 0, tilePixelSize, tilePixelSize]`, where `tilePixelSize` is calculated - * by multiplying the tile size with the tile pixel ratio. For sources using - * {@link ol.format.MVT} as feature format, the - * {@link ol.format.MVT#getLastExtent} method will return the correct extent. - * The default is `[0, 0, 4096, 4096]`. - * @param {ol.Extent} extent The extent. - * @api - */ -ol.VectorTile.prototype.setExtent = function(extent) { - this.extent_ = extent; -}; - - -/** - * Function for use in an {@link ol.source.VectorTile}'s `tileLoadFunction`. - * Sets the features for the tile. - * @param {Array.<ol.Feature>} features Features. - * @api - */ -ol.VectorTile.prototype.setFeatures = function(features) { - this.features_ = features; - this.setState(ol.TileState.LOADED); -}; - - -/** - * Function for use in an {@link ol.source.VectorTile}'s `tileLoadFunction`. - * Sets the projection of the features that were added with - * {@link ol.VectorTile#setFeatures}. - * @param {ol.proj.Projection} projection Feature projection. - * @api - */ -ol.VectorTile.prototype.setProjection = function(projection) { - this.projection_ = projection; -}; - - -/** - * @param {ol.layer.Layer} layer Layer. - * @param {string} key Key. - * @param {ol.render.ReplayGroup} replayGroup Replay group. - */ -ol.VectorTile.prototype.setReplayGroup = function(layer, key, replayGroup) { - this.replayGroups_[ol.getUid(layer) + ',' + key] = replayGroup; -}; - - -/** - * Set the feature loader for reading this tile's features. - * @param {ol.FeatureLoader} loader Feature loader. - * @api - */ -ol.VectorTile.prototype.setLoader = function(loader) { - this.loader_ = loader; -}; - - -/** - * @const - * @type {ol.Extent} - */ -ol.VectorTile.DEFAULT_EXTENT = [0, 0, 4096, 4096]; - -goog.provide('ol.source.VectorTile'); - -goog.require('ol'); -goog.require('ol.TileState'); -goog.require('ol.VectorImageTile'); -goog.require('ol.VectorTile'); -goog.require('ol.size'); -goog.require('ol.source.UrlTile'); -goog.require('ol.tilecoord'); -goog.require('ol.tilegrid'); - - -/** - * @classdesc - * Class for layer sources providing vector data divided into a tile grid, to be - * used with {@link ol.layer.VectorTile}. Although this source receives tiles - * with vector features from the server, it is not meant for feature editing. - * Features are optimized for rendering, their geometries are clipped at or near - * tile boundaries and simplified for a view resolution. See - * {@link ol.source.Vector} for vector sources that are suitable for feature - * editing. - * - * @constructor - * @fires ol.source.Tile.Event - * @extends {ol.source.UrlTile} - * @param {olx.source.VectorTileOptions} options Vector tile options. - * @api - */ -ol.source.VectorTile = function(options) { - var projection = options.projection || 'EPSG:3857'; - - var extent = options.extent || ol.tilegrid.extentFromProjection(projection); - - var tileGrid = options.tileGrid || ol.tilegrid.createXYZ({ - extent: extent, - maxZoom: options.maxZoom || 22, - minZoom: options.minZoom, - tileSize: options.tileSize || 512 - }); - - ol.source.UrlTile.call(this, { - attributions: options.attributions, - cacheSize: options.cacheSize !== undefined ? options.cacheSize : 128, - extent: extent, - logo: options.logo, - opaque: false, - projection: projection, - state: options.state, - tileGrid: tileGrid, - tileLoadFunction: options.tileLoadFunction ? - options.tileLoadFunction : ol.VectorImageTile.defaultLoadFunction, - tileUrlFunction: options.tileUrlFunction, - url: options.url, - urls: options.urls, - wrapX: options.wrapX === undefined ? true : options.wrapX, - transition: options.transition - }); - - /** - * @private - * @type {ol.format.Feature} - */ - this.format_ = options.format ? options.format : null; - - /** - * @private - * @type {Object.<string,ol.VectorTile>} - */ - this.sourceTiles_ = {}; - - /** - * @private - * @type {boolean} - */ - this.overlaps_ = options.overlaps == undefined ? true : options.overlaps; - - /** - * @protected - * @type {function(new: ol.VectorTile, ol.TileCoord, ol.TileState, string, - * ol.format.Feature, ol.TileLoadFunctionType)} - */ - this.tileClass = options.tileClass ? options.tileClass : ol.VectorTile; - - /** - * @private - * @type {Object.<string,ol.tilegrid.TileGrid>} - */ - this.tileGrids_ = {}; - -}; -ol.inherits(ol.source.VectorTile, ol.source.UrlTile); - - -/** - * @return {boolean} The source can have overlapping geometries. - */ -ol.source.VectorTile.prototype.getOverlaps = function() { - return this.overlaps_; -}; - -/** - * clear {@link ol.TileCache} and delete all source tiles - * @api - */ -ol.source.VectorTile.prototype.clear = function() { - this.tileCache.clear(); - this.sourceTiles_ = {}; -}; - -/** - * @inheritDoc - */ -ol.source.VectorTile.prototype.getTile = function(z, x, y, pixelRatio, projection) { - var tileCoordKey = ol.tilecoord.getKeyZXY(z, x, y); - if (this.tileCache.containsKey(tileCoordKey)) { - return /** @type {!ol.Tile} */ (this.tileCache.get(tileCoordKey)); - } else { - var tileCoord = [z, x, y]; - var urlTileCoord = this.getTileCoordForTileUrlFunction( - tileCoord, projection); - var tileUrl = urlTileCoord ? - this.tileUrlFunction(urlTileCoord, pixelRatio, projection) : undefined; - var tile = new ol.VectorImageTile( - tileCoord, - tileUrl !== undefined ? ol.TileState.IDLE : ol.TileState.EMPTY, - tileUrl !== undefined ? tileUrl : '', - this.format_, this.tileLoadFunction, urlTileCoord, this.tileUrlFunction, - this.tileGrid, this.getTileGridForProjection(projection), - this.sourceTiles_, pixelRatio, projection, this.tileClass, - this.handleTileChange.bind(this), - this.tileOptions); - - this.tileCache.set(tileCoordKey, tile); - return tile; - } -}; - - -/** - * @inheritDoc - */ -ol.source.VectorTile.prototype.getTileGridForProjection = function(projection) { - var code = projection.getCode(); - var tileGrid = this.tileGrids_[code]; - if (!tileGrid) { - // A tile grid that matches the tile size of the source tile grid is more - // likely to have 1:1 relationships between source tiles and rendered tiles. - var sourceTileGrid = this.tileGrid; - tileGrid = this.tileGrids_[code] = ol.tilegrid.createForProjection(projection, undefined, - sourceTileGrid ? sourceTileGrid.getTileSize(sourceTileGrid.getMinZoom()) : undefined); - } - return tileGrid; -}; - - -/** - * @inheritDoc - */ -ol.source.VectorTile.prototype.getTilePixelRatio = function(pixelRatio) { - return pixelRatio; -}; - - -/** - * @inheritDoc - */ -ol.source.VectorTile.prototype.getTilePixelSize = function(z, pixelRatio, projection) { - var tileSize = ol.size.toSize(this.getTileGridForProjection(projection).getTileSize(z)); - return [Math.round(tileSize[0] * pixelRatio), Math.round(tileSize[1] * pixelRatio)]; -}; - -goog.provide('ol.source.WMTSRequestEncoding'); - -/** - * Request encoding. One of 'KVP', 'REST'. - * @enum {string} - */ -ol.source.WMTSRequestEncoding = { - KVP: 'KVP', // see spec §8 - REST: 'REST' // see spec §10 -}; - -goog.provide('ol.tilegrid.WMTS'); - -goog.require('ol'); -goog.require('ol.array'); -goog.require('ol.proj'); -goog.require('ol.tilegrid.TileGrid'); - - -/** - * @classdesc - * Set the grid pattern for sources accessing WMTS tiled-image servers. - * - * @constructor - * @extends {ol.tilegrid.TileGrid} - * @param {olx.tilegrid.WMTSOptions} options WMTS options. - * @struct - * @api - */ -ol.tilegrid.WMTS = function(options) { - /** - * @private - * @type {!Array.<string>} - */ - this.matrixIds_ = options.matrixIds; - // FIXME: should the matrixIds become optional? - - ol.tilegrid.TileGrid.call(this, { - extent: options.extent, - origin: options.origin, - origins: options.origins, - resolutions: options.resolutions, - tileSize: options.tileSize, - tileSizes: options.tileSizes, - sizes: options.sizes - }); -}; -ol.inherits(ol.tilegrid.WMTS, ol.tilegrid.TileGrid); - - -/** - * @param {number} z Z. - * @return {string} MatrixId.. - */ -ol.tilegrid.WMTS.prototype.getMatrixId = function(z) { - return this.matrixIds_[z]; -}; - - -/** - * Get the list of matrix identifiers. - * @return {Array.<string>} MatrixIds. - * @api - */ -ol.tilegrid.WMTS.prototype.getMatrixIds = function() { - return this.matrixIds_; -}; - - -/** - * Create a tile grid from a WMTS capabilities matrix set and an - * optional TileMatrixSetLimits. - * @param {Object} matrixSet An object representing a matrixSet in the - * capabilities document. - * @param {ol.Extent=} opt_extent An optional extent to restrict the tile - * ranges the server provides. - * @param {Array.<Object>=} opt_matrixLimits An optional object representing - * the available matrices for tileGrid. - * @return {ol.tilegrid.WMTS} WMTS tileGrid instance. - * @api - */ -ol.tilegrid.WMTS.createFromCapabilitiesMatrixSet = function(matrixSet, opt_extent, - opt_matrixLimits) { - - /** @type {!Array.<number>} */ - var resolutions = []; - /** @type {!Array.<string>} */ - var matrixIds = []; - /** @type {!Array.<ol.Coordinate>} */ - var origins = []; - /** @type {!Array.<ol.Size>} */ - var tileSizes = []; - /** @type {!Array.<ol.Size>} */ - var sizes = []; - - var matrixLimits = opt_matrixLimits !== undefined ? opt_matrixLimits : []; - - var supportedCRSPropName = 'SupportedCRS'; - var matrixIdsPropName = 'TileMatrix'; - var identifierPropName = 'Identifier'; - var scaleDenominatorPropName = 'ScaleDenominator'; - var topLeftCornerPropName = 'TopLeftCorner'; - var tileWidthPropName = 'TileWidth'; - var tileHeightPropName = 'TileHeight'; - - var projection; - projection = ol.proj.get(matrixSet[supportedCRSPropName].replace( - /urn:ogc:def:crs:(\w+):(.*:)?(\w+)$/, '$1:$3')); - var metersPerUnit = projection.getMetersPerUnit(); - // swap origin x and y coordinates if axis orientation is lat/long - var switchOriginXY = projection.getAxisOrientation().substr(0, 2) == 'ne'; - - matrixSet[matrixIdsPropName].sort(function(a, b) { - return b[scaleDenominatorPropName] - a[scaleDenominatorPropName]; - }); - - matrixSet[matrixIdsPropName].forEach(function(elt, index, array) { - - var matrixAvailable; - // use of matrixLimits to filter TileMatrices from GetCapabilities - // TileMatrixSet from unavailable matrix levels. - if (matrixLimits.length > 0) { - matrixAvailable = ol.array.find(matrixLimits, - function(elt_ml, index_ml, array_ml) { - return elt[identifierPropName] == elt_ml[matrixIdsPropName]; - }); - } else { - matrixAvailable = true; - } - - if (matrixAvailable) { - matrixIds.push(elt[identifierPropName]); - var resolution = elt[scaleDenominatorPropName] * 0.28E-3 / metersPerUnit; - var tileWidth = elt[tileWidthPropName]; - var tileHeight = elt[tileHeightPropName]; - if (switchOriginXY) { - origins.push([elt[topLeftCornerPropName][1], - elt[topLeftCornerPropName][0]]); - } else { - origins.push(elt[topLeftCornerPropName]); - } - resolutions.push(resolution); - tileSizes.push(tileWidth == tileHeight ? - tileWidth : [tileWidth, tileHeight]); - // top-left origin, so height is negative - sizes.push([elt['MatrixWidth'], -elt['MatrixHeight']]); - } - }); - - return new ol.tilegrid.WMTS({ - extent: opt_extent, - origins: origins, - resolutions: resolutions, - matrixIds: matrixIds, - tileSizes: tileSizes, - sizes: sizes - }); -}; - -goog.provide('ol.source.WMTS'); - -goog.require('ol'); -goog.require('ol.TileUrlFunction'); -goog.require('ol.array'); -goog.require('ol.extent'); -goog.require('ol.obj'); -goog.require('ol.proj'); -goog.require('ol.source.TileImage'); -goog.require('ol.source.WMTSRequestEncoding'); -goog.require('ol.tilegrid.WMTS'); -goog.require('ol.uri'); - - -/** - * @classdesc - * Layer source for tile data from WMTS servers. - * - * @constructor - * @extends {ol.source.TileImage} - * @param {olx.source.WMTSOptions} options WMTS options. - * @api - */ -ol.source.WMTS = function(options) { - - // TODO: add support for TileMatrixLimits - - /** - * @private - * @type {string} - */ - this.version_ = options.version !== undefined ? options.version : '1.0.0'; - - /** - * @private - * @type {string} - */ - this.format_ = options.format !== undefined ? options.format : 'image/jpeg'; - - /** - * @private - * @type {!Object} - */ - this.dimensions_ = options.dimensions !== undefined ? options.dimensions : {}; - - /** - * @private - * @type {string} - */ - this.layer_ = options.layer; - - /** - * @private - * @type {string} - */ - this.matrixSet_ = options.matrixSet; - - /** - * @private - * @type {string} - */ - this.style_ = options.style; - - var urls = options.urls; - if (urls === undefined && options.url !== undefined) { - urls = ol.TileUrlFunction.expandUrl(options.url); - } - - // FIXME: should we guess this requestEncoding from options.url(s) - // structure? that would mean KVP only if a template is not provided. - - /** - * @private - * @type {ol.source.WMTSRequestEncoding} - */ - this.requestEncoding_ = options.requestEncoding !== undefined ? - /** @type {ol.source.WMTSRequestEncoding} */ (options.requestEncoding) : - ol.source.WMTSRequestEncoding.KVP; - - var requestEncoding = this.requestEncoding_; - - // FIXME: should we create a default tileGrid? - // we could issue a getCapabilities xhr to retrieve missing configuration - var tileGrid = options.tileGrid; - - // context property names are lower case to allow for a case insensitive - // replacement as some services use different naming conventions - var context = { - 'layer': this.layer_, - 'style': this.style_, - 'tilematrixset': this.matrixSet_ - }; - - if (requestEncoding == ol.source.WMTSRequestEncoding.KVP) { - ol.obj.assign(context, { - 'Service': 'WMTS', - 'Request': 'GetTile', - 'Version': this.version_, - 'Format': this.format_ - }); - } - - var dimensions = this.dimensions_; - - /** - * @param {string} template Template. - * @return {ol.TileUrlFunctionType} Tile URL function. - */ - function createFromWMTSTemplate(template) { - - // TODO: we may want to create our own appendParams function so that params - // order conforms to wmts spec guidance, and so that we can avoid to escape - // special template params - - template = (requestEncoding == ol.source.WMTSRequestEncoding.KVP) ? - ol.uri.appendParams(template, context) : - template.replace(/\{(\w+?)\}/g, function(m, p) { - return (p.toLowerCase() in context) ? context[p.toLowerCase()] : m; - }); - - return ( - /** - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.proj.Projection} projection Projection. - * @return {string|undefined} Tile URL. - */ - function(tileCoord, pixelRatio, projection) { - if (!tileCoord) { - return undefined; - } else { - var localContext = { - 'TileMatrix': tileGrid.getMatrixId(tileCoord[0]), - 'TileCol': tileCoord[1], - 'TileRow': -tileCoord[2] - 1 - }; - ol.obj.assign(localContext, dimensions); - var url = template; - if (requestEncoding == ol.source.WMTSRequestEncoding.KVP) { - url = ol.uri.appendParams(url, localContext); - } else { - url = url.replace(/\{(\w+?)\}/g, function(m, p) { - return localContext[p]; - }); - } - return url; - } - }); - } - - var tileUrlFunction = (urls && urls.length > 0) ? - ol.TileUrlFunction.createFromTileUrlFunctions( - urls.map(createFromWMTSTemplate)) : - ol.TileUrlFunction.nullTileUrlFunction; - - ol.source.TileImage.call(this, { - attributions: options.attributions, - cacheSize: options.cacheSize, - crossOrigin: options.crossOrigin, - logo: options.logo, - projection: options.projection, - reprojectionErrorThreshold: options.reprojectionErrorThreshold, - tileClass: options.tileClass, - tileGrid: tileGrid, - tileLoadFunction: options.tileLoadFunction, - tilePixelRatio: options.tilePixelRatio, - tileUrlFunction: tileUrlFunction, - urls: urls, - wrapX: options.wrapX !== undefined ? options.wrapX : false, - transition: options.transition - }); - - this.setKey(this.getKeyForDimensions_()); - -}; -ol.inherits(ol.source.WMTS, ol.source.TileImage); - - -/** - * Get the dimensions, i.e. those passed to the constructor through the - * "dimensions" option, and possibly updated using the updateDimensions - * method. - * @return {!Object} Dimensions. - * @api - */ -ol.source.WMTS.prototype.getDimensions = function() { - return this.dimensions_; -}; - - -/** - * Return the image format of the WMTS source. - * @return {string} Format. - * @api - */ -ol.source.WMTS.prototype.getFormat = function() { - return this.format_; -}; - - -/** - * Return the layer of the WMTS source. - * @return {string} Layer. - * @api - */ -ol.source.WMTS.prototype.getLayer = function() { - return this.layer_; -}; - - -/** - * Return the matrix set of the WMTS source. - * @return {string} MatrixSet. - * @api - */ -ol.source.WMTS.prototype.getMatrixSet = function() { - return this.matrixSet_; -}; - - -/** - * Return the request encoding, either "KVP" or "REST". - * @return {ol.source.WMTSRequestEncoding} Request encoding. - * @api - */ -ol.source.WMTS.prototype.getRequestEncoding = function() { - return this.requestEncoding_; -}; - - -/** - * Return the style of the WMTS source. - * @return {string} Style. - * @api - */ -ol.source.WMTS.prototype.getStyle = function() { - return this.style_; -}; - - -/** - * Return the version of the WMTS source. - * @return {string} Version. - * @api - */ -ol.source.WMTS.prototype.getVersion = function() { - return this.version_; -}; - - -/** - * @private - * @return {string} The key for the current dimensions. - */ -ol.source.WMTS.prototype.getKeyForDimensions_ = function() { - var i = 0; - var res = []; - for (var key in this.dimensions_) { - res[i++] = key + '-' + this.dimensions_[key]; - } - return res.join('/'); -}; - - -/** - * Update the dimensions. - * @param {Object} dimensions Dimensions. - * @api - */ -ol.source.WMTS.prototype.updateDimensions = function(dimensions) { - ol.obj.assign(this.dimensions_, dimensions); - this.setKey(this.getKeyForDimensions_()); -}; - - -/** - * Generate source options from a capabilities object. - * @param {Object} wmtsCap An object representing the capabilities document. - * @param {Object} config Configuration properties for the layer. Defaults for - * the layer will apply if not provided. - * - * Required config properties: - * - layer - {string} The layer identifier. - * - * Optional config properties: - * - matrixSet - {string} The matrix set identifier, required if there is - * more than one matrix set in the layer capabilities. - * - projection - {string} The desired CRS when no matrixSet is specified. - * eg: "EPSG:3857". If the desired projection is not available, - * an error is thrown. - * - requestEncoding - {string} url encoding format for the layer. Default is - * the first tile url format found in the GetCapabilities response. - * - style - {string} The name of the style - * - format - {string} Image format for the layer. Default is the first - * format returned in the GetCapabilities response. - * - crossOrigin - {string|null|undefined} Cross origin. Default is `undefined`. - * @return {?olx.source.WMTSOptions} WMTS source options object or `null` if the layer was not found. - * @api - */ -ol.source.WMTS.optionsFromCapabilities = function(wmtsCap, config) { - var layers = wmtsCap['Contents']['Layer']; - var l = ol.array.find(layers, function(elt, index, array) { - return elt['Identifier'] == config['layer']; - }); - if (l === null) { - return null; - } - var tileMatrixSets = wmtsCap['Contents']['TileMatrixSet']; - var idx, matrixSet, matrixLimits; - if (l['TileMatrixSetLink'].length > 1) { - if ('projection' in config) { - idx = ol.array.findIndex(l['TileMatrixSetLink'], - function(elt, index, array) { - var tileMatrixSet = ol.array.find(tileMatrixSets, function(el) { - return el['Identifier'] == elt['TileMatrixSet']; - }); - var supportedCRS = tileMatrixSet['SupportedCRS'].replace(/urn:ogc:def:crs:(\w+):(.*:)?(\w+)$/, '$1:$3'); - var proj1 = ol.proj.get(supportedCRS); - var proj2 = ol.proj.get(config['projection']); - if (proj1 && proj2) { - return ol.proj.equivalent(proj1, proj2); - } else { - return supportedCRS == config['projection']; - } - }); - } else { - idx = ol.array.findIndex(l['TileMatrixSetLink'], - function(elt, index, array) { - return elt['TileMatrixSet'] == config['matrixSet']; - }); - } - } else { - idx = 0; - } - if (idx < 0) { - idx = 0; - } - matrixSet = /** @type {string} */ - (l['TileMatrixSetLink'][idx]['TileMatrixSet']); - matrixLimits = /** @type {Array.<Object>} */ - (l['TileMatrixSetLink'][idx]['TileMatrixSetLimits']); - - var format = /** @type {string} */ (l['Format'][0]); - if ('format' in config) { - format = config['format']; - } - idx = ol.array.findIndex(l['Style'], function(elt, index, array) { - if ('style' in config) { - return elt['Title'] == config['style']; - } else { - return elt['isDefault']; - } - }); - if (idx < 0) { - idx = 0; - } - var style = /** @type {string} */ (l['Style'][idx]['Identifier']); - - var dimensions = {}; - if ('Dimension' in l) { - l['Dimension'].forEach(function(elt, index, array) { - var key = elt['Identifier']; - var value = elt['Default']; - if (value === undefined) { - value = elt['Value'][0]; - } - dimensions[key] = value; - }); - } - - var matrixSets = wmtsCap['Contents']['TileMatrixSet']; - var matrixSetObj = ol.array.find(matrixSets, function(elt, index, array) { - return elt['Identifier'] == matrixSet; - }); - - var projection; - if ('projection' in config) { - projection = ol.proj.get(config['projection']); - } else { - projection = ol.proj.get(matrixSetObj['SupportedCRS'].replace( - /urn:ogc:def:crs:(\w+):(.*:)?(\w+)$/, '$1:$3')); - } - - var wgs84BoundingBox = l['WGS84BoundingBox']; - var extent, wrapX; - if (wgs84BoundingBox !== undefined) { - var wgs84ProjectionExtent = ol.proj.get('EPSG:4326').getExtent(); - wrapX = (wgs84BoundingBox[0] == wgs84ProjectionExtent[0] && - wgs84BoundingBox[2] == wgs84ProjectionExtent[2]); - extent = ol.proj.transformExtent( - wgs84BoundingBox, 'EPSG:4326', projection); - var projectionExtent = projection.getExtent(); - if (projectionExtent) { - // If possible, do a sanity check on the extent - it should never be - // bigger than the validity extent of the projection of a matrix set. - if (!ol.extent.containsExtent(projectionExtent, extent)) { - extent = undefined; - } - } - } - - var tileGrid = ol.tilegrid.WMTS.createFromCapabilitiesMatrixSet( - matrixSetObj, extent, matrixLimits); - - /** @type {!Array.<string>} */ - var urls = []; - var requestEncoding = config['requestEncoding']; - requestEncoding = requestEncoding !== undefined ? requestEncoding : ''; - - if ('OperationsMetadata' in wmtsCap && 'GetTile' in wmtsCap['OperationsMetadata']) { - var gets = wmtsCap['OperationsMetadata']['GetTile']['DCP']['HTTP']['Get']; - - for (var i = 0, ii = gets.length; i < ii; ++i) { - var constraint = ol.array.find(gets[i]['Constraint'], function(element) { - return element['name'] == 'GetEncoding'; - }); - var encodings = constraint['AllowedValues']['Value']; - - if (requestEncoding === '') { - // requestEncoding not provided, use the first encoding from the list - requestEncoding = encodings[0]; - } - if (requestEncoding === ol.source.WMTSRequestEncoding.KVP) { - if (ol.array.includes(encodings, ol.source.WMTSRequestEncoding.KVP)) { - urls.push(/** @type {string} */ (gets[i]['href'])); - } - } else { - break; - } - } - } - if (urls.length === 0) { - requestEncoding = ol.source.WMTSRequestEncoding.REST; - l['ResourceURL'].forEach(function(element) { - if (element['resourceType'] === 'tile') { - format = element['format']; - urls.push(/** @type {string} */ (element['template'])); - } - }); - } - - return { - urls: urls, - layer: config['layer'], - matrixSet: matrixSet, - format: format, - projection: projection, - requestEncoding: requestEncoding, - tileGrid: tileGrid, - style: style, - dimensions: dimensions, - wrapX: wrapX, - crossOrigin: config['crossOrigin'] - }; -}; - -goog.provide('ol.source.Zoomify'); - -goog.require('ol'); -goog.require('ol.ImageTile'); -goog.require('ol.TileState'); -goog.require('ol.TileUrlFunction'); -goog.require('ol.asserts'); -goog.require('ol.dom'); -goog.require('ol.extent'); -goog.require('ol.source.TileImage'); -goog.require('ol.tilegrid.TileGrid'); - - -/** - * @classdesc - * Layer source for tile data in Zoomify format (both Zoomify and Internet - * Imaging Protocol are supported). - * - * @constructor - * @extends {ol.source.TileImage} - * @param {olx.source.ZoomifyOptions=} opt_options Options. - * @api - */ -ol.source.Zoomify = function(opt_options) { - - var options = opt_options || {}; - - var size = options.size; - var tierSizeCalculation = options.tierSizeCalculation !== undefined ? - options.tierSizeCalculation : - ol.source.Zoomify.TierSizeCalculation_.DEFAULT; - - var imageWidth = size[0]; - var imageHeight = size[1]; - var tierSizeInTiles = []; - var tileSize = ol.DEFAULT_TILE_SIZE; - - switch (tierSizeCalculation) { - case ol.source.Zoomify.TierSizeCalculation_.DEFAULT: - while (imageWidth > tileSize || imageHeight > tileSize) { - tierSizeInTiles.push([ - Math.ceil(imageWidth / tileSize), - Math.ceil(imageHeight / tileSize) - ]); - tileSize += tileSize; - } - break; - case ol.source.Zoomify.TierSizeCalculation_.TRUNCATED: - var width = imageWidth; - var height = imageHeight; - while (width > tileSize || height > tileSize) { - tierSizeInTiles.push([ - Math.ceil(width / tileSize), - Math.ceil(height / tileSize) - ]); - width >>= 1; - height >>= 1; - } - break; - default: - ol.asserts.assert(false, 53); // Unknown `tierSizeCalculation` configured - break; - } - - tierSizeInTiles.push([1, 1]); - tierSizeInTiles.reverse(); - - var resolutions = [1]; - var tileCountUpToTier = [0]; - var i, ii; - for (i = 1, ii = tierSizeInTiles.length; i < ii; i++) { - resolutions.push(1 << i); - tileCountUpToTier.push( - tierSizeInTiles[i - 1][0] * tierSizeInTiles[i - 1][1] + - tileCountUpToTier[i - 1] - ); - } - resolutions.reverse(); - - var extent = [0, -size[1], size[0], 0]; - var tileGrid = new ol.tilegrid.TileGrid({ - extent: extent, - origin: ol.extent.getTopLeft(extent), - resolutions: resolutions - }); - - var url = options.url; - if (url && url.indexOf('{TileGroup}') == -1 && url.indexOf('{tileIndex}') == -1) { - url += '{TileGroup}/{z}-{x}-{y}.jpg'; - } - var urls = ol.TileUrlFunction.expandUrl(url); - - /** - * @param {string} template Template. - * @return {ol.TileUrlFunctionType} Tile URL function. - */ - function createFromTemplate(template) { - - return ( - /** - * @param {ol.TileCoord} tileCoord Tile Coordinate. - * @param {number} pixelRatio Pixel ratio. - * @param {ol.proj.Projection} projection Projection. - * @return {string|undefined} Tile URL. - */ - function(tileCoord, pixelRatio, projection) { - if (!tileCoord) { - return undefined; - } else { - var tileCoordZ = tileCoord[0]; - var tileCoordX = tileCoord[1]; - var tileCoordY = -tileCoord[2] - 1; - var tileIndex = - tileCoordX + - tileCoordY * tierSizeInTiles[tileCoordZ][0]; - var tileGroup = ((tileIndex + tileCountUpToTier[tileCoordZ]) / ol.DEFAULT_TILE_SIZE) | 0; - var localContext = { - 'z': tileCoordZ, - 'x': tileCoordX, - 'y': tileCoordY, - 'tileIndex': tileIndex, - 'TileGroup': 'TileGroup' + tileGroup - }; - return template.replace(/\{(\w+?)\}/g, function(m, p) { - return localContext[p]; - }); - } - }); - } - - var tileUrlFunction = ol.TileUrlFunction.createFromTileUrlFunctions(urls.map(createFromTemplate)); - - ol.source.TileImage.call(this, { - attributions: options.attributions, - cacheSize: options.cacheSize, - crossOrigin: options.crossOrigin, - logo: options.logo, - projection: options.projection, - reprojectionErrorThreshold: options.reprojectionErrorThreshold, - tileClass: ol.source.Zoomify.Tile_, - tileGrid: tileGrid, - tileUrlFunction: tileUrlFunction, - transition: options.transition - }); - -}; -ol.inherits(ol.source.Zoomify, ol.source.TileImage); - - -/** - * @constructor - * @extends {ol.ImageTile} - * @param {ol.TileCoord} tileCoord Tile coordinate. - * @param {ol.TileState} state State. - * @param {string} src Image source URI. - * @param {?string} crossOrigin Cross origin. - * @param {ol.TileLoadFunctionType} tileLoadFunction Tile load function. - * @param {olx.TileOptions=} opt_options Tile options. - * @private - */ -ol.source.Zoomify.Tile_ = function( - tileCoord, state, src, crossOrigin, tileLoadFunction, opt_options) { - - ol.ImageTile.call(this, tileCoord, state, src, crossOrigin, tileLoadFunction, opt_options); - - /** - * @private - * @type {HTMLCanvasElement|HTMLImageElement|HTMLVideoElement} - */ - this.zoomifyImage_ = null; - -}; -ol.inherits(ol.source.Zoomify.Tile_, ol.ImageTile); - - -/** - * @inheritDoc - */ -ol.source.Zoomify.Tile_.prototype.getImage = function() { - if (this.zoomifyImage_) { - return this.zoomifyImage_; - } - var tileSize = ol.DEFAULT_TILE_SIZE; - var image = ol.ImageTile.prototype.getImage.call(this); - if (this.state == ol.TileState.LOADED) { - if (image.width == tileSize && image.height == tileSize) { - this.zoomifyImage_ = image; - return image; - } else { - var context = ol.dom.createCanvasContext2D(tileSize, tileSize); - context.drawImage(image, 0, 0); - this.zoomifyImage_ = context.canvas; - return context.canvas; - } - } else { - return image; - } -}; - - -/** - * @enum {string} - * @private - */ -ol.source.Zoomify.TierSizeCalculation_ = { - DEFAULT: 'default', - TRUNCATED: 'truncated' -}; - - -/** - * @fileoverview - * @suppress {accessControls, ambiguousFunctionDecl, checkDebuggerStatement, checkRegExp, checkTypes, checkVars, const, constantProperty, deprecated, duplicate, es5Strict, fileoverviewTags, missingProperties, nonStandardJsDocs, strictModuleDepCheck, suspiciousCode, undefinedNames, undefinedVars, unknownDefines, unusedLocalVariables, uselessCode, visibility} - */ -goog.provide('ol.ext.vectortile.VectorTile'); - -/** @typedef {function(*)} */ -ol.ext.vectortile.VectorTile = function() {}; - -(function() {(function (exports) { -'use strict'; - -var pointGeometry = Point; -function Point(x, y) { - this.x = x; - this.y = y; -} -Point.prototype = { - clone: function() { return new Point(this.x, this.y); }, - add: function(p) { return this.clone()._add(p); }, - sub: function(p) { return this.clone()._sub(p); }, - multByPoint: function(p) { return this.clone()._multByPoint(p); }, - divByPoint: function(p) { return this.clone()._divByPoint(p); }, - mult: function(k) { return this.clone()._mult(k); }, - div: function(k) { return this.clone()._div(k); }, - rotate: function(a) { return this.clone()._rotate(a); }, - rotateAround: function(a,p) { return this.clone()._rotateAround(a,p); }, - matMult: function(m) { return this.clone()._matMult(m); }, - unit: function() { return this.clone()._unit(); }, - perp: function() { return this.clone()._perp(); }, - round: function() { return this.clone()._round(); }, - mag: function() { - return Math.sqrt(this.x * this.x + this.y * this.y); - }, - equals: function(other) { - return this.x === other.x && - this.y === other.y; - }, - dist: function(p) { - return Math.sqrt(this.distSqr(p)); - }, - distSqr: function(p) { - var dx = p.x - this.x, - dy = p.y - this.y; - return dx * dx + dy * dy; - }, - angle: function() { - return Math.atan2(this.y, this.x); - }, - angleTo: function(b) { - return Math.atan2(this.y - b.y, this.x - b.x); - }, - angleWith: function(b) { - return this.angleWithSep(b.x, b.y); - }, - angleWithSep: function(x, y) { - return Math.atan2( - this.x * y - this.y * x, - this.x * x + this.y * y); - }, - _matMult: function(m) { - var x = m[0] * this.x + m[1] * this.y, - y = m[2] * this.x + m[3] * this.y; - this.x = x; - this.y = y; - return this; - }, - _add: function(p) { - this.x += p.x; - this.y += p.y; - return this; - }, - _sub: function(p) { - this.x -= p.x; - this.y -= p.y; - return this; - }, - _mult: function(k) { - this.x *= k; - this.y *= k; - return this; - }, - _div: function(k) { - this.x /= k; - this.y /= k; - return this; - }, - _multByPoint: function(p) { - this.x *= p.x; - this.y *= p.y; - return this; - }, - _divByPoint: function(p) { - this.x /= p.x; - this.y /= p.y; - return this; - }, - _unit: function() { - this._div(this.mag()); - return this; - }, - _perp: function() { - var y = this.y; - this.y = this.x; - this.x = -y; - return this; - }, - _rotate: function(angle) { - var cos = Math.cos(angle), - sin = Math.sin(angle), - x = cos * this.x - sin * this.y, - y = sin * this.x + cos * this.y; - this.x = x; - this.y = y; - return this; - }, - _rotateAround: function(angle, p) { - var cos = Math.cos(angle), - sin = Math.sin(angle), - x = p.x + cos * (this.x - p.x) - sin * (this.y - p.y), - y = p.y + sin * (this.x - p.x) + cos * (this.y - p.y); - this.x = x; - this.y = y; - return this; - }, - _round: function() { - this.x = Math.round(this.x); - this.y = Math.round(this.y); - return this; - } -}; -Point.convert = function (a) { - if (a instanceof Point) { - return a; - } - if (Array.isArray(a)) { - return new Point(a[0], a[1]); - } - return a; -}; - -var vectortilefeature = VectorTileFeature$1; -function VectorTileFeature$1(pbf, end, extent, keys, values) { - this.properties = {}; - this.extent = extent; - this.type = 0; - this._pbf = pbf; - this._geometry = -1; - this._keys = keys; - this._values = values; - pbf.readFields(readFeature, this, end); -} -function readFeature(tag, feature, pbf) { - if (tag == 1) feature.id = pbf.readVarint(); - else if (tag == 2) readTag(pbf, feature); - else if (tag == 3) feature.type = pbf.readVarint(); - else if (tag == 4) feature._geometry = pbf.pos; -} -function readTag(pbf, feature) { - var end = pbf.readVarint() + pbf.pos; - while (pbf.pos < end) { - var key = feature._keys[pbf.readVarint()], - value = feature._values[pbf.readVarint()]; - feature.properties[key] = value; - } -} -VectorTileFeature$1.types = ['Unknown', 'Point', 'LineString', 'Polygon']; -VectorTileFeature$1.prototype.loadGeometry = function() { - var pbf = this._pbf; - pbf.pos = this._geometry; - var end = pbf.readVarint() + pbf.pos, - cmd = 1, - length = 0, - x = 0, - y = 0, - lines = [], - line; - while (pbf.pos < end) { - if (!length) { - var cmdLen = pbf.readVarint(); - cmd = cmdLen & 0x7; - length = cmdLen >> 3; - } - length--; - if (cmd === 1 || cmd === 2) { - x += pbf.readSVarint(); - y += pbf.readSVarint(); - if (cmd === 1) { - if (line) lines.push(line); - line = []; - } - line.push(new pointGeometry(x, y)); - } else if (cmd === 7) { - if (line) { - line.push(line[0].clone()); - } - } else { - throw new Error('unknown command ' + cmd); - } - } - if (line) lines.push(line); - return lines; -}; -VectorTileFeature$1.prototype.bbox = function() { - var pbf = this._pbf; - pbf.pos = this._geometry; - var end = pbf.readVarint() + pbf.pos, - cmd = 1, - length = 0, - x = 0, - y = 0, - x1 = Infinity, - x2 = -Infinity, - y1 = Infinity, - y2 = -Infinity; - while (pbf.pos < end) { - if (!length) { - var cmdLen = pbf.readVarint(); - cmd = cmdLen & 0x7; - length = cmdLen >> 3; - } - length--; - if (cmd === 1 || cmd === 2) { - x += pbf.readSVarint(); - y += pbf.readSVarint(); - if (x < x1) x1 = x; - if (x > x2) x2 = x; - if (y < y1) y1 = y; - if (y > y2) y2 = y; - } else if (cmd !== 7) { - throw new Error('unknown command ' + cmd); - } - } - return [x1, y1, x2, y2]; -}; -VectorTileFeature$1.prototype.toGeoJSON = function(x, y, z) { - var size = this.extent * Math.pow(2, z), - x0 = this.extent * x, - y0 = this.extent * y, - coords = this.loadGeometry(), - type = VectorTileFeature$1.types[this.type], - i, j; - function project(line) { - for (var j = 0; j < line.length; j++) { - var p = line[j], y2 = 180 - (p.y + y0) * 360 / size; - line[j] = [ - (p.x + x0) * 360 / size - 180, - 360 / Math.PI * Math.atan(Math.exp(y2 * Math.PI / 180)) - 90 - ]; - } - } - switch (this.type) { - case 1: - var points = []; - for (i = 0; i < coords.length; i++) { - points[i] = coords[i][0]; - } - coords = points; - project(coords); - break; - case 2: - for (i = 0; i < coords.length; i++) { - project(coords[i]); - } - break; - case 3: - coords = classifyRings(coords); - for (i = 0; i < coords.length; i++) { - for (j = 0; j < coords[i].length; j++) { - project(coords[i][j]); - } - } - break; - } - if (coords.length === 1) { - coords = coords[0]; - } else { - type = 'Multi' + type; - } - var result = { - type: "Feature", - geometry: { - type: type, - coordinates: coords - }, - properties: this.properties - }; - if ('id' in this) { - result.id = this.id; - } - return result; -}; -function classifyRings(rings) { - var len = rings.length; - if (len <= 1) return [rings]; - var polygons = [], - polygon, - ccw; - for (var i = 0; i < len; i++) { - var area = signedArea(rings[i]); - if (area === 0) continue; - if (ccw === undefined) ccw = area < 0; - if (ccw === area < 0) { - if (polygon) polygons.push(polygon); - polygon = [rings[i]]; - } else { - polygon.push(rings[i]); - } - } - if (polygon) polygons.push(polygon); - return polygons; -} -function signedArea(ring) { - var sum = 0; - for (var i = 0, len = ring.length, j = len - 1, p1, p2; i < len; j = i++) { - p1 = ring[i]; - p2 = ring[j]; - sum += (p2.x - p1.x) * (p1.y + p2.y); - } - return sum; -} - -var vectortilelayer = VectorTileLayer$1; -function VectorTileLayer$1(pbf, end) { - this.version = 1; - this.name = null; - this.extent = 4096; - this.length = 0; - this._pbf = pbf; - this._keys = []; - this._values = []; - this._features = []; - pbf.readFields(readLayer, this, end); - this.length = this._features.length; -} -function readLayer(tag, layer, pbf) { - if (tag === 15) layer.version = pbf.readVarint(); - else if (tag === 1) layer.name = pbf.readString(); - else if (tag === 5) layer.extent = pbf.readVarint(); - else if (tag === 2) layer._features.push(pbf.pos); - else if (tag === 3) layer._keys.push(pbf.readString()); - else if (tag === 4) layer._values.push(readValueMessage(pbf)); -} -function readValueMessage(pbf) { - var value = null, - end = pbf.readVarint() + pbf.pos; - while (pbf.pos < end) { - var tag = pbf.readVarint() >> 3; - value = tag === 1 ? pbf.readString() : - tag === 2 ? pbf.readFloat() : - tag === 3 ? pbf.readDouble() : - tag === 4 ? pbf.readVarint64() : - tag === 5 ? pbf.readVarint() : - tag === 6 ? pbf.readSVarint() : - tag === 7 ? pbf.readBoolean() : null; - } - return value; -} -VectorTileLayer$1.prototype.feature = function(i) { - if (i < 0 || i >= this._features.length) throw new Error('feature index out of bounds'); - this._pbf.pos = this._features[i]; - var end = this._pbf.readVarint() + this._pbf.pos; - return new vectortilefeature(this._pbf, end, this.extent, this._keys, this._values); -}; - -var vectortile = VectorTile$1; -function VectorTile$1(pbf, end) { - this.layers = pbf.readFields(readTile, {}, end); -} -function readTile(tag, layers, pbf) { - if (tag === 3) { - var layer = new vectortilelayer(pbf, pbf.readVarint() + pbf.pos); - if (layer.length) layers[layer.name] = layer; - } -} - -var VectorTile = vectortile; -var VectorTileFeature = vectortilefeature; -var VectorTileLayer = vectortilelayer; -var vectorTile = { - VectorTile: VectorTile, - VectorTileFeature: VectorTileFeature, - VectorTileLayer: VectorTileLayer -}; - -exports['default'] = vectorTile; -exports.VectorTile = VectorTile; -exports.VectorTileFeature = VectorTileFeature; -exports.VectorTileLayer = VectorTileLayer; - -}((this.vectortile = this.vectortile || {})));}).call(ol.ext); - -// Copyright 2009 The Closure Library Authors. -// All Rights Reserved. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS-IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -// -// This file has been auto-generated by GenJsDeps, please do not edit. - -goog.addDependency( - 'demos/editor/equationeditor.js', ['goog.demos.editor.EquationEditor'], - ['goog.ui.equation.EquationEditorDialog']); -goog.addDependency( - 'demos/editor/helloworld.js', ['goog.demos.editor.HelloWorld'], - ['goog.dom', 'goog.dom.TagName', 'goog.editor.Plugin']); -goog.addDependency( - 'demos/editor/helloworlddialog.js', - [ - 'goog.demos.editor.HelloWorldDialog', - 'goog.demos.editor.HelloWorldDialog.OkEvent' - ], - [ - 'goog.dom.TagName', 'goog.events.Event', 'goog.string', - 'goog.ui.editor.AbstractDialog', 'goog.ui.editor.AbstractDialog.Builder', - 'goog.ui.editor.AbstractDialog.EventType' - ]); -goog.addDependency( - 'demos/editor/helloworlddialogplugin.js', - [ - 'goog.demos.editor.HelloWorldDialogPlugin', - 'goog.demos.editor.HelloWorldDialogPlugin.Command' - ], - [ - 'goog.demos.editor.HelloWorldDialog', 'goog.dom.TagName', - 'goog.editor.plugins.AbstractDialogPlugin', 'goog.editor.range', - 'goog.functions', 'goog.ui.editor.AbstractDialog.EventType' - ]); - -/** - * @fileoverview Custom exports file. - * @suppress {checkVars,extraRequire} - */ - -goog.require('ol'); -goog.require('ol.AssertionError'); -goog.require('ol.Attribution'); -goog.require('ol.CanvasMap'); -goog.require('ol.Collection'); -goog.require('ol.DeviceOrientation'); -goog.require('ol.Feature'); -goog.require('ol.Geolocation'); -goog.require('ol.Graticule'); -goog.require('ol.Image'); -goog.require('ol.ImageTile'); -goog.require('ol.Kinetic'); -goog.require('ol.Map'); -goog.require('ol.MapBrowserEvent'); -goog.require('ol.MapEvent'); -goog.require('ol.Object'); -goog.require('ol.Observable'); -goog.require('ol.Overlay'); -goog.require('ol.PluggableMap'); -goog.require('ol.Sphere'); -goog.require('ol.Tile'); -goog.require('ol.VectorTile'); -goog.require('ol.View'); -goog.require('ol.color'); -goog.require('ol.colorlike'); -goog.require('ol.control'); -goog.require('ol.control.Attribution'); -goog.require('ol.control.Control'); -goog.require('ol.control.FullScreen'); -goog.require('ol.control.MousePosition'); -goog.require('ol.control.OverviewMap'); -goog.require('ol.control.Rotate'); -goog.require('ol.control.ScaleLine'); -goog.require('ol.control.Zoom'); -goog.require('ol.control.ZoomSlider'); -goog.require('ol.control.ZoomToExtent'); -goog.require('ol.coordinate'); -goog.require('ol.easing'); -goog.require('ol.events.Event'); -goog.require('ol.events.condition'); -goog.require('ol.extent'); -goog.require('ol.featureloader'); -goog.require('ol.format.EsriJSON'); -goog.require('ol.format.Feature'); -goog.require('ol.format.GML'); -goog.require('ol.format.GML2'); -goog.require('ol.format.GML3'); -goog.require('ol.format.GMLBase'); -goog.require('ol.format.GPX'); -goog.require('ol.format.GeoJSON'); -goog.require('ol.format.IGC'); -goog.require('ol.format.KML'); -goog.require('ol.format.MVT'); -goog.require('ol.format.OSMXML'); -goog.require('ol.format.Polyline'); -goog.require('ol.format.TopoJSON'); -goog.require('ol.format.WFS'); -goog.require('ol.format.WKT'); -goog.require('ol.format.WMSCapabilities'); -goog.require('ol.format.WMSGetFeatureInfo'); -goog.require('ol.format.WMTSCapabilities'); -goog.require('ol.format.filter'); -goog.require('ol.format.filter.And'); -goog.require('ol.format.filter.Bbox'); -goog.require('ol.format.filter.Comparison'); -goog.require('ol.format.filter.ComparisonBinary'); -goog.require('ol.format.filter.During'); -goog.require('ol.format.filter.EqualTo'); -goog.require('ol.format.filter.Filter'); -goog.require('ol.format.filter.GreaterThan'); -goog.require('ol.format.filter.GreaterThanOrEqualTo'); -goog.require('ol.format.filter.Intersects'); -goog.require('ol.format.filter.IsBetween'); -goog.require('ol.format.filter.IsLike'); -goog.require('ol.format.filter.IsNull'); -goog.require('ol.format.filter.LessThan'); -goog.require('ol.format.filter.LessThanOrEqualTo'); -goog.require('ol.format.filter.Not'); -goog.require('ol.format.filter.NotEqualTo'); -goog.require('ol.format.filter.Or'); -goog.require('ol.format.filter.Spatial'); -goog.require('ol.format.filter.Within'); -goog.require('ol.geom.Circle'); -goog.require('ol.geom.Geometry'); -goog.require('ol.geom.GeometryCollection'); -goog.require('ol.geom.LineString'); -goog.require('ol.geom.LinearRing'); -goog.require('ol.geom.MultiLineString'); -goog.require('ol.geom.MultiPoint'); -goog.require('ol.geom.MultiPolygon'); -goog.require('ol.geom.Point'); -goog.require('ol.geom.Polygon'); -goog.require('ol.geom.SimpleGeometry'); -goog.require('ol.has'); -goog.require('ol.interaction'); -goog.require('ol.interaction.DoubleClickZoom'); -goog.require('ol.interaction.DragAndDrop'); -goog.require('ol.interaction.DragBox'); -goog.require('ol.interaction.DragPan'); -goog.require('ol.interaction.DragRotate'); -goog.require('ol.interaction.DragRotateAndZoom'); -goog.require('ol.interaction.DragZoom'); -goog.require('ol.interaction.Draw'); -goog.require('ol.interaction.Extent'); -goog.require('ol.interaction.Interaction'); -goog.require('ol.interaction.KeyboardPan'); -goog.require('ol.interaction.KeyboardZoom'); -goog.require('ol.interaction.Modify'); -goog.require('ol.interaction.MouseWheelZoom'); -goog.require('ol.interaction.PinchRotate'); -goog.require('ol.interaction.PinchZoom'); -goog.require('ol.interaction.Pointer'); -goog.require('ol.interaction.Select'); -goog.require('ol.interaction.Snap'); -goog.require('ol.interaction.Translate'); -goog.require('ol.layer.Base'); -goog.require('ol.layer.Group'); -goog.require('ol.layer.Heatmap'); -goog.require('ol.layer.Image'); -goog.require('ol.layer.Layer'); -goog.require('ol.layer.Tile'); -goog.require('ol.layer.Vector'); -goog.require('ol.layer.VectorTile'); -goog.require('ol.loadingstrategy'); -goog.require('ol.proj'); -goog.require('ol.proj.Projection'); -goog.require('ol.proj.Units'); -goog.require('ol.proj.common'); -goog.require('ol.render'); -goog.require('ol.render.Event'); -goog.require('ol.render.Feature'); -goog.require('ol.render.VectorContext'); -goog.require('ol.render.canvas.Immediate'); -goog.require('ol.render.webgl.Immediate'); -goog.require('ol.renderer.canvas.ImageLayer'); -goog.require('ol.renderer.canvas.Map'); -goog.require('ol.renderer.canvas.TileLayer'); -goog.require('ol.renderer.canvas.VectorLayer'); -goog.require('ol.renderer.canvas.VectorTileLayer'); -goog.require('ol.renderer.webgl.ImageLayer'); -goog.require('ol.renderer.webgl.Map'); -goog.require('ol.renderer.webgl.TileLayer'); -goog.require('ol.renderer.webgl.VectorLayer'); -goog.require('ol.size'); -goog.require('ol.source.BingMaps'); -goog.require('ol.source.CartoDB'); -goog.require('ol.source.Cluster'); -goog.require('ol.source.Image'); -goog.require('ol.source.ImageArcGISRest'); -goog.require('ol.source.ImageCanvas'); -goog.require('ol.source.ImageMapGuide'); -goog.require('ol.source.ImageStatic'); -goog.require('ol.source.ImageVector'); -goog.require('ol.source.ImageWMS'); -goog.require('ol.source.OSM'); -goog.require('ol.source.Raster'); -goog.require('ol.source.Source'); -goog.require('ol.source.Stamen'); -goog.require('ol.source.Tile'); -goog.require('ol.source.TileArcGISRest'); -goog.require('ol.source.TileDebug'); -goog.require('ol.source.TileImage'); -goog.require('ol.source.TileJSON'); -goog.require('ol.source.TileUTFGrid'); -goog.require('ol.source.TileWMS'); -goog.require('ol.source.UrlTile'); -goog.require('ol.source.Vector'); -goog.require('ol.source.VectorTile'); -goog.require('ol.source.WMTS'); -goog.require('ol.source.XYZ'); -goog.require('ol.source.Zoomify'); -goog.require('ol.style.AtlasManager'); -goog.require('ol.style.Circle'); -goog.require('ol.style.Fill'); -goog.require('ol.style.Icon'); -goog.require('ol.style.Image'); -goog.require('ol.style.RegularShape'); -goog.require('ol.style.Stroke'); -goog.require('ol.style.Style'); -goog.require('ol.style.Text'); -goog.require('ol.tilegrid'); -goog.require('ol.tilegrid.TileGrid'); -goog.require('ol.tilegrid.WMTS'); -goog.require('ol.webgl.Context'); -goog.require('ol.xml'); - - - -goog.exportProperty( - ol.AssertionError.prototype, - 'code', - ol.AssertionError.prototype.code); - -goog.exportSymbol( - 'ol.Attribution', - ol.Attribution, - OPENLAYERS); - -goog.exportProperty( - ol.Attribution.prototype, - 'getHTML', - ol.Attribution.prototype.getHTML); - -goog.exportSymbol( - 'ol.CanvasMap', - ol.CanvasMap, - OPENLAYERS); - -goog.exportSymbol( - 'ol.Collection', - ol.Collection, - OPENLAYERS); - -goog.exportProperty( - ol.Collection.prototype, - 'clear', - ol.Collection.prototype.clear); - -goog.exportProperty( - ol.Collection.prototype, - 'extend', - ol.Collection.prototype.extend); - -goog.exportProperty( - ol.Collection.prototype, - 'forEach', - ol.Collection.prototype.forEach); - -goog.exportProperty( - ol.Collection.prototype, - 'getArray', - ol.Collection.prototype.getArray); - -goog.exportProperty( - ol.Collection.prototype, - 'item', - ol.Collection.prototype.item); - -goog.exportProperty( - ol.Collection.prototype, - 'getLength', - ol.Collection.prototype.getLength); - -goog.exportProperty( - ol.Collection.prototype, - 'insertAt', - ol.Collection.prototype.insertAt); - -goog.exportProperty( - ol.Collection.prototype, - 'pop', - ol.Collection.prototype.pop); - -goog.exportProperty( - ol.Collection.prototype, - 'push', - ol.Collection.prototype.push); - -goog.exportProperty( - ol.Collection.prototype, - 'remove', - ol.Collection.prototype.remove); - -goog.exportProperty( - ol.Collection.prototype, - 'removeAt', - ol.Collection.prototype.removeAt); - -goog.exportProperty( - ol.Collection.prototype, - 'setAt', - ol.Collection.prototype.setAt); - -goog.exportProperty( - ol.Collection.Event.prototype, - 'element', - ol.Collection.Event.prototype.element); - -goog.exportSymbol( - 'ol.color.asArray', - ol.color.asArray, - OPENLAYERS); - -goog.exportSymbol( - 'ol.color.asString', - ol.color.asString, - OPENLAYERS); - -goog.exportSymbol( - 'ol.colorlike.asColorLike', - ol.colorlike.asColorLike, - OPENLAYERS); - -goog.exportSymbol( - 'ol.control.defaults', - ol.control.defaults, - OPENLAYERS); - -goog.exportSymbol( - 'ol.coordinate.add', - ol.coordinate.add, - OPENLAYERS); - -goog.exportSymbol( - 'ol.coordinate.createStringXY', - ol.coordinate.createStringXY, - OPENLAYERS); - -goog.exportSymbol( - 'ol.coordinate.format', - ol.coordinate.format, - OPENLAYERS); - -goog.exportSymbol( - 'ol.coordinate.rotate', - ol.coordinate.rotate, - OPENLAYERS); - -goog.exportSymbol( - 'ol.coordinate.toStringHDMS', - ol.coordinate.toStringHDMS, - OPENLAYERS); - -goog.exportSymbol( - 'ol.coordinate.toStringXY', - ol.coordinate.toStringXY, - OPENLAYERS); - -goog.exportSymbol( - 'ol.DeviceOrientation', - ol.DeviceOrientation, - OPENLAYERS); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'getAlpha', - ol.DeviceOrientation.prototype.getAlpha); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'getBeta', - ol.DeviceOrientation.prototype.getBeta); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'getGamma', - ol.DeviceOrientation.prototype.getGamma); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'getHeading', - ol.DeviceOrientation.prototype.getHeading); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'getTracking', - ol.DeviceOrientation.prototype.getTracking); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'setTracking', - ol.DeviceOrientation.prototype.setTracking); - -goog.exportSymbol( - 'ol.easing.easeIn', - ol.easing.easeIn, - OPENLAYERS); - -goog.exportSymbol( - 'ol.easing.easeOut', - ol.easing.easeOut, - OPENLAYERS); - -goog.exportSymbol( - 'ol.easing.inAndOut', - ol.easing.inAndOut, - OPENLAYERS); - -goog.exportSymbol( - 'ol.easing.linear', - ol.easing.linear, - OPENLAYERS); - -goog.exportSymbol( - 'ol.easing.upAndDown', - ol.easing.upAndDown, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.boundingExtent', - ol.extent.boundingExtent, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.buffer', - ol.extent.buffer, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.containsCoordinate', - ol.extent.containsCoordinate, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.containsExtent', - ol.extent.containsExtent, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.containsXY', - ol.extent.containsXY, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.createEmpty', - ol.extent.createEmpty, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.equals', - ol.extent.equals, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.extend', - ol.extent.extend, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.getArea', - ol.extent.getArea, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.getBottomLeft', - ol.extent.getBottomLeft, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.getBottomRight', - ol.extent.getBottomRight, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.getCenter', - ol.extent.getCenter, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.getHeight', - ol.extent.getHeight, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.getIntersection', - ol.extent.getIntersection, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.getSize', - ol.extent.getSize, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.getTopLeft', - ol.extent.getTopLeft, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.getTopRight', - ol.extent.getTopRight, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.getWidth', - ol.extent.getWidth, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.intersects', - ol.extent.intersects, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.isEmpty', - ol.extent.isEmpty, - OPENLAYERS); - -goog.exportSymbol( - 'ol.extent.applyTransform', - ol.extent.applyTransform, - OPENLAYERS); - -goog.exportSymbol( - 'ol.Feature', - ol.Feature, - OPENLAYERS); - -goog.exportProperty( - ol.Feature.prototype, - 'clone', - ol.Feature.prototype.clone); - -goog.exportProperty( - ol.Feature.prototype, - 'getGeometry', - ol.Feature.prototype.getGeometry); - -goog.exportProperty( - ol.Feature.prototype, - 'getId', - ol.Feature.prototype.getId); - -goog.exportProperty( - ol.Feature.prototype, - 'getGeometryName', - ol.Feature.prototype.getGeometryName); - -goog.exportProperty( - ol.Feature.prototype, - 'getStyle', - ol.Feature.prototype.getStyle); - -goog.exportProperty( - ol.Feature.prototype, - 'getStyleFunction', - ol.Feature.prototype.getStyleFunction); - -goog.exportProperty( - ol.Feature.prototype, - 'setGeometry', - ol.Feature.prototype.setGeometry); - -goog.exportProperty( - ol.Feature.prototype, - 'setStyle', - ol.Feature.prototype.setStyle); - -goog.exportProperty( - ol.Feature.prototype, - 'setId', - ol.Feature.prototype.setId); - -goog.exportProperty( - ol.Feature.prototype, - 'setGeometryName', - ol.Feature.prototype.setGeometryName); - -goog.exportSymbol( - 'ol.featureloader.xhr', - ol.featureloader.xhr, - OPENLAYERS); - -goog.exportSymbol( - 'ol.Geolocation', - ol.Geolocation, - OPENLAYERS); - -goog.exportProperty( - ol.Geolocation.prototype, - 'getAccuracy', - ol.Geolocation.prototype.getAccuracy); - -goog.exportProperty( - ol.Geolocation.prototype, - 'getAccuracyGeometry', - ol.Geolocation.prototype.getAccuracyGeometry); - -goog.exportProperty( - ol.Geolocation.prototype, - 'getAltitude', - ol.Geolocation.prototype.getAltitude); - -goog.exportProperty( - ol.Geolocation.prototype, - 'getAltitudeAccuracy', - ol.Geolocation.prototype.getAltitudeAccuracy); - -goog.exportProperty( - ol.Geolocation.prototype, - 'getHeading', - ol.Geolocation.prototype.getHeading); - -goog.exportProperty( - ol.Geolocation.prototype, - 'getPosition', - ol.Geolocation.prototype.getPosition); - -goog.exportProperty( - ol.Geolocation.prototype, - 'getProjection', - ol.Geolocation.prototype.getProjection); - -goog.exportProperty( - ol.Geolocation.prototype, - 'getSpeed', - ol.Geolocation.prototype.getSpeed); - -goog.exportProperty( - ol.Geolocation.prototype, - 'getTracking', - ol.Geolocation.prototype.getTracking); - -goog.exportProperty( - ol.Geolocation.prototype, - 'getTrackingOptions', - ol.Geolocation.prototype.getTrackingOptions); - -goog.exportProperty( - ol.Geolocation.prototype, - 'setProjection', - ol.Geolocation.prototype.setProjection); - -goog.exportProperty( - ol.Geolocation.prototype, - 'setTracking', - ol.Geolocation.prototype.setTracking); - -goog.exportProperty( - ol.Geolocation.prototype, - 'setTrackingOptions', - ol.Geolocation.prototype.setTrackingOptions); - -goog.exportSymbol( - 'ol.Graticule', - ol.Graticule, - OPENLAYERS); - -goog.exportProperty( - ol.Graticule.prototype, - 'getMap', - ol.Graticule.prototype.getMap); - -goog.exportProperty( - ol.Graticule.prototype, - 'getMeridians', - ol.Graticule.prototype.getMeridians); - -goog.exportProperty( - ol.Graticule.prototype, - 'getParallels', - ol.Graticule.prototype.getParallels); - -goog.exportProperty( - ol.Graticule.prototype, - 'setMap', - ol.Graticule.prototype.setMap); - -goog.exportSymbol( - 'ol.has.DEVICE_PIXEL_RATIO', - ol.has.DEVICE_PIXEL_RATIO, - OPENLAYERS); - -goog.exportSymbol( - 'ol.has.CANVAS', - ol.has.CANVAS, - OPENLAYERS); - -goog.exportSymbol( - 'ol.has.DEVICE_ORIENTATION', - ol.has.DEVICE_ORIENTATION, - OPENLAYERS); - -goog.exportSymbol( - 'ol.has.GEOLOCATION', - ol.has.GEOLOCATION, - OPENLAYERS); - -goog.exportSymbol( - 'ol.has.TOUCH', - ol.has.TOUCH, - OPENLAYERS); - -goog.exportSymbol( - 'ol.has.WEBGL', - ol.has.WEBGL, - OPENLAYERS); - -goog.exportProperty( - ol.Image.prototype, - 'getImage', - ol.Image.prototype.getImage); - -goog.exportProperty( - ol.Image.prototype, - 'load', - ol.Image.prototype.load); - -goog.exportProperty( - ol.ImageTile.prototype, - 'getImage', - ol.ImageTile.prototype.getImage); - -goog.exportSymbol( - 'ol.inherits', - ol.inherits, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.defaults', - ol.interaction.defaults, - OPENLAYERS); - -goog.exportSymbol( - 'ol.Kinetic', - ol.Kinetic, - OPENLAYERS); - -goog.exportSymbol( - 'ol.loadingstrategy.all', - ol.loadingstrategy.all, - OPENLAYERS); - -goog.exportSymbol( - 'ol.loadingstrategy.bbox', - ol.loadingstrategy.bbox, - OPENLAYERS); - -goog.exportSymbol( - 'ol.loadingstrategy.tile', - ol.loadingstrategy.tile, - OPENLAYERS); - -goog.exportSymbol( - 'ol.Map', - ol.Map, - OPENLAYERS); - -goog.exportProperty( - ol.MapBrowserEvent.prototype, - 'originalEvent', - ol.MapBrowserEvent.prototype.originalEvent); - -goog.exportProperty( - ol.MapBrowserEvent.prototype, - 'pixel', - ol.MapBrowserEvent.prototype.pixel); - -goog.exportProperty( - ol.MapBrowserEvent.prototype, - 'coordinate', - ol.MapBrowserEvent.prototype.coordinate); - -goog.exportProperty( - ol.MapBrowserEvent.prototype, - 'dragging', - ol.MapBrowserEvent.prototype.dragging); - -goog.exportProperty( - ol.MapEvent.prototype, - 'map', - ol.MapEvent.prototype.map); - -goog.exportProperty( - ol.MapEvent.prototype, - 'frameState', - ol.MapEvent.prototype.frameState); - -goog.exportSymbol( - 'ol.Object', - ol.Object, - OPENLAYERS); - -goog.exportProperty( - ol.Object.prototype, - 'get', - ol.Object.prototype.get); - -goog.exportProperty( - ol.Object.prototype, - 'getKeys', - ol.Object.prototype.getKeys); - -goog.exportProperty( - ol.Object.prototype, - 'getProperties', - ol.Object.prototype.getProperties); - -goog.exportProperty( - ol.Object.prototype, - 'set', - ol.Object.prototype.set); - -goog.exportProperty( - ol.Object.prototype, - 'setProperties', - ol.Object.prototype.setProperties); - -goog.exportProperty( - ol.Object.prototype, - 'unset', - ol.Object.prototype.unset); - -goog.exportProperty( - ol.Object.Event.prototype, - 'key', - ol.Object.Event.prototype.key); - -goog.exportProperty( - ol.Object.Event.prototype, - 'oldValue', - ol.Object.Event.prototype.oldValue); - -goog.exportSymbol( - 'ol.Observable', - ol.Observable, - OPENLAYERS); - -goog.exportSymbol( - 'ol.Observable.unByKey', - ol.Observable.unByKey, - OPENLAYERS); - -goog.exportProperty( - ol.Observable.prototype, - 'changed', - ol.Observable.prototype.changed); - -goog.exportProperty( - ol.Observable.prototype, - 'dispatchEvent', - ol.Observable.prototype.dispatchEvent); - -goog.exportProperty( - ol.Observable.prototype, - 'getRevision', - ol.Observable.prototype.getRevision); - -goog.exportProperty( - ol.Observable.prototype, - 'on', - ol.Observable.prototype.on); - -goog.exportProperty( - ol.Observable.prototype, - 'once', - ol.Observable.prototype.once); - -goog.exportProperty( - ol.Observable.prototype, - 'un', - ol.Observable.prototype.un); - -goog.exportSymbol( - 'ol.Overlay', - ol.Overlay, - OPENLAYERS); - -goog.exportProperty( - ol.Overlay.prototype, - 'getElement', - ol.Overlay.prototype.getElement); - -goog.exportProperty( - ol.Overlay.prototype, - 'getId', - ol.Overlay.prototype.getId); - -goog.exportProperty( - ol.Overlay.prototype, - 'getMap', - ol.Overlay.prototype.getMap); - -goog.exportProperty( - ol.Overlay.prototype, - 'getOffset', - ol.Overlay.prototype.getOffset); - -goog.exportProperty( - ol.Overlay.prototype, - 'getPosition', - ol.Overlay.prototype.getPosition); - -goog.exportProperty( - ol.Overlay.prototype, - 'getPositioning', - ol.Overlay.prototype.getPositioning); - -goog.exportProperty( - ol.Overlay.prototype, - 'setElement', - ol.Overlay.prototype.setElement); - -goog.exportProperty( - ol.Overlay.prototype, - 'setMap', - ol.Overlay.prototype.setMap); - -goog.exportProperty( - ol.Overlay.prototype, - 'setOffset', - ol.Overlay.prototype.setOffset); - -goog.exportProperty( - ol.Overlay.prototype, - 'setPosition', - ol.Overlay.prototype.setPosition); - -goog.exportProperty( - ol.Overlay.prototype, - 'setPositioning', - ol.Overlay.prototype.setPositioning); - -goog.exportSymbol( - 'ol.PluggableMap', - ol.PluggableMap, - OPENLAYERS); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'addControl', - ol.PluggableMap.prototype.addControl); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'addInteraction', - ol.PluggableMap.prototype.addInteraction); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'addLayer', - ol.PluggableMap.prototype.addLayer); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'addOverlay', - ol.PluggableMap.prototype.addOverlay); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'forEachFeatureAtPixel', - ol.PluggableMap.prototype.forEachFeatureAtPixel); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getFeaturesAtPixel', - ol.PluggableMap.prototype.getFeaturesAtPixel); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'forEachLayerAtPixel', - ol.PluggableMap.prototype.forEachLayerAtPixel); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'hasFeatureAtPixel', - ol.PluggableMap.prototype.hasFeatureAtPixel); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getEventCoordinate', - ol.PluggableMap.prototype.getEventCoordinate); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getEventPixel', - ol.PluggableMap.prototype.getEventPixel); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getTarget', - ol.PluggableMap.prototype.getTarget); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getTargetElement', - ol.PluggableMap.prototype.getTargetElement); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getCoordinateFromPixel', - ol.PluggableMap.prototype.getCoordinateFromPixel); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getControls', - ol.PluggableMap.prototype.getControls); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getOverlays', - ol.PluggableMap.prototype.getOverlays); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getOverlayById', - ol.PluggableMap.prototype.getOverlayById); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getInteractions', - ol.PluggableMap.prototype.getInteractions); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getLayerGroup', - ol.PluggableMap.prototype.getLayerGroup); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getLayers', - ol.PluggableMap.prototype.getLayers); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getPixelFromCoordinate', - ol.PluggableMap.prototype.getPixelFromCoordinate); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getSize', - ol.PluggableMap.prototype.getSize); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getView', - ol.PluggableMap.prototype.getView); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getViewport', - ol.PluggableMap.prototype.getViewport); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'renderSync', - ol.PluggableMap.prototype.renderSync); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'render', - ol.PluggableMap.prototype.render); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'removeControl', - ol.PluggableMap.prototype.removeControl); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'removeInteraction', - ol.PluggableMap.prototype.removeInteraction); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'removeLayer', - ol.PluggableMap.prototype.removeLayer); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'removeOverlay', - ol.PluggableMap.prototype.removeOverlay); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'setLayerGroup', - ol.PluggableMap.prototype.setLayerGroup); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'setSize', - ol.PluggableMap.prototype.setSize); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'setTarget', - ol.PluggableMap.prototype.setTarget); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'setView', - ol.PluggableMap.prototype.setView); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'updateSize', - ol.PluggableMap.prototype.updateSize); - -goog.exportSymbol( - 'ol.proj.METERS_PER_UNIT', - ol.proj.METERS_PER_UNIT, - OPENLAYERS); - -goog.exportSymbol( - 'ol.proj.setProj4', - ol.proj.setProj4, - OPENLAYERS); - -goog.exportSymbol( - 'ol.proj.getPointResolution', - ol.proj.getPointResolution, - OPENLAYERS); - -goog.exportSymbol( - 'ol.proj.addEquivalentProjections', - ol.proj.addEquivalentProjections, - OPENLAYERS); - -goog.exportSymbol( - 'ol.proj.addProjection', - ol.proj.addProjection, - OPENLAYERS); - -goog.exportSymbol( - 'ol.proj.addCoordinateTransforms', - ol.proj.addCoordinateTransforms, - OPENLAYERS); - -goog.exportSymbol( - 'ol.proj.fromLonLat', - ol.proj.fromLonLat, - OPENLAYERS); - -goog.exportSymbol( - 'ol.proj.toLonLat', - ol.proj.toLonLat, - OPENLAYERS); - -goog.exportSymbol( - 'ol.proj.get', - ol.proj.get, - OPENLAYERS); - -goog.exportSymbol( - 'ol.proj.equivalent', - ol.proj.equivalent, - OPENLAYERS); - -goog.exportSymbol( - 'ol.proj.getTransform', - ol.proj.getTransform, - OPENLAYERS); - -goog.exportSymbol( - 'ol.proj.transform', - ol.proj.transform, - OPENLAYERS); - -goog.exportSymbol( - 'ol.proj.transformExtent', - ol.proj.transformExtent, - OPENLAYERS); - -goog.exportSymbol( - 'ol.render.toContext', - ol.render.toContext, - OPENLAYERS); - -goog.exportSymbol( - 'ol.size.toSize', - ol.size.toSize, - OPENLAYERS); - -goog.exportSymbol( - 'ol.Sphere', - ol.Sphere, - OPENLAYERS); - -goog.exportProperty( - ol.Sphere.prototype, - 'geodesicArea', - ol.Sphere.prototype.geodesicArea); - -goog.exportProperty( - ol.Sphere.prototype, - 'haversineDistance', - ol.Sphere.prototype.haversineDistance); - -goog.exportSymbol( - 'ol.Sphere.getLength', - ol.Sphere.getLength, - OPENLAYERS); - -goog.exportSymbol( - 'ol.Sphere.getArea', - ol.Sphere.getArea, - OPENLAYERS); - -goog.exportProperty( - ol.Tile.prototype, - 'getTileCoord', - ol.Tile.prototype.getTileCoord); - -goog.exportProperty( - ol.Tile.prototype, - 'load', - ol.Tile.prototype.load); - -goog.exportSymbol( - 'ol.tilegrid.createXYZ', - ol.tilegrid.createXYZ, - OPENLAYERS); - -goog.exportProperty( - ol.VectorTile.prototype, - 'getFormat', - ol.VectorTile.prototype.getFormat); - -goog.exportProperty( - ol.VectorTile.prototype, - 'getFeatures', - ol.VectorTile.prototype.getFeatures); - -goog.exportProperty( - ol.VectorTile.prototype, - 'getProjection', - ol.VectorTile.prototype.getProjection); - -goog.exportProperty( - ol.VectorTile.prototype, - 'setExtent', - ol.VectorTile.prototype.setExtent); - -goog.exportProperty( - ol.VectorTile.prototype, - 'setFeatures', - ol.VectorTile.prototype.setFeatures); - -goog.exportProperty( - ol.VectorTile.prototype, - 'setProjection', - ol.VectorTile.prototype.setProjection); - -goog.exportProperty( - ol.VectorTile.prototype, - 'setLoader', - ol.VectorTile.prototype.setLoader); - -goog.exportSymbol( - 'ol.View', - ol.View, - OPENLAYERS); - -goog.exportProperty( - ol.View.prototype, - 'animate', - ol.View.prototype.animate); - -goog.exportProperty( - ol.View.prototype, - 'getAnimating', - ol.View.prototype.getAnimating); - -goog.exportProperty( - ol.View.prototype, - 'getInteracting', - ol.View.prototype.getInteracting); - -goog.exportProperty( - ol.View.prototype, - 'cancelAnimations', - ol.View.prototype.cancelAnimations); - -goog.exportProperty( - ol.View.prototype, - 'constrainCenter', - ol.View.prototype.constrainCenter); - -goog.exportProperty( - ol.View.prototype, - 'constrainResolution', - ol.View.prototype.constrainResolution); - -goog.exportProperty( - ol.View.prototype, - 'constrainRotation', - ol.View.prototype.constrainRotation); - -goog.exportProperty( - ol.View.prototype, - 'getCenter', - ol.View.prototype.getCenter); - -goog.exportProperty( - ol.View.prototype, - 'calculateExtent', - ol.View.prototype.calculateExtent); - -goog.exportProperty( - ol.View.prototype, - 'getMaxResolution', - ol.View.prototype.getMaxResolution); - -goog.exportProperty( - ol.View.prototype, - 'getMinResolution', - ol.View.prototype.getMinResolution); - -goog.exportProperty( - ol.View.prototype, - 'getMaxZoom', - ol.View.prototype.getMaxZoom); - -goog.exportProperty( - ol.View.prototype, - 'setMaxZoom', - ol.View.prototype.setMaxZoom); - -goog.exportProperty( - ol.View.prototype, - 'getMinZoom', - ol.View.prototype.getMinZoom); - -goog.exportProperty( - ol.View.prototype, - 'setMinZoom', - ol.View.prototype.setMinZoom); - -goog.exportProperty( - ol.View.prototype, - 'getProjection', - ol.View.prototype.getProjection); - -goog.exportProperty( - ol.View.prototype, - 'getResolution', - ol.View.prototype.getResolution); - -goog.exportProperty( - ol.View.prototype, - 'getResolutions', - ol.View.prototype.getResolutions); - -goog.exportProperty( - ol.View.prototype, - 'getResolutionForExtent', - ol.View.prototype.getResolutionForExtent); - -goog.exportProperty( - ol.View.prototype, - 'getRotation', - ol.View.prototype.getRotation); - -goog.exportProperty( - ol.View.prototype, - 'getZoom', - ol.View.prototype.getZoom); - -goog.exportProperty( - ol.View.prototype, - 'getZoomForResolution', - ol.View.prototype.getZoomForResolution); - -goog.exportProperty( - ol.View.prototype, - 'getResolutionForZoom', - ol.View.prototype.getResolutionForZoom); - -goog.exportProperty( - ol.View.prototype, - 'fit', - ol.View.prototype.fit); - -goog.exportProperty( - ol.View.prototype, - 'centerOn', - ol.View.prototype.centerOn); - -goog.exportProperty( - ol.View.prototype, - 'rotate', - ol.View.prototype.rotate); - -goog.exportProperty( - ol.View.prototype, - 'setCenter', - ol.View.prototype.setCenter); - -goog.exportProperty( - ol.View.prototype, - 'setResolution', - ol.View.prototype.setResolution); - -goog.exportProperty( - ol.View.prototype, - 'setRotation', - ol.View.prototype.setRotation); - -goog.exportProperty( - ol.View.prototype, - 'setZoom', - ol.View.prototype.setZoom); - -goog.exportSymbol( - 'ol.xml.getAllTextContent', - ol.xml.getAllTextContent, - OPENLAYERS); - -goog.exportSymbol( - 'ol.xml.parse', - ol.xml.parse, - OPENLAYERS); - -goog.exportProperty( - ol.webgl.Context.prototype, - 'getGL', - ol.webgl.Context.prototype.getGL); - -goog.exportProperty( - ol.webgl.Context.prototype, - 'useProgram', - ol.webgl.Context.prototype.useProgram); - -goog.exportSymbol( - 'ol.tilegrid.TileGrid', - ol.tilegrid.TileGrid, - OPENLAYERS); - -goog.exportProperty( - ol.tilegrid.TileGrid.prototype, - 'forEachTileCoord', - ol.tilegrid.TileGrid.prototype.forEachTileCoord); - -goog.exportProperty( - ol.tilegrid.TileGrid.prototype, - 'getMaxZoom', - ol.tilegrid.TileGrid.prototype.getMaxZoom); - -goog.exportProperty( - ol.tilegrid.TileGrid.prototype, - 'getMinZoom', - ol.tilegrid.TileGrid.prototype.getMinZoom); - -goog.exportProperty( - ol.tilegrid.TileGrid.prototype, - 'getOrigin', - ol.tilegrid.TileGrid.prototype.getOrigin); - -goog.exportProperty( - ol.tilegrid.TileGrid.prototype, - 'getResolution', - ol.tilegrid.TileGrid.prototype.getResolution); - -goog.exportProperty( - ol.tilegrid.TileGrid.prototype, - 'getResolutions', - ol.tilegrid.TileGrid.prototype.getResolutions); - -goog.exportProperty( - ol.tilegrid.TileGrid.prototype, - 'getTileCoordExtent', - ol.tilegrid.TileGrid.prototype.getTileCoordExtent); - -goog.exportProperty( - ol.tilegrid.TileGrid.prototype, - 'getTileCoordForCoordAndResolution', - ol.tilegrid.TileGrid.prototype.getTileCoordForCoordAndResolution); - -goog.exportProperty( - ol.tilegrid.TileGrid.prototype, - 'getTileCoordForCoordAndZ', - ol.tilegrid.TileGrid.prototype.getTileCoordForCoordAndZ); - -goog.exportProperty( - ol.tilegrid.TileGrid.prototype, - 'getTileSize', - ol.tilegrid.TileGrid.prototype.getTileSize); - -goog.exportProperty( - ol.tilegrid.TileGrid.prototype, - 'getZForResolution', - ol.tilegrid.TileGrid.prototype.getZForResolution); - -goog.exportSymbol( - 'ol.tilegrid.WMTS', - ol.tilegrid.WMTS, - OPENLAYERS); - -goog.exportProperty( - ol.tilegrid.WMTS.prototype, - 'getMatrixIds', - ol.tilegrid.WMTS.prototype.getMatrixIds); - -goog.exportSymbol( - 'ol.tilegrid.WMTS.createFromCapabilitiesMatrixSet', - ol.tilegrid.WMTS.createFromCapabilitiesMatrixSet, - OPENLAYERS); - -goog.exportSymbol( - 'ol.style.AtlasManager', - ol.style.AtlasManager, - OPENLAYERS); - -goog.exportSymbol( - 'ol.style.Circle', - ol.style.Circle, - OPENLAYERS); - -goog.exportProperty( - ol.style.Circle.prototype, - 'setRadius', - ol.style.Circle.prototype.setRadius); - -goog.exportSymbol( - 'ol.style.Fill', - ol.style.Fill, - OPENLAYERS); - -goog.exportProperty( - ol.style.Fill.prototype, - 'clone', - ol.style.Fill.prototype.clone); - -goog.exportProperty( - ol.style.Fill.prototype, - 'getColor', - ol.style.Fill.prototype.getColor); - -goog.exportProperty( - ol.style.Fill.prototype, - 'setColor', - ol.style.Fill.prototype.setColor); - -goog.exportSymbol( - 'ol.style.Icon', - ol.style.Icon, - OPENLAYERS); - -goog.exportProperty( - ol.style.Icon.prototype, - 'clone', - ol.style.Icon.prototype.clone); - -goog.exportProperty( - ol.style.Icon.prototype, - 'getAnchor', - ol.style.Icon.prototype.getAnchor); - -goog.exportProperty( - ol.style.Icon.prototype, - 'getColor', - ol.style.Icon.prototype.getColor); - -goog.exportProperty( - ol.style.Icon.prototype, - 'getImage', - ol.style.Icon.prototype.getImage); - -goog.exportProperty( - ol.style.Icon.prototype, - 'getOrigin', - ol.style.Icon.prototype.getOrigin); - -goog.exportProperty( - ol.style.Icon.prototype, - 'getSrc', - ol.style.Icon.prototype.getSrc); - -goog.exportProperty( - ol.style.Icon.prototype, - 'getSize', - ol.style.Icon.prototype.getSize); - -goog.exportProperty( - ol.style.Icon.prototype, - 'load', - ol.style.Icon.prototype.load); - -goog.exportSymbol( - 'ol.style.Image', - ol.style.Image, - OPENLAYERS); - -goog.exportProperty( - ol.style.Image.prototype, - 'getOpacity', - ol.style.Image.prototype.getOpacity); - -goog.exportProperty( - ol.style.Image.prototype, - 'getRotateWithView', - ol.style.Image.prototype.getRotateWithView); - -goog.exportProperty( - ol.style.Image.prototype, - 'getRotation', - ol.style.Image.prototype.getRotation); - -goog.exportProperty( - ol.style.Image.prototype, - 'getScale', - ol.style.Image.prototype.getScale); - -goog.exportProperty( - ol.style.Image.prototype, - 'getSnapToPixel', - ol.style.Image.prototype.getSnapToPixel); - -goog.exportProperty( - ol.style.Image.prototype, - 'setOpacity', - ol.style.Image.prototype.setOpacity); - -goog.exportProperty( - ol.style.Image.prototype, - 'setRotation', - ol.style.Image.prototype.setRotation); - -goog.exportProperty( - ol.style.Image.prototype, - 'setScale', - ol.style.Image.prototype.setScale); - -goog.exportSymbol( - 'ol.style.RegularShape', - ol.style.RegularShape, - OPENLAYERS); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'clone', - ol.style.RegularShape.prototype.clone); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'getAnchor', - ol.style.RegularShape.prototype.getAnchor); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'getAngle', - ol.style.RegularShape.prototype.getAngle); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'getFill', - ol.style.RegularShape.prototype.getFill); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'getImage', - ol.style.RegularShape.prototype.getImage); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'getOrigin', - ol.style.RegularShape.prototype.getOrigin); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'getPoints', - ol.style.RegularShape.prototype.getPoints); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'getRadius', - ol.style.RegularShape.prototype.getRadius); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'getRadius2', - ol.style.RegularShape.prototype.getRadius2); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'getSize', - ol.style.RegularShape.prototype.getSize); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'getStroke', - ol.style.RegularShape.prototype.getStroke); - -goog.exportSymbol( - 'ol.style.Stroke', - ol.style.Stroke, - OPENLAYERS); - -goog.exportProperty( - ol.style.Stroke.prototype, - 'clone', - ol.style.Stroke.prototype.clone); - -goog.exportProperty( - ol.style.Stroke.prototype, - 'getColor', - ol.style.Stroke.prototype.getColor); - -goog.exportProperty( - ol.style.Stroke.prototype, - 'getLineCap', - ol.style.Stroke.prototype.getLineCap); - -goog.exportProperty( - ol.style.Stroke.prototype, - 'getLineDash', - ol.style.Stroke.prototype.getLineDash); - -goog.exportProperty( - ol.style.Stroke.prototype, - 'getLineDashOffset', - ol.style.Stroke.prototype.getLineDashOffset); - -goog.exportProperty( - ol.style.Stroke.prototype, - 'getLineJoin', - ol.style.Stroke.prototype.getLineJoin); - -goog.exportProperty( - ol.style.Stroke.prototype, - 'getMiterLimit', - ol.style.Stroke.prototype.getMiterLimit); - -goog.exportProperty( - ol.style.Stroke.prototype, - 'getWidth', - ol.style.Stroke.prototype.getWidth); - -goog.exportProperty( - ol.style.Stroke.prototype, - 'setColor', - ol.style.Stroke.prototype.setColor); - -goog.exportProperty( - ol.style.Stroke.prototype, - 'setLineCap', - ol.style.Stroke.prototype.setLineCap); - -goog.exportProperty( - ol.style.Stroke.prototype, - 'setLineDash', - ol.style.Stroke.prototype.setLineDash); - -goog.exportProperty( - ol.style.Stroke.prototype, - 'setLineDashOffset', - ol.style.Stroke.prototype.setLineDashOffset); - -goog.exportProperty( - ol.style.Stroke.prototype, - 'setLineJoin', - ol.style.Stroke.prototype.setLineJoin); - -goog.exportProperty( - ol.style.Stroke.prototype, - 'setMiterLimit', - ol.style.Stroke.prototype.setMiterLimit); - -goog.exportProperty( - ol.style.Stroke.prototype, - 'setWidth', - ol.style.Stroke.prototype.setWidth); - -goog.exportSymbol( - 'ol.style.Style', - ol.style.Style, - OPENLAYERS); - -goog.exportProperty( - ol.style.Style.prototype, - 'clone', - ol.style.Style.prototype.clone); - -goog.exportProperty( - ol.style.Style.prototype, - 'getRenderer', - ol.style.Style.prototype.getRenderer); - -goog.exportProperty( - ol.style.Style.prototype, - 'setRenderer', - ol.style.Style.prototype.setRenderer); - -goog.exportProperty( - ol.style.Style.prototype, - 'getGeometry', - ol.style.Style.prototype.getGeometry); - -goog.exportProperty( - ol.style.Style.prototype, - 'getGeometryFunction', - ol.style.Style.prototype.getGeometryFunction); - -goog.exportProperty( - ol.style.Style.prototype, - 'getFill', - ol.style.Style.prototype.getFill); - -goog.exportProperty( - ol.style.Style.prototype, - 'setFill', - ol.style.Style.prototype.setFill); - -goog.exportProperty( - ol.style.Style.prototype, - 'getImage', - ol.style.Style.prototype.getImage); - -goog.exportProperty( - ol.style.Style.prototype, - 'setImage', - ol.style.Style.prototype.setImage); - -goog.exportProperty( - ol.style.Style.prototype, - 'getStroke', - ol.style.Style.prototype.getStroke); - -goog.exportProperty( - ol.style.Style.prototype, - 'setStroke', - ol.style.Style.prototype.setStroke); - -goog.exportProperty( - ol.style.Style.prototype, - 'getText', - ol.style.Style.prototype.getText); - -goog.exportProperty( - ol.style.Style.prototype, - 'setText', - ol.style.Style.prototype.setText); - -goog.exportProperty( - ol.style.Style.prototype, - 'getZIndex', - ol.style.Style.prototype.getZIndex); - -goog.exportProperty( - ol.style.Style.prototype, - 'setGeometry', - ol.style.Style.prototype.setGeometry); - -goog.exportProperty( - ol.style.Style.prototype, - 'setZIndex', - ol.style.Style.prototype.setZIndex); - -goog.exportSymbol( - 'ol.style.Text', - ol.style.Text, - OPENLAYERS); - -goog.exportProperty( - ol.style.Text.prototype, - 'clone', - ol.style.Text.prototype.clone); - -goog.exportProperty( - ol.style.Text.prototype, - 'getExceedLength', - ol.style.Text.prototype.getExceedLength); - -goog.exportProperty( - ol.style.Text.prototype, - 'getFont', - ol.style.Text.prototype.getFont); - -goog.exportProperty( - ol.style.Text.prototype, - 'getMaxAngle', - ol.style.Text.prototype.getMaxAngle); - -goog.exportProperty( - ol.style.Text.prototype, - 'getPlacement', - ol.style.Text.prototype.getPlacement); - -goog.exportProperty( - ol.style.Text.prototype, - 'getOffsetX', - ol.style.Text.prototype.getOffsetX); - -goog.exportProperty( - ol.style.Text.prototype, - 'getOffsetY', - ol.style.Text.prototype.getOffsetY); - -goog.exportProperty( - ol.style.Text.prototype, - 'getFill', - ol.style.Text.prototype.getFill); - -goog.exportProperty( - ol.style.Text.prototype, - 'getRotateWithView', - ol.style.Text.prototype.getRotateWithView); - -goog.exportProperty( - ol.style.Text.prototype, - 'getRotation', - ol.style.Text.prototype.getRotation); - -goog.exportProperty( - ol.style.Text.prototype, - 'getScale', - ol.style.Text.prototype.getScale); - -goog.exportProperty( - ol.style.Text.prototype, - 'getStroke', - ol.style.Text.prototype.getStroke); - -goog.exportProperty( - ol.style.Text.prototype, - 'getText', - ol.style.Text.prototype.getText); - -goog.exportProperty( - ol.style.Text.prototype, - 'getTextAlign', - ol.style.Text.prototype.getTextAlign); - -goog.exportProperty( - ol.style.Text.prototype, - 'getTextBaseline', - ol.style.Text.prototype.getTextBaseline); - -goog.exportProperty( - ol.style.Text.prototype, - 'setExceedLength', - ol.style.Text.prototype.setExceedLength); - -goog.exportProperty( - ol.style.Text.prototype, - 'setFont', - ol.style.Text.prototype.setFont); - -goog.exportProperty( - ol.style.Text.prototype, - 'setMaxAngle', - ol.style.Text.prototype.setMaxAngle); - -goog.exportProperty( - ol.style.Text.prototype, - 'setOffsetX', - ol.style.Text.prototype.setOffsetX); - -goog.exportProperty( - ol.style.Text.prototype, - 'setOffsetY', - ol.style.Text.prototype.setOffsetY); - -goog.exportProperty( - ol.style.Text.prototype, - 'setPlacement', - ol.style.Text.prototype.setPlacement); - -goog.exportProperty( - ol.style.Text.prototype, - 'setFill', - ol.style.Text.prototype.setFill); - -goog.exportProperty( - ol.style.Text.prototype, - 'setRotation', - ol.style.Text.prototype.setRotation); - -goog.exportProperty( - ol.style.Text.prototype, - 'setScale', - ol.style.Text.prototype.setScale); - -goog.exportProperty( - ol.style.Text.prototype, - 'setStroke', - ol.style.Text.prototype.setStroke); - -goog.exportProperty( - ol.style.Text.prototype, - 'setText', - ol.style.Text.prototype.setText); - -goog.exportProperty( - ol.style.Text.prototype, - 'setTextAlign', - ol.style.Text.prototype.setTextAlign); - -goog.exportProperty( - ol.style.Text.prototype, - 'setTextBaseline', - ol.style.Text.prototype.setTextBaseline); - -goog.exportSymbol( - 'ol.source.BingMaps', - ol.source.BingMaps, - OPENLAYERS); - -goog.exportSymbol( - 'ol.source.BingMaps.TOS_ATTRIBUTION', - ol.source.BingMaps.TOS_ATTRIBUTION, - OPENLAYERS); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'getApiKey', - ol.source.BingMaps.prototype.getApiKey); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'getImagerySet', - ol.source.BingMaps.prototype.getImagerySet); - -goog.exportSymbol( - 'ol.source.CartoDB', - ol.source.CartoDB, - OPENLAYERS); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'getConfig', - ol.source.CartoDB.prototype.getConfig); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'updateConfig', - ol.source.CartoDB.prototype.updateConfig); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'setConfig', - ol.source.CartoDB.prototype.setConfig); - -goog.exportSymbol( - 'ol.source.Cluster', - ol.source.Cluster, - OPENLAYERS); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getDistance', - ol.source.Cluster.prototype.getDistance); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getSource', - ol.source.Cluster.prototype.getSource); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'setDistance', - ol.source.Cluster.prototype.setDistance); - -goog.exportSymbol( - 'ol.source.Image', - ol.source.Image, - OPENLAYERS); - -goog.exportProperty( - ol.source.Image.Event.prototype, - 'image', - ol.source.Image.Event.prototype.image); - -goog.exportSymbol( - 'ol.source.ImageArcGISRest', - ol.source.ImageArcGISRest, - OPENLAYERS); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'getParams', - ol.source.ImageArcGISRest.prototype.getParams); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'getImageLoadFunction', - ol.source.ImageArcGISRest.prototype.getImageLoadFunction); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'getUrl', - ol.source.ImageArcGISRest.prototype.getUrl); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'setImageLoadFunction', - ol.source.ImageArcGISRest.prototype.setImageLoadFunction); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'setUrl', - ol.source.ImageArcGISRest.prototype.setUrl); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'updateParams', - ol.source.ImageArcGISRest.prototype.updateParams); - -goog.exportSymbol( - 'ol.source.ImageCanvas', - ol.source.ImageCanvas, - OPENLAYERS); - -goog.exportSymbol( - 'ol.source.ImageMapGuide', - ol.source.ImageMapGuide, - OPENLAYERS); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'getParams', - ol.source.ImageMapGuide.prototype.getParams); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'getImageLoadFunction', - ol.source.ImageMapGuide.prototype.getImageLoadFunction); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'updateParams', - ol.source.ImageMapGuide.prototype.updateParams); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'setImageLoadFunction', - ol.source.ImageMapGuide.prototype.setImageLoadFunction); - -goog.exportSymbol( - 'ol.source.ImageStatic', - ol.source.ImageStatic, - OPENLAYERS); - -goog.exportSymbol( - 'ol.source.ImageVector', - ol.source.ImageVector, - OPENLAYERS); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'getSource', - ol.source.ImageVector.prototype.getSource); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'getStyle', - ol.source.ImageVector.prototype.getStyle); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'getStyleFunction', - ol.source.ImageVector.prototype.getStyleFunction); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'setStyle', - ol.source.ImageVector.prototype.setStyle); - -goog.exportSymbol( - 'ol.source.ImageWMS', - ol.source.ImageWMS, - OPENLAYERS); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'getGetFeatureInfoUrl', - ol.source.ImageWMS.prototype.getGetFeatureInfoUrl); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'getParams', - ol.source.ImageWMS.prototype.getParams); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'getImageLoadFunction', - ol.source.ImageWMS.prototype.getImageLoadFunction); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'getUrl', - ol.source.ImageWMS.prototype.getUrl); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'setImageLoadFunction', - ol.source.ImageWMS.prototype.setImageLoadFunction); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'setUrl', - ol.source.ImageWMS.prototype.setUrl); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'updateParams', - ol.source.ImageWMS.prototype.updateParams); - -goog.exportSymbol( - 'ol.source.OSM', - ol.source.OSM, - OPENLAYERS); - -goog.exportSymbol( - 'ol.source.OSM.ATTRIBUTION', - ol.source.OSM.ATTRIBUTION, - OPENLAYERS); - -goog.exportSymbol( - 'ol.source.Raster', - ol.source.Raster, - OPENLAYERS); - -goog.exportProperty( - ol.source.Raster.prototype, - 'setOperation', - ol.source.Raster.prototype.setOperation); - -goog.exportProperty( - ol.source.Raster.Event.prototype, - 'extent', - ol.source.Raster.Event.prototype.extent); - -goog.exportProperty( - ol.source.Raster.Event.prototype, - 'resolution', - ol.source.Raster.Event.prototype.resolution); - -goog.exportProperty( - ol.source.Raster.Event.prototype, - 'data', - ol.source.Raster.Event.prototype.data); - -goog.exportSymbol( - 'ol.source.Source', - ol.source.Source, - OPENLAYERS); - -goog.exportProperty( - ol.source.Source.prototype, - 'getAttributions', - ol.source.Source.prototype.getAttributions); - -goog.exportProperty( - ol.source.Source.prototype, - 'getLogo', - ol.source.Source.prototype.getLogo); - -goog.exportProperty( - ol.source.Source.prototype, - 'getProjection', - ol.source.Source.prototype.getProjection); - -goog.exportProperty( - ol.source.Source.prototype, - 'getState', - ol.source.Source.prototype.getState); - -goog.exportProperty( - ol.source.Source.prototype, - 'refresh', - ol.source.Source.prototype.refresh); - -goog.exportProperty( - ol.source.Source.prototype, - 'setAttributions', - ol.source.Source.prototype.setAttributions); - -goog.exportSymbol( - 'ol.source.Stamen', - ol.source.Stamen, - OPENLAYERS); - -goog.exportSymbol( - 'ol.source.Tile', - ol.source.Tile, - OPENLAYERS); - -goog.exportProperty( - ol.source.Tile.prototype, - 'getTileGrid', - ol.source.Tile.prototype.getTileGrid); - -goog.exportProperty( - ol.source.Tile.Event.prototype, - 'tile', - ol.source.Tile.Event.prototype.tile); - -goog.exportSymbol( - 'ol.source.TileArcGISRest', - ol.source.TileArcGISRest, - OPENLAYERS); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'getParams', - ol.source.TileArcGISRest.prototype.getParams); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'updateParams', - ol.source.TileArcGISRest.prototype.updateParams); - -goog.exportSymbol( - 'ol.source.TileDebug', - ol.source.TileDebug, - OPENLAYERS); - -goog.exportSymbol( - 'ol.source.TileImage', - ol.source.TileImage, - OPENLAYERS); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'setRenderReprojectionEdges', - ol.source.TileImage.prototype.setRenderReprojectionEdges); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'setTileGridForProjection', - ol.source.TileImage.prototype.setTileGridForProjection); - -goog.exportSymbol( - 'ol.source.TileJSON', - ol.source.TileJSON, - OPENLAYERS); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'getTileJSON', - ol.source.TileJSON.prototype.getTileJSON); - -goog.exportSymbol( - 'ol.source.TileUTFGrid', - ol.source.TileUTFGrid, - OPENLAYERS); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'getTemplate', - ol.source.TileUTFGrid.prototype.getTemplate); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'forDataAtCoordinateAndResolution', - ol.source.TileUTFGrid.prototype.forDataAtCoordinateAndResolution); - -goog.exportSymbol( - 'ol.source.TileWMS', - ol.source.TileWMS, - OPENLAYERS); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'getGetFeatureInfoUrl', - ol.source.TileWMS.prototype.getGetFeatureInfoUrl); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'getParams', - ol.source.TileWMS.prototype.getParams); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'updateParams', - ol.source.TileWMS.prototype.updateParams); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'getTileLoadFunction', - ol.source.UrlTile.prototype.getTileLoadFunction); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'getTileUrlFunction', - ol.source.UrlTile.prototype.getTileUrlFunction); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'getUrls', - ol.source.UrlTile.prototype.getUrls); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'setTileLoadFunction', - ol.source.UrlTile.prototype.setTileLoadFunction); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'setTileUrlFunction', - ol.source.UrlTile.prototype.setTileUrlFunction); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'setUrl', - ol.source.UrlTile.prototype.setUrl); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'setUrls', - ol.source.UrlTile.prototype.setUrls); - -goog.exportSymbol( - 'ol.source.Vector', - ol.source.Vector, - OPENLAYERS); - -goog.exportProperty( - ol.source.Vector.prototype, - 'addFeature', - ol.source.Vector.prototype.addFeature); - -goog.exportProperty( - ol.source.Vector.prototype, - 'addFeatures', - ol.source.Vector.prototype.addFeatures); - -goog.exportProperty( - ol.source.Vector.prototype, - 'clear', - ol.source.Vector.prototype.clear); - -goog.exportProperty( - ol.source.Vector.prototype, - 'forEachFeature', - ol.source.Vector.prototype.forEachFeature); - -goog.exportProperty( - ol.source.Vector.prototype, - 'forEachFeatureInExtent', - ol.source.Vector.prototype.forEachFeatureInExtent); - -goog.exportProperty( - ol.source.Vector.prototype, - 'forEachFeatureIntersectingExtent', - ol.source.Vector.prototype.forEachFeatureIntersectingExtent); - -goog.exportProperty( - ol.source.Vector.prototype, - 'getFeaturesCollection', - ol.source.Vector.prototype.getFeaturesCollection); - -goog.exportProperty( - ol.source.Vector.prototype, - 'getFeatures', - ol.source.Vector.prototype.getFeatures); - -goog.exportProperty( - ol.source.Vector.prototype, - 'getFeaturesAtCoordinate', - ol.source.Vector.prototype.getFeaturesAtCoordinate); - -goog.exportProperty( - ol.source.Vector.prototype, - 'getFeaturesInExtent', - ol.source.Vector.prototype.getFeaturesInExtent); - -goog.exportProperty( - ol.source.Vector.prototype, - 'getClosestFeatureToCoordinate', - ol.source.Vector.prototype.getClosestFeatureToCoordinate); - -goog.exportProperty( - ol.source.Vector.prototype, - 'getExtent', - ol.source.Vector.prototype.getExtent); - -goog.exportProperty( - ol.source.Vector.prototype, - 'getFeatureById', - ol.source.Vector.prototype.getFeatureById); - -goog.exportProperty( - ol.source.Vector.prototype, - 'getFormat', - ol.source.Vector.prototype.getFormat); - -goog.exportProperty( - ol.source.Vector.prototype, - 'getUrl', - ol.source.Vector.prototype.getUrl); - -goog.exportProperty( - ol.source.Vector.prototype, - 'removeFeature', - ol.source.Vector.prototype.removeFeature); - -goog.exportProperty( - ol.source.Vector.prototype, - 'setLoader', - ol.source.Vector.prototype.setLoader); - -goog.exportProperty( - ol.source.Vector.Event.prototype, - 'feature', - ol.source.Vector.Event.prototype.feature); - -goog.exportSymbol( - 'ol.source.VectorTile', - ol.source.VectorTile, - OPENLAYERS); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'clear', - ol.source.VectorTile.prototype.clear); - -goog.exportSymbol( - 'ol.source.WMTS', - ol.source.WMTS, - OPENLAYERS); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getDimensions', - ol.source.WMTS.prototype.getDimensions); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getFormat', - ol.source.WMTS.prototype.getFormat); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getLayer', - ol.source.WMTS.prototype.getLayer); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getMatrixSet', - ol.source.WMTS.prototype.getMatrixSet); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getRequestEncoding', - ol.source.WMTS.prototype.getRequestEncoding); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getStyle', - ol.source.WMTS.prototype.getStyle); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getVersion', - ol.source.WMTS.prototype.getVersion); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'updateDimensions', - ol.source.WMTS.prototype.updateDimensions); - -goog.exportSymbol( - 'ol.source.WMTS.optionsFromCapabilities', - ol.source.WMTS.optionsFromCapabilities, - OPENLAYERS); - -goog.exportSymbol( - 'ol.source.XYZ', - ol.source.XYZ, - OPENLAYERS); - -goog.exportSymbol( - 'ol.source.Zoomify', - ol.source.Zoomify, - OPENLAYERS); - -goog.exportSymbol( - 'ol.renderer.webgl.ImageLayer', - ol.renderer.webgl.ImageLayer, - OPENLAYERS); - -goog.exportSymbol( - 'ol.renderer.webgl.Map', - ol.renderer.webgl.Map, - OPENLAYERS); - -goog.exportSymbol( - 'ol.renderer.webgl.TileLayer', - ol.renderer.webgl.TileLayer, - OPENLAYERS); - -goog.exportSymbol( - 'ol.renderer.webgl.VectorLayer', - ol.renderer.webgl.VectorLayer, - OPENLAYERS); - -goog.exportSymbol( - 'ol.renderer.canvas.ImageLayer', - ol.renderer.canvas.ImageLayer, - OPENLAYERS); - -goog.exportSymbol( - 'ol.renderer.canvas.Map', - ol.renderer.canvas.Map, - OPENLAYERS); - -goog.exportSymbol( - 'ol.renderer.canvas.TileLayer', - ol.renderer.canvas.TileLayer, - OPENLAYERS); - -goog.exportSymbol( - 'ol.renderer.canvas.VectorLayer', - ol.renderer.canvas.VectorLayer, - OPENLAYERS); - -goog.exportSymbol( - 'ol.renderer.canvas.VectorTileLayer', - ol.renderer.canvas.VectorTileLayer, - OPENLAYERS); - -goog.exportProperty( - ol.render.Event.prototype, - 'vectorContext', - ol.render.Event.prototype.vectorContext); - -goog.exportProperty( - ol.render.Event.prototype, - 'frameState', - ol.render.Event.prototype.frameState); - -goog.exportProperty( - ol.render.Event.prototype, - 'context', - ol.render.Event.prototype.context); - -goog.exportProperty( - ol.render.Event.prototype, - 'glContext', - ol.render.Event.prototype.glContext); - -goog.exportProperty( - ol.render.Feature.prototype, - 'get', - ol.render.Feature.prototype.get); - -goog.exportProperty( - ol.render.Feature.prototype, - 'getExtent', - ol.render.Feature.prototype.getExtent); - -goog.exportProperty( - ol.render.Feature.prototype, - 'getId', - ol.render.Feature.prototype.getId); - -goog.exportProperty( - ol.render.Feature.prototype, - 'getGeometry', - ol.render.Feature.prototype.getGeometry); - -goog.exportProperty( - ol.render.Feature.prototype, - 'getProperties', - ol.render.Feature.prototype.getProperties); - -goog.exportProperty( - ol.render.Feature.prototype, - 'getType', - ol.render.Feature.prototype.getType); - -goog.exportSymbol( - 'ol.render.VectorContext', - ol.render.VectorContext, - OPENLAYERS); - -goog.exportProperty( - ol.render.webgl.Immediate.prototype, - 'setStyle', - ol.render.webgl.Immediate.prototype.setStyle); - -goog.exportProperty( - ol.render.webgl.Immediate.prototype, - 'drawGeometry', - ol.render.webgl.Immediate.prototype.drawGeometry); - -goog.exportProperty( - ol.render.webgl.Immediate.prototype, - 'drawFeature', - ol.render.webgl.Immediate.prototype.drawFeature); - -goog.exportProperty( - ol.render.canvas.Immediate.prototype, - 'drawCircle', - ol.render.canvas.Immediate.prototype.drawCircle); - -goog.exportProperty( - ol.render.canvas.Immediate.prototype, - 'setStyle', - ol.render.canvas.Immediate.prototype.setStyle); - -goog.exportProperty( - ol.render.canvas.Immediate.prototype, - 'drawGeometry', - ol.render.canvas.Immediate.prototype.drawGeometry); - -goog.exportProperty( - ol.render.canvas.Immediate.prototype, - 'drawFeature', - ol.render.canvas.Immediate.prototype.drawFeature); - -goog.exportSymbol( - 'ol.proj.common.add', - ol.proj.common.add, - OPENLAYERS); - -goog.exportSymbol( - 'ol.proj.Projection', - ol.proj.Projection, - OPENLAYERS); - -goog.exportProperty( - ol.proj.Projection.prototype, - 'getCode', - ol.proj.Projection.prototype.getCode); - -goog.exportProperty( - ol.proj.Projection.prototype, - 'getExtent', - ol.proj.Projection.prototype.getExtent); - -goog.exportProperty( - ol.proj.Projection.prototype, - 'getUnits', - ol.proj.Projection.prototype.getUnits); - -goog.exportProperty( - ol.proj.Projection.prototype, - 'getMetersPerUnit', - ol.proj.Projection.prototype.getMetersPerUnit); - -goog.exportProperty( - ol.proj.Projection.prototype, - 'getWorldExtent', - ol.proj.Projection.prototype.getWorldExtent); - -goog.exportProperty( - ol.proj.Projection.prototype, - 'isGlobal', - ol.proj.Projection.prototype.isGlobal); - -goog.exportProperty( - ol.proj.Projection.prototype, - 'setGlobal', - ol.proj.Projection.prototype.setGlobal); - -goog.exportProperty( - ol.proj.Projection.prototype, - 'setExtent', - ol.proj.Projection.prototype.setExtent); - -goog.exportProperty( - ol.proj.Projection.prototype, - 'setWorldExtent', - ol.proj.Projection.prototype.setWorldExtent); - -goog.exportProperty( - ol.proj.Projection.prototype, - 'setGetPointResolution', - ol.proj.Projection.prototype.setGetPointResolution); - -goog.exportSymbol( - 'ol.proj.Units.METERS_PER_UNIT', - ol.proj.Units.METERS_PER_UNIT, - OPENLAYERS); - -goog.exportSymbol( - 'ol.layer.Base', - ol.layer.Base, - OPENLAYERS); - -goog.exportProperty( - ol.layer.Base.prototype, - 'getExtent', - ol.layer.Base.prototype.getExtent); - -goog.exportProperty( - ol.layer.Base.prototype, - 'getMaxResolution', - ol.layer.Base.prototype.getMaxResolution); - -goog.exportProperty( - ol.layer.Base.prototype, - 'getMinResolution', - ol.layer.Base.prototype.getMinResolution); - -goog.exportProperty( - ol.layer.Base.prototype, - 'getOpacity', - ol.layer.Base.prototype.getOpacity); - -goog.exportProperty( - ol.layer.Base.prototype, - 'getVisible', - ol.layer.Base.prototype.getVisible); - -goog.exportProperty( - ol.layer.Base.prototype, - 'getZIndex', - ol.layer.Base.prototype.getZIndex); - -goog.exportProperty( - ol.layer.Base.prototype, - 'setExtent', - ol.layer.Base.prototype.setExtent); - -goog.exportProperty( - ol.layer.Base.prototype, - 'setMaxResolution', - ol.layer.Base.prototype.setMaxResolution); - -goog.exportProperty( - ol.layer.Base.prototype, - 'setMinResolution', - ol.layer.Base.prototype.setMinResolution); - -goog.exportProperty( - ol.layer.Base.prototype, - 'setOpacity', - ol.layer.Base.prototype.setOpacity); - -goog.exportProperty( - ol.layer.Base.prototype, - 'setVisible', - ol.layer.Base.prototype.setVisible); - -goog.exportProperty( - ol.layer.Base.prototype, - 'setZIndex', - ol.layer.Base.prototype.setZIndex); - -goog.exportSymbol( - 'ol.layer.Group', - ol.layer.Group, - OPENLAYERS); - -goog.exportProperty( - ol.layer.Group.prototype, - 'getLayers', - ol.layer.Group.prototype.getLayers); - -goog.exportProperty( - ol.layer.Group.prototype, - 'setLayers', - ol.layer.Group.prototype.setLayers); - -goog.exportSymbol( - 'ol.layer.Heatmap', - ol.layer.Heatmap, - OPENLAYERS); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'getBlur', - ol.layer.Heatmap.prototype.getBlur); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'getGradient', - ol.layer.Heatmap.prototype.getGradient); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'getRadius', - ol.layer.Heatmap.prototype.getRadius); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'setBlur', - ol.layer.Heatmap.prototype.setBlur); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'setGradient', - ol.layer.Heatmap.prototype.setGradient); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'setRadius', - ol.layer.Heatmap.prototype.setRadius); - -goog.exportSymbol( - 'ol.layer.Image', - ol.layer.Image, - OPENLAYERS); - -goog.exportProperty( - ol.layer.Image.prototype, - 'getSource', - ol.layer.Image.prototype.getSource); - -goog.exportSymbol( - 'ol.layer.Layer', - ol.layer.Layer, - OPENLAYERS); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'getSource', - ol.layer.Layer.prototype.getSource); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'setMap', - ol.layer.Layer.prototype.setMap); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'setSource', - ol.layer.Layer.prototype.setSource); - -goog.exportSymbol( - 'ol.layer.Tile', - ol.layer.Tile, - OPENLAYERS); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'getPreload', - ol.layer.Tile.prototype.getPreload); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'getSource', - ol.layer.Tile.prototype.getSource); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'setPreload', - ol.layer.Tile.prototype.setPreload); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'getUseInterimTilesOnError', - ol.layer.Tile.prototype.getUseInterimTilesOnError); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'setUseInterimTilesOnError', - ol.layer.Tile.prototype.setUseInterimTilesOnError); - -goog.exportSymbol( - 'ol.layer.Vector', - ol.layer.Vector, - OPENLAYERS); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'getSource', - ol.layer.Vector.prototype.getSource); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'getStyle', - ol.layer.Vector.prototype.getStyle); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'getStyleFunction', - ol.layer.Vector.prototype.getStyleFunction); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'setStyle', - ol.layer.Vector.prototype.setStyle); - -goog.exportSymbol( - 'ol.layer.VectorTile', - ol.layer.VectorTile, - OPENLAYERS); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'getPreload', - ol.layer.VectorTile.prototype.getPreload); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'getUseInterimTilesOnError', - ol.layer.VectorTile.prototype.getUseInterimTilesOnError); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'setPreload', - ol.layer.VectorTile.prototype.setPreload); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'setUseInterimTilesOnError', - ol.layer.VectorTile.prototype.setUseInterimTilesOnError); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'getSource', - ol.layer.VectorTile.prototype.getSource); - -goog.exportSymbol( - 'ol.interaction.DoubleClickZoom', - ol.interaction.DoubleClickZoom, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.DoubleClickZoom.handleEvent', - ol.interaction.DoubleClickZoom.handleEvent, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.DragAndDrop', - ol.interaction.DragAndDrop, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.DragAndDrop.handleEvent', - ol.interaction.DragAndDrop.handleEvent, - OPENLAYERS); - -goog.exportProperty( - ol.interaction.DragAndDrop.Event.prototype, - 'features', - ol.interaction.DragAndDrop.Event.prototype.features); - -goog.exportProperty( - ol.interaction.DragAndDrop.Event.prototype, - 'file', - ol.interaction.DragAndDrop.Event.prototype.file); - -goog.exportProperty( - ol.interaction.DragAndDrop.Event.prototype, - 'projection', - ol.interaction.DragAndDrop.Event.prototype.projection); - -goog.exportSymbol( - 'ol.interaction.DragBox', - ol.interaction.DragBox, - OPENLAYERS); - -goog.exportProperty( - ol.interaction.DragBox.prototype, - 'getGeometry', - ol.interaction.DragBox.prototype.getGeometry); - -goog.exportProperty( - ol.interaction.DragBox.Event.prototype, - 'coordinate', - ol.interaction.DragBox.Event.prototype.coordinate); - -goog.exportProperty( - ol.interaction.DragBox.Event.prototype, - 'mapBrowserEvent', - ol.interaction.DragBox.Event.prototype.mapBrowserEvent); - -goog.exportSymbol( - 'ol.interaction.DragPan', - ol.interaction.DragPan, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.DragRotate', - ol.interaction.DragRotate, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.DragRotateAndZoom', - ol.interaction.DragRotateAndZoom, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.DragZoom', - ol.interaction.DragZoom, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.Draw', - ol.interaction.Draw, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.Draw.handleEvent', - ol.interaction.Draw.handleEvent, - OPENLAYERS); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'removeLastPoint', - ol.interaction.Draw.prototype.removeLastPoint); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'finishDrawing', - ol.interaction.Draw.prototype.finishDrawing); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'extend', - ol.interaction.Draw.prototype.extend); - -goog.exportSymbol( - 'ol.interaction.Draw.createRegularPolygon', - ol.interaction.Draw.createRegularPolygon, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.Draw.createBox', - ol.interaction.Draw.createBox, - OPENLAYERS); - -goog.exportProperty( - ol.interaction.Draw.Event.prototype, - 'feature', - ol.interaction.Draw.Event.prototype.feature); - -goog.exportSymbol( - 'ol.interaction.Extent', - ol.interaction.Extent, - OPENLAYERS); - -goog.exportProperty( - ol.interaction.Extent.prototype, - 'getExtent', - ol.interaction.Extent.prototype.getExtent); - -goog.exportProperty( - ol.interaction.Extent.prototype, - 'setExtent', - ol.interaction.Extent.prototype.setExtent); - -goog.exportProperty( - ol.interaction.Extent.Event.prototype, - 'extent', - ol.interaction.Extent.Event.prototype.extent); - -goog.exportSymbol( - 'ol.interaction.Interaction', - ol.interaction.Interaction, - OPENLAYERS); - -goog.exportProperty( - ol.interaction.Interaction.prototype, - 'getActive', - ol.interaction.Interaction.prototype.getActive); - -goog.exportProperty( - ol.interaction.Interaction.prototype, - 'getMap', - ol.interaction.Interaction.prototype.getMap); - -goog.exportProperty( - ol.interaction.Interaction.prototype, - 'setActive', - ol.interaction.Interaction.prototype.setActive); - -goog.exportSymbol( - 'ol.interaction.KeyboardPan', - ol.interaction.KeyboardPan, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.KeyboardPan.handleEvent', - ol.interaction.KeyboardPan.handleEvent, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.KeyboardZoom', - ol.interaction.KeyboardZoom, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.KeyboardZoom.handleEvent', - ol.interaction.KeyboardZoom.handleEvent, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.Modify', - ol.interaction.Modify, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.Modify.handleEvent', - ol.interaction.Modify.handleEvent, - OPENLAYERS); - -goog.exportProperty( - ol.interaction.Modify.prototype, - 'removePoint', - ol.interaction.Modify.prototype.removePoint); - -goog.exportProperty( - ol.interaction.Modify.Event.prototype, - 'features', - ol.interaction.Modify.Event.prototype.features); - -goog.exportProperty( - ol.interaction.Modify.Event.prototype, - 'mapBrowserEvent', - ol.interaction.Modify.Event.prototype.mapBrowserEvent); - -goog.exportSymbol( - 'ol.interaction.MouseWheelZoom', - ol.interaction.MouseWheelZoom, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.MouseWheelZoom.handleEvent', - ol.interaction.MouseWheelZoom.handleEvent, - OPENLAYERS); - -goog.exportProperty( - ol.interaction.MouseWheelZoom.prototype, - 'setMouseAnchor', - ol.interaction.MouseWheelZoom.prototype.setMouseAnchor); - -goog.exportSymbol( - 'ol.interaction.PinchRotate', - ol.interaction.PinchRotate, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.PinchZoom', - ol.interaction.PinchZoom, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.Pointer', - ol.interaction.Pointer, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.Pointer.handleEvent', - ol.interaction.Pointer.handleEvent, - OPENLAYERS); - -goog.exportSymbol( - 'ol.interaction.Select', - ol.interaction.Select, - OPENLAYERS); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'getFeatures', - ol.interaction.Select.prototype.getFeatures); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'getHitTolerance', - ol.interaction.Select.prototype.getHitTolerance); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'getLayer', - ol.interaction.Select.prototype.getLayer); - -goog.exportSymbol( - 'ol.interaction.Select.handleEvent', - ol.interaction.Select.handleEvent, - OPENLAYERS); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'setHitTolerance', - ol.interaction.Select.prototype.setHitTolerance); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'setMap', - ol.interaction.Select.prototype.setMap); - -goog.exportProperty( - ol.interaction.Select.Event.prototype, - 'selected', - ol.interaction.Select.Event.prototype.selected); - -goog.exportProperty( - ol.interaction.Select.Event.prototype, - 'deselected', - ol.interaction.Select.Event.prototype.deselected); - -goog.exportProperty( - ol.interaction.Select.Event.prototype, - 'mapBrowserEvent', - ol.interaction.Select.Event.prototype.mapBrowserEvent); - -goog.exportSymbol( - 'ol.interaction.Snap', - ol.interaction.Snap, - OPENLAYERS); - -goog.exportProperty( - ol.interaction.Snap.prototype, - 'addFeature', - ol.interaction.Snap.prototype.addFeature); - -goog.exportProperty( - ol.interaction.Snap.prototype, - 'removeFeature', - ol.interaction.Snap.prototype.removeFeature); - -goog.exportSymbol( - 'ol.interaction.Translate', - ol.interaction.Translate, - OPENLAYERS); - -goog.exportProperty( - ol.interaction.Translate.prototype, - 'getHitTolerance', - ol.interaction.Translate.prototype.getHitTolerance); - -goog.exportProperty( - ol.interaction.Translate.prototype, - 'setHitTolerance', - ol.interaction.Translate.prototype.setHitTolerance); - -goog.exportProperty( - ol.interaction.Translate.Event.prototype, - 'features', - ol.interaction.Translate.Event.prototype.features); - -goog.exportProperty( - ol.interaction.Translate.Event.prototype, - 'coordinate', - ol.interaction.Translate.Event.prototype.coordinate); - -goog.exportSymbol( - 'ol.geom.Circle', - ol.geom.Circle, - OPENLAYERS); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'clone', - ol.geom.Circle.prototype.clone); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'getCenter', - ol.geom.Circle.prototype.getCenter); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'getRadius', - ol.geom.Circle.prototype.getRadius); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'getType', - ol.geom.Circle.prototype.getType); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'intersectsExtent', - ol.geom.Circle.prototype.intersectsExtent); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'setCenter', - ol.geom.Circle.prototype.setCenter); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'setCenterAndRadius', - ol.geom.Circle.prototype.setCenterAndRadius); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'setRadius', - ol.geom.Circle.prototype.setRadius); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'transform', - ol.geom.Circle.prototype.transform); - -goog.exportSymbol( - 'ol.geom.Geometry', - ol.geom.Geometry, - OPENLAYERS); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'getClosestPoint', - ol.geom.Geometry.prototype.getClosestPoint); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'intersectsCoordinate', - ol.geom.Geometry.prototype.intersectsCoordinate); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'getExtent', - ol.geom.Geometry.prototype.getExtent); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'rotate', - ol.geom.Geometry.prototype.rotate); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'scale', - ol.geom.Geometry.prototype.scale); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'simplify', - ol.geom.Geometry.prototype.simplify); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'transform', - ol.geom.Geometry.prototype.transform); - -goog.exportSymbol( - 'ol.geom.GeometryCollection', - ol.geom.GeometryCollection, - OPENLAYERS); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'clone', - ol.geom.GeometryCollection.prototype.clone); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'getGeometries', - ol.geom.GeometryCollection.prototype.getGeometries); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'getType', - ol.geom.GeometryCollection.prototype.getType); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'intersectsExtent', - ol.geom.GeometryCollection.prototype.intersectsExtent); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'setGeometries', - ol.geom.GeometryCollection.prototype.setGeometries); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'applyTransform', - ol.geom.GeometryCollection.prototype.applyTransform); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'translate', - ol.geom.GeometryCollection.prototype.translate); - -goog.exportSymbol( - 'ol.geom.LinearRing', - ol.geom.LinearRing, - OPENLAYERS); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'clone', - ol.geom.LinearRing.prototype.clone); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'getArea', - ol.geom.LinearRing.prototype.getArea); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'getCoordinates', - ol.geom.LinearRing.prototype.getCoordinates); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'getType', - ol.geom.LinearRing.prototype.getType); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'setCoordinates', - ol.geom.LinearRing.prototype.setCoordinates); - -goog.exportSymbol( - 'ol.geom.LineString', - ol.geom.LineString, - OPENLAYERS); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'appendCoordinate', - ol.geom.LineString.prototype.appendCoordinate); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'clone', - ol.geom.LineString.prototype.clone); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'forEachSegment', - ol.geom.LineString.prototype.forEachSegment); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'getCoordinateAtM', - ol.geom.LineString.prototype.getCoordinateAtM); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'getCoordinates', - ol.geom.LineString.prototype.getCoordinates); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'getCoordinateAt', - ol.geom.LineString.prototype.getCoordinateAt); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'getLength', - ol.geom.LineString.prototype.getLength); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'getType', - ol.geom.LineString.prototype.getType); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'intersectsExtent', - ol.geom.LineString.prototype.intersectsExtent); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'setCoordinates', - ol.geom.LineString.prototype.setCoordinates); - -goog.exportSymbol( - 'ol.geom.MultiLineString', - ol.geom.MultiLineString, - OPENLAYERS); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'appendLineString', - ol.geom.MultiLineString.prototype.appendLineString); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'clone', - ol.geom.MultiLineString.prototype.clone); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'getCoordinateAtM', - ol.geom.MultiLineString.prototype.getCoordinateAtM); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'getCoordinates', - ol.geom.MultiLineString.prototype.getCoordinates); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'getLineString', - ol.geom.MultiLineString.prototype.getLineString); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'getLineStrings', - ol.geom.MultiLineString.prototype.getLineStrings); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'getType', - ol.geom.MultiLineString.prototype.getType); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'intersectsExtent', - ol.geom.MultiLineString.prototype.intersectsExtent); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'setCoordinates', - ol.geom.MultiLineString.prototype.setCoordinates); - -goog.exportSymbol( - 'ol.geom.MultiPoint', - ol.geom.MultiPoint, - OPENLAYERS); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'appendPoint', - ol.geom.MultiPoint.prototype.appendPoint); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'clone', - ol.geom.MultiPoint.prototype.clone); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'getCoordinates', - ol.geom.MultiPoint.prototype.getCoordinates); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'getPoint', - ol.geom.MultiPoint.prototype.getPoint); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'getPoints', - ol.geom.MultiPoint.prototype.getPoints); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'getType', - ol.geom.MultiPoint.prototype.getType); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'intersectsExtent', - ol.geom.MultiPoint.prototype.intersectsExtent); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'setCoordinates', - ol.geom.MultiPoint.prototype.setCoordinates); - -goog.exportSymbol( - 'ol.geom.MultiPolygon', - ol.geom.MultiPolygon, - OPENLAYERS); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'appendPolygon', - ol.geom.MultiPolygon.prototype.appendPolygon); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'clone', - ol.geom.MultiPolygon.prototype.clone); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'getArea', - ol.geom.MultiPolygon.prototype.getArea); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'getCoordinates', - ol.geom.MultiPolygon.prototype.getCoordinates); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'getInteriorPoints', - ol.geom.MultiPolygon.prototype.getInteriorPoints); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'getPolygon', - ol.geom.MultiPolygon.prototype.getPolygon); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'getPolygons', - ol.geom.MultiPolygon.prototype.getPolygons); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'getType', - ol.geom.MultiPolygon.prototype.getType); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'intersectsExtent', - ol.geom.MultiPolygon.prototype.intersectsExtent); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'setCoordinates', - ol.geom.MultiPolygon.prototype.setCoordinates); - -goog.exportSymbol( - 'ol.geom.Point', - ol.geom.Point, - OPENLAYERS); - -goog.exportProperty( - ol.geom.Point.prototype, - 'clone', - ol.geom.Point.prototype.clone); - -goog.exportProperty( - ol.geom.Point.prototype, - 'getCoordinates', - ol.geom.Point.prototype.getCoordinates); - -goog.exportProperty( - ol.geom.Point.prototype, - 'getType', - ol.geom.Point.prototype.getType); - -goog.exportProperty( - ol.geom.Point.prototype, - 'intersectsExtent', - ol.geom.Point.prototype.intersectsExtent); - -goog.exportProperty( - ol.geom.Point.prototype, - 'setCoordinates', - ol.geom.Point.prototype.setCoordinates); - -goog.exportSymbol( - 'ol.geom.Polygon', - ol.geom.Polygon, - OPENLAYERS); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'appendLinearRing', - ol.geom.Polygon.prototype.appendLinearRing); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'clone', - ol.geom.Polygon.prototype.clone); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'getArea', - ol.geom.Polygon.prototype.getArea); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'getCoordinates', - ol.geom.Polygon.prototype.getCoordinates); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'getInteriorPoint', - ol.geom.Polygon.prototype.getInteriorPoint); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'getLinearRingCount', - ol.geom.Polygon.prototype.getLinearRingCount); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'getLinearRing', - ol.geom.Polygon.prototype.getLinearRing); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'getLinearRings', - ol.geom.Polygon.prototype.getLinearRings); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'getType', - ol.geom.Polygon.prototype.getType); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'intersectsExtent', - ol.geom.Polygon.prototype.intersectsExtent); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'setCoordinates', - ol.geom.Polygon.prototype.setCoordinates); - -goog.exportSymbol( - 'ol.geom.Polygon.circular', - ol.geom.Polygon.circular, - OPENLAYERS); - -goog.exportSymbol( - 'ol.geom.Polygon.fromExtent', - ol.geom.Polygon.fromExtent, - OPENLAYERS); - -goog.exportSymbol( - 'ol.geom.Polygon.fromCircle', - ol.geom.Polygon.fromCircle, - OPENLAYERS); - -goog.exportSymbol( - 'ol.geom.SimpleGeometry', - ol.geom.SimpleGeometry, - OPENLAYERS); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'getFirstCoordinate', - ol.geom.SimpleGeometry.prototype.getFirstCoordinate); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'getLastCoordinate', - ol.geom.SimpleGeometry.prototype.getLastCoordinate); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'getLayout', - ol.geom.SimpleGeometry.prototype.getLayout); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'applyTransform', - ol.geom.SimpleGeometry.prototype.applyTransform); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'translate', - ol.geom.SimpleGeometry.prototype.translate); - -goog.exportSymbol( - 'ol.format.EsriJSON', - ol.format.EsriJSON, - OPENLAYERS); - -goog.exportProperty( - ol.format.EsriJSON.prototype, - 'readFeature', - ol.format.EsriJSON.prototype.readFeature); - -goog.exportProperty( - ol.format.EsriJSON.prototype, - 'readFeatures', - ol.format.EsriJSON.prototype.readFeatures); - -goog.exportProperty( - ol.format.EsriJSON.prototype, - 'readGeometry', - ol.format.EsriJSON.prototype.readGeometry); - -goog.exportProperty( - ol.format.EsriJSON.prototype, - 'readProjection', - ol.format.EsriJSON.prototype.readProjection); - -goog.exportProperty( - ol.format.EsriJSON.prototype, - 'writeGeometry', - ol.format.EsriJSON.prototype.writeGeometry); - -goog.exportProperty( - ol.format.EsriJSON.prototype, - 'writeGeometryObject', - ol.format.EsriJSON.prototype.writeGeometryObject); - -goog.exportProperty( - ol.format.EsriJSON.prototype, - 'writeFeature', - ol.format.EsriJSON.prototype.writeFeature); - -goog.exportProperty( - ol.format.EsriJSON.prototype, - 'writeFeatureObject', - ol.format.EsriJSON.prototype.writeFeatureObject); - -goog.exportProperty( - ol.format.EsriJSON.prototype, - 'writeFeatures', - ol.format.EsriJSON.prototype.writeFeatures); - -goog.exportProperty( - ol.format.EsriJSON.prototype, - 'writeFeaturesObject', - ol.format.EsriJSON.prototype.writeFeaturesObject); - -goog.exportSymbol( - 'ol.format.Feature', - ol.format.Feature, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.and', - ol.format.filter.and, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.or', - ol.format.filter.or, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.not', - ol.format.filter.not, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.bbox', - ol.format.filter.bbox, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.intersects', - ol.format.filter.intersects, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.within', - ol.format.filter.within, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.equalTo', - ol.format.filter.equalTo, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.notEqualTo', - ol.format.filter.notEqualTo, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.lessThan', - ol.format.filter.lessThan, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.lessThanOrEqualTo', - ol.format.filter.lessThanOrEqualTo, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.greaterThan', - ol.format.filter.greaterThan, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.greaterThanOrEqualTo', - ol.format.filter.greaterThanOrEqualTo, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.isNull', - ol.format.filter.isNull, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.between', - ol.format.filter.between, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.like', - ol.format.filter.like, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.during', - ol.format.filter.during, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.GeoJSON', - ol.format.GeoJSON, - OPENLAYERS); - -goog.exportProperty( - ol.format.GeoJSON.prototype, - 'readFeature', - ol.format.GeoJSON.prototype.readFeature); - -goog.exportProperty( - ol.format.GeoJSON.prototype, - 'readFeatures', - ol.format.GeoJSON.prototype.readFeatures); - -goog.exportProperty( - ol.format.GeoJSON.prototype, - 'readGeometry', - ol.format.GeoJSON.prototype.readGeometry); - -goog.exportProperty( - ol.format.GeoJSON.prototype, - 'readProjection', - ol.format.GeoJSON.prototype.readProjection); - -goog.exportProperty( - ol.format.GeoJSON.prototype, - 'writeFeature', - ol.format.GeoJSON.prototype.writeFeature); - -goog.exportProperty( - ol.format.GeoJSON.prototype, - 'writeFeatureObject', - ol.format.GeoJSON.prototype.writeFeatureObject); - -goog.exportProperty( - ol.format.GeoJSON.prototype, - 'writeFeatures', - ol.format.GeoJSON.prototype.writeFeatures); - -goog.exportProperty( - ol.format.GeoJSON.prototype, - 'writeFeaturesObject', - ol.format.GeoJSON.prototype.writeFeaturesObject); - -goog.exportProperty( - ol.format.GeoJSON.prototype, - 'writeGeometry', - ol.format.GeoJSON.prototype.writeGeometry); - -goog.exportProperty( - ol.format.GeoJSON.prototype, - 'writeGeometryObject', - ol.format.GeoJSON.prototype.writeGeometryObject); - -goog.exportSymbol( - 'ol.format.GML', - ol.format.GML, - OPENLAYERS); - -goog.exportProperty( - ol.format.GML.prototype, - 'writeFeatures', - ol.format.GML.prototype.writeFeatures); - -goog.exportProperty( - ol.format.GML.prototype, - 'writeFeaturesNode', - ol.format.GML.prototype.writeFeaturesNode); - -goog.exportSymbol( - 'ol.format.GML2', - ol.format.GML2, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.GML3', - ol.format.GML3, - OPENLAYERS); - -goog.exportProperty( - ol.format.GML3.prototype, - 'writeGeometryNode', - ol.format.GML3.prototype.writeGeometryNode); - -goog.exportProperty( - ol.format.GML3.prototype, - 'writeFeatures', - ol.format.GML3.prototype.writeFeatures); - -goog.exportProperty( - ol.format.GML3.prototype, - 'writeFeaturesNode', - ol.format.GML3.prototype.writeFeaturesNode); - -goog.exportProperty( - ol.format.GMLBase.prototype, - 'readFeatures', - ol.format.GMLBase.prototype.readFeatures); - -goog.exportSymbol( - 'ol.format.GPX', - ol.format.GPX, - OPENLAYERS); - -goog.exportProperty( - ol.format.GPX.prototype, - 'readFeature', - ol.format.GPX.prototype.readFeature); - -goog.exportProperty( - ol.format.GPX.prototype, - 'readFeatures', - ol.format.GPX.prototype.readFeatures); - -goog.exportProperty( - ol.format.GPX.prototype, - 'readProjection', - ol.format.GPX.prototype.readProjection); - -goog.exportProperty( - ol.format.GPX.prototype, - 'writeFeatures', - ol.format.GPX.prototype.writeFeatures); - -goog.exportProperty( - ol.format.GPX.prototype, - 'writeFeaturesNode', - ol.format.GPX.prototype.writeFeaturesNode); - -goog.exportSymbol( - 'ol.format.IGC', - ol.format.IGC, - OPENLAYERS); - -goog.exportProperty( - ol.format.IGC.prototype, - 'readFeature', - ol.format.IGC.prototype.readFeature); - -goog.exportProperty( - ol.format.IGC.prototype, - 'readFeatures', - ol.format.IGC.prototype.readFeatures); - -goog.exportProperty( - ol.format.IGC.prototype, - 'readProjection', - ol.format.IGC.prototype.readProjection); - -goog.exportSymbol( - 'ol.format.KML', - ol.format.KML, - OPENLAYERS); - -goog.exportProperty( - ol.format.KML.prototype, - 'readFeature', - ol.format.KML.prototype.readFeature); - -goog.exportProperty( - ol.format.KML.prototype, - 'readFeatures', - ol.format.KML.prototype.readFeatures); - -goog.exportProperty( - ol.format.KML.prototype, - 'readName', - ol.format.KML.prototype.readName); - -goog.exportProperty( - ol.format.KML.prototype, - 'readNetworkLinks', - ol.format.KML.prototype.readNetworkLinks); - -goog.exportProperty( - ol.format.KML.prototype, - 'readRegion', - ol.format.KML.prototype.readRegion); - -goog.exportProperty( - ol.format.KML.prototype, - 'readRegionFromNode', - ol.format.KML.prototype.readRegionFromNode); - -goog.exportProperty( - ol.format.KML.prototype, - 'readProjection', - ol.format.KML.prototype.readProjection); - -goog.exportProperty( - ol.format.KML.prototype, - 'writeFeatures', - ol.format.KML.prototype.writeFeatures); - -goog.exportProperty( - ol.format.KML.prototype, - 'writeFeaturesNode', - ol.format.KML.prototype.writeFeaturesNode); - -goog.exportSymbol( - 'ol.format.MVT', - ol.format.MVT, - OPENLAYERS); - -goog.exportProperty( - ol.format.MVT.prototype, - 'getLastExtent', - ol.format.MVT.prototype.getLastExtent); - -goog.exportProperty( - ol.format.MVT.prototype, - 'readFeatures', - ol.format.MVT.prototype.readFeatures); - -goog.exportProperty( - ol.format.MVT.prototype, - 'readProjection', - ol.format.MVT.prototype.readProjection); - -goog.exportProperty( - ol.format.MVT.prototype, - 'setLayers', - ol.format.MVT.prototype.setLayers); - -goog.exportSymbol( - 'ol.format.OSMXML', - ol.format.OSMXML, - OPENLAYERS); - -goog.exportProperty( - ol.format.OSMXML.prototype, - 'readFeatures', - ol.format.OSMXML.prototype.readFeatures); - -goog.exportProperty( - ol.format.OSMXML.prototype, - 'readProjection', - ol.format.OSMXML.prototype.readProjection); - -goog.exportSymbol( - 'ol.format.Polyline', - ol.format.Polyline, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.Polyline.encodeDeltas', - ol.format.Polyline.encodeDeltas, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.Polyline.decodeDeltas', - ol.format.Polyline.decodeDeltas, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.Polyline.encodeFloats', - ol.format.Polyline.encodeFloats, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.Polyline.decodeFloats', - ol.format.Polyline.decodeFloats, - OPENLAYERS); - -goog.exportProperty( - ol.format.Polyline.prototype, - 'readFeature', - ol.format.Polyline.prototype.readFeature); - -goog.exportProperty( - ol.format.Polyline.prototype, - 'readFeatures', - ol.format.Polyline.prototype.readFeatures); - -goog.exportProperty( - ol.format.Polyline.prototype, - 'readGeometry', - ol.format.Polyline.prototype.readGeometry); - -goog.exportProperty( - ol.format.Polyline.prototype, - 'readProjection', - ol.format.Polyline.prototype.readProjection); - -goog.exportProperty( - ol.format.Polyline.prototype, - 'writeGeometry', - ol.format.Polyline.prototype.writeGeometry); - -goog.exportSymbol( - 'ol.format.TopoJSON', - ol.format.TopoJSON, - OPENLAYERS); - -goog.exportProperty( - ol.format.TopoJSON.prototype, - 'readFeatures', - ol.format.TopoJSON.prototype.readFeatures); - -goog.exportProperty( - ol.format.TopoJSON.prototype, - 'readProjection', - ol.format.TopoJSON.prototype.readProjection); - -goog.exportSymbol( - 'ol.format.WFS', - ol.format.WFS, - OPENLAYERS); - -goog.exportProperty( - ol.format.WFS.prototype, - 'readFeatures', - ol.format.WFS.prototype.readFeatures); - -goog.exportProperty( - ol.format.WFS.prototype, - 'readTransactionResponse', - ol.format.WFS.prototype.readTransactionResponse); - -goog.exportProperty( - ol.format.WFS.prototype, - 'readFeatureCollectionMetadata', - ol.format.WFS.prototype.readFeatureCollectionMetadata); - -goog.exportSymbol( - 'ol.format.WFS.writeFilter', - ol.format.WFS.writeFilter, - OPENLAYERS); - -goog.exportProperty( - ol.format.WFS.prototype, - 'writeGetFeature', - ol.format.WFS.prototype.writeGetFeature); - -goog.exportProperty( - ol.format.WFS.prototype, - 'writeTransaction', - ol.format.WFS.prototype.writeTransaction); - -goog.exportProperty( - ol.format.WFS.prototype, - 'readProjection', - ol.format.WFS.prototype.readProjection); - -goog.exportSymbol( - 'ol.format.WKT', - ol.format.WKT, - OPENLAYERS); - -goog.exportProperty( - ol.format.WKT.prototype, - 'readFeature', - ol.format.WKT.prototype.readFeature); - -goog.exportProperty( - ol.format.WKT.prototype, - 'readFeatures', - ol.format.WKT.prototype.readFeatures); - -goog.exportProperty( - ol.format.WKT.prototype, - 'readGeometry', - ol.format.WKT.prototype.readGeometry); - -goog.exportProperty( - ol.format.WKT.prototype, - 'writeFeature', - ol.format.WKT.prototype.writeFeature); - -goog.exportProperty( - ol.format.WKT.prototype, - 'writeFeatures', - ol.format.WKT.prototype.writeFeatures); - -goog.exportProperty( - ol.format.WKT.prototype, - 'writeGeometry', - ol.format.WKT.prototype.writeGeometry); - -goog.exportSymbol( - 'ol.format.WMSCapabilities', - ol.format.WMSCapabilities, - OPENLAYERS); - -goog.exportProperty( - ol.format.WMSCapabilities.prototype, - 'read', - ol.format.WMSCapabilities.prototype.read); - -goog.exportSymbol( - 'ol.format.WMSGetFeatureInfo', - ol.format.WMSGetFeatureInfo, - OPENLAYERS); - -goog.exportProperty( - ol.format.WMSGetFeatureInfo.prototype, - 'readFeatures', - ol.format.WMSGetFeatureInfo.prototype.readFeatures); - -goog.exportSymbol( - 'ol.format.WMTSCapabilities', - ol.format.WMTSCapabilities, - OPENLAYERS); - -goog.exportProperty( - ol.format.WMTSCapabilities.prototype, - 'read', - ol.format.WMTSCapabilities.prototype.read); - -goog.exportSymbol( - 'ol.format.filter.And', - ol.format.filter.And, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.Bbox', - ol.format.filter.Bbox, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.Comparison', - ol.format.filter.Comparison, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.ComparisonBinary', - ol.format.filter.ComparisonBinary, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.During', - ol.format.filter.During, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.EqualTo', - ol.format.filter.EqualTo, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.Filter', - ol.format.filter.Filter, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.GreaterThan', - ol.format.filter.GreaterThan, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.GreaterThanOrEqualTo', - ol.format.filter.GreaterThanOrEqualTo, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.Intersects', - ol.format.filter.Intersects, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.IsBetween', - ol.format.filter.IsBetween, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.IsLike', - ol.format.filter.IsLike, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.IsNull', - ol.format.filter.IsNull, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.LessThan', - ol.format.filter.LessThan, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.LessThanOrEqualTo', - ol.format.filter.LessThanOrEqualTo, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.Not', - ol.format.filter.Not, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.NotEqualTo', - ol.format.filter.NotEqualTo, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.Or', - ol.format.filter.Or, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.Spatial', - ol.format.filter.Spatial, - OPENLAYERS); - -goog.exportSymbol( - 'ol.format.filter.Within', - ol.format.filter.Within, - OPENLAYERS); - -goog.exportSymbol( - 'ol.events.condition.altKeyOnly', - ol.events.condition.altKeyOnly, - OPENLAYERS); - -goog.exportSymbol( - 'ol.events.condition.altShiftKeysOnly', - ol.events.condition.altShiftKeysOnly, - OPENLAYERS); - -goog.exportSymbol( - 'ol.events.condition.always', - ol.events.condition.always, - OPENLAYERS); - -goog.exportSymbol( - 'ol.events.condition.click', - ol.events.condition.click, - OPENLAYERS); - -goog.exportSymbol( - 'ol.events.condition.never', - ol.events.condition.never, - OPENLAYERS); - -goog.exportSymbol( - 'ol.events.condition.pointerMove', - ol.events.condition.pointerMove, - OPENLAYERS); - -goog.exportSymbol( - 'ol.events.condition.singleClick', - ol.events.condition.singleClick, - OPENLAYERS); - -goog.exportSymbol( - 'ol.events.condition.doubleClick', - ol.events.condition.doubleClick, - OPENLAYERS); - -goog.exportSymbol( - 'ol.events.condition.noModifierKeys', - ol.events.condition.noModifierKeys, - OPENLAYERS); - -goog.exportSymbol( - 'ol.events.condition.platformModifierKeyOnly', - ol.events.condition.platformModifierKeyOnly, - OPENLAYERS); - -goog.exportSymbol( - 'ol.events.condition.shiftKeyOnly', - ol.events.condition.shiftKeyOnly, - OPENLAYERS); - -goog.exportSymbol( - 'ol.events.condition.targetNotEditable', - ol.events.condition.targetNotEditable, - OPENLAYERS); - -goog.exportSymbol( - 'ol.events.condition.mouseOnly', - ol.events.condition.mouseOnly, - OPENLAYERS); - -goog.exportSymbol( - 'ol.events.condition.primaryAction', - ol.events.condition.primaryAction, - OPENLAYERS); - -goog.exportProperty( - ol.events.Event.prototype, - 'type', - ol.events.Event.prototype.type); - -goog.exportProperty( - ol.events.Event.prototype, - 'target', - ol.events.Event.prototype.target); - -goog.exportProperty( - ol.events.Event.prototype, - 'preventDefault', - ol.events.Event.prototype.preventDefault); - -goog.exportProperty( - ol.events.Event.prototype, - 'stopPropagation', - ol.events.Event.prototype.stopPropagation); - -goog.exportSymbol( - 'ol.control.Attribution', - ol.control.Attribution, - OPENLAYERS); - -goog.exportSymbol( - 'ol.control.Attribution.render', - ol.control.Attribution.render, - OPENLAYERS); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'getCollapsible', - ol.control.Attribution.prototype.getCollapsible); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'setCollapsible', - ol.control.Attribution.prototype.setCollapsible); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'setCollapsed', - ol.control.Attribution.prototype.setCollapsed); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'getCollapsed', - ol.control.Attribution.prototype.getCollapsed); - -goog.exportSymbol( - 'ol.control.Control', - ol.control.Control, - OPENLAYERS); - -goog.exportProperty( - ol.control.Control.prototype, - 'getMap', - ol.control.Control.prototype.getMap); - -goog.exportProperty( - ol.control.Control.prototype, - 'setMap', - ol.control.Control.prototype.setMap); - -goog.exportProperty( - ol.control.Control.prototype, - 'setTarget', - ol.control.Control.prototype.setTarget); - -goog.exportSymbol( - 'ol.control.FullScreen', - ol.control.FullScreen, - OPENLAYERS); - -goog.exportSymbol( - 'ol.control.MousePosition', - ol.control.MousePosition, - OPENLAYERS); - -goog.exportSymbol( - 'ol.control.MousePosition.render', - ol.control.MousePosition.render, - OPENLAYERS); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'getCoordinateFormat', - ol.control.MousePosition.prototype.getCoordinateFormat); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'getProjection', - ol.control.MousePosition.prototype.getProjection); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'setCoordinateFormat', - ol.control.MousePosition.prototype.setCoordinateFormat); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'setProjection', - ol.control.MousePosition.prototype.setProjection); - -goog.exportSymbol( - 'ol.control.OverviewMap', - ol.control.OverviewMap, - OPENLAYERS); - -goog.exportSymbol( - 'ol.control.OverviewMap.render', - ol.control.OverviewMap.render, - OPENLAYERS); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'getCollapsible', - ol.control.OverviewMap.prototype.getCollapsible); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'setCollapsible', - ol.control.OverviewMap.prototype.setCollapsible); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'setCollapsed', - ol.control.OverviewMap.prototype.setCollapsed); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'getCollapsed', - ol.control.OverviewMap.prototype.getCollapsed); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'getOverviewMap', - ol.control.OverviewMap.prototype.getOverviewMap); - -goog.exportSymbol( - 'ol.control.Rotate', - ol.control.Rotate, - OPENLAYERS); - -goog.exportSymbol( - 'ol.control.Rotate.render', - ol.control.Rotate.render, - OPENLAYERS); - -goog.exportSymbol( - 'ol.control.ScaleLine', - ol.control.ScaleLine, - OPENLAYERS); - -goog.exportProperty( - ol.control.ScaleLine.prototype, - 'getUnits', - ol.control.ScaleLine.prototype.getUnits); - -goog.exportSymbol( - 'ol.control.ScaleLine.render', - ol.control.ScaleLine.render, - OPENLAYERS); - -goog.exportProperty( - ol.control.ScaleLine.prototype, - 'setUnits', - ol.control.ScaleLine.prototype.setUnits); - -goog.exportSymbol( - 'ol.control.Zoom', - ol.control.Zoom, - OPENLAYERS); - -goog.exportSymbol( - 'ol.control.ZoomSlider', - ol.control.ZoomSlider, - OPENLAYERS); - -goog.exportSymbol( - 'ol.control.ZoomSlider.render', - ol.control.ZoomSlider.render, - OPENLAYERS); - -goog.exportSymbol( - 'ol.control.ZoomToExtent', - ol.control.ZoomToExtent, - OPENLAYERS); - -goog.exportProperty( - ol.Object.prototype, - 'changed', - ol.Object.prototype.changed); - -goog.exportProperty( - ol.Object.prototype, - 'dispatchEvent', - ol.Object.prototype.dispatchEvent); - -goog.exportProperty( - ol.Object.prototype, - 'getRevision', - ol.Object.prototype.getRevision); - -goog.exportProperty( - ol.Object.prototype, - 'on', - ol.Object.prototype.on); - -goog.exportProperty( - ol.Object.prototype, - 'once', - ol.Object.prototype.once); - -goog.exportProperty( - ol.Object.prototype, - 'un', - ol.Object.prototype.un); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'get', - ol.PluggableMap.prototype.get); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getKeys', - ol.PluggableMap.prototype.getKeys); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getProperties', - ol.PluggableMap.prototype.getProperties); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'set', - ol.PluggableMap.prototype.set); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'setProperties', - ol.PluggableMap.prototype.setProperties); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'unset', - ol.PluggableMap.prototype.unset); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'changed', - ol.PluggableMap.prototype.changed); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'dispatchEvent', - ol.PluggableMap.prototype.dispatchEvent); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'getRevision', - ol.PluggableMap.prototype.getRevision); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'on', - ol.PluggableMap.prototype.on); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'once', - ol.PluggableMap.prototype.once); - -goog.exportProperty( - ol.PluggableMap.prototype, - 'un', - ol.PluggableMap.prototype.un); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'addControl', - ol.CanvasMap.prototype.addControl); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'addInteraction', - ol.CanvasMap.prototype.addInteraction); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'addLayer', - ol.CanvasMap.prototype.addLayer); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'addOverlay', - ol.CanvasMap.prototype.addOverlay); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'forEachFeatureAtPixel', - ol.CanvasMap.prototype.forEachFeatureAtPixel); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getFeaturesAtPixel', - ol.CanvasMap.prototype.getFeaturesAtPixel); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'forEachLayerAtPixel', - ol.CanvasMap.prototype.forEachLayerAtPixel); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'hasFeatureAtPixel', - ol.CanvasMap.prototype.hasFeatureAtPixel); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getEventCoordinate', - ol.CanvasMap.prototype.getEventCoordinate); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getEventPixel', - ol.CanvasMap.prototype.getEventPixel); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getTarget', - ol.CanvasMap.prototype.getTarget); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getTargetElement', - ol.CanvasMap.prototype.getTargetElement); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getCoordinateFromPixel', - ol.CanvasMap.prototype.getCoordinateFromPixel); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getControls', - ol.CanvasMap.prototype.getControls); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getOverlays', - ol.CanvasMap.prototype.getOverlays); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getOverlayById', - ol.CanvasMap.prototype.getOverlayById); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getInteractions', - ol.CanvasMap.prototype.getInteractions); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getLayerGroup', - ol.CanvasMap.prototype.getLayerGroup); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getLayers', - ol.CanvasMap.prototype.getLayers); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getPixelFromCoordinate', - ol.CanvasMap.prototype.getPixelFromCoordinate); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getSize', - ol.CanvasMap.prototype.getSize); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getView', - ol.CanvasMap.prototype.getView); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getViewport', - ol.CanvasMap.prototype.getViewport); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'renderSync', - ol.CanvasMap.prototype.renderSync); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'render', - ol.CanvasMap.prototype.render); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'removeControl', - ol.CanvasMap.prototype.removeControl); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'removeInteraction', - ol.CanvasMap.prototype.removeInteraction); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'removeLayer', - ol.CanvasMap.prototype.removeLayer); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'removeOverlay', - ol.CanvasMap.prototype.removeOverlay); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'setLayerGroup', - ol.CanvasMap.prototype.setLayerGroup); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'setSize', - ol.CanvasMap.prototype.setSize); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'setTarget', - ol.CanvasMap.prototype.setTarget); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'setView', - ol.CanvasMap.prototype.setView); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'updateSize', - ol.CanvasMap.prototype.updateSize); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'get', - ol.CanvasMap.prototype.get); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getKeys', - ol.CanvasMap.prototype.getKeys); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getProperties', - ol.CanvasMap.prototype.getProperties); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'set', - ol.CanvasMap.prototype.set); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'setProperties', - ol.CanvasMap.prototype.setProperties); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'unset', - ol.CanvasMap.prototype.unset); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'changed', - ol.CanvasMap.prototype.changed); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'dispatchEvent', - ol.CanvasMap.prototype.dispatchEvent); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'getRevision', - ol.CanvasMap.prototype.getRevision); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'on', - ol.CanvasMap.prototype.on); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'once', - ol.CanvasMap.prototype.once); - -goog.exportProperty( - ol.CanvasMap.prototype, - 'un', - ol.CanvasMap.prototype.un); - -goog.exportProperty( - ol.Collection.prototype, - 'get', - ol.Collection.prototype.get); - -goog.exportProperty( - ol.Collection.prototype, - 'getKeys', - ol.Collection.prototype.getKeys); - -goog.exportProperty( - ol.Collection.prototype, - 'getProperties', - ol.Collection.prototype.getProperties); - -goog.exportProperty( - ol.Collection.prototype, - 'set', - ol.Collection.prototype.set); - -goog.exportProperty( - ol.Collection.prototype, - 'setProperties', - ol.Collection.prototype.setProperties); - -goog.exportProperty( - ol.Collection.prototype, - 'unset', - ol.Collection.prototype.unset); - -goog.exportProperty( - ol.Collection.prototype, - 'changed', - ol.Collection.prototype.changed); - -goog.exportProperty( - ol.Collection.prototype, - 'dispatchEvent', - ol.Collection.prototype.dispatchEvent); - -goog.exportProperty( - ol.Collection.prototype, - 'getRevision', - ol.Collection.prototype.getRevision); - -goog.exportProperty( - ol.Collection.prototype, - 'on', - ol.Collection.prototype.on); - -goog.exportProperty( - ol.Collection.prototype, - 'once', - ol.Collection.prototype.once); - -goog.exportProperty( - ol.Collection.prototype, - 'un', - ol.Collection.prototype.un); - -goog.exportProperty( - ol.Collection.Event.prototype, - 'type', - ol.Collection.Event.prototype.type); - -goog.exportProperty( - ol.Collection.Event.prototype, - 'target', - ol.Collection.Event.prototype.target); - -goog.exportProperty( - ol.Collection.Event.prototype, - 'preventDefault', - ol.Collection.Event.prototype.preventDefault); - -goog.exportProperty( - ol.Collection.Event.prototype, - 'stopPropagation', - ol.Collection.Event.prototype.stopPropagation); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'get', - ol.DeviceOrientation.prototype.get); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'getKeys', - ol.DeviceOrientation.prototype.getKeys); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'getProperties', - ol.DeviceOrientation.prototype.getProperties); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'set', - ol.DeviceOrientation.prototype.set); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'setProperties', - ol.DeviceOrientation.prototype.setProperties); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'unset', - ol.DeviceOrientation.prototype.unset); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'changed', - ol.DeviceOrientation.prototype.changed); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'dispatchEvent', - ol.DeviceOrientation.prototype.dispatchEvent); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'getRevision', - ol.DeviceOrientation.prototype.getRevision); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'on', - ol.DeviceOrientation.prototype.on); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'once', - ol.DeviceOrientation.prototype.once); - -goog.exportProperty( - ol.DeviceOrientation.prototype, - 'un', - ol.DeviceOrientation.prototype.un); - -goog.exportProperty( - ol.Feature.prototype, - 'get', - ol.Feature.prototype.get); - -goog.exportProperty( - ol.Feature.prototype, - 'getKeys', - ol.Feature.prototype.getKeys); - -goog.exportProperty( - ol.Feature.prototype, - 'getProperties', - ol.Feature.prototype.getProperties); - -goog.exportProperty( - ol.Feature.prototype, - 'set', - ol.Feature.prototype.set); - -goog.exportProperty( - ol.Feature.prototype, - 'setProperties', - ol.Feature.prototype.setProperties); - -goog.exportProperty( - ol.Feature.prototype, - 'unset', - ol.Feature.prototype.unset); - -goog.exportProperty( - ol.Feature.prototype, - 'changed', - ol.Feature.prototype.changed); - -goog.exportProperty( - ol.Feature.prototype, - 'dispatchEvent', - ol.Feature.prototype.dispatchEvent); - -goog.exportProperty( - ol.Feature.prototype, - 'getRevision', - ol.Feature.prototype.getRevision); - -goog.exportProperty( - ol.Feature.prototype, - 'on', - ol.Feature.prototype.on); - -goog.exportProperty( - ol.Feature.prototype, - 'once', - ol.Feature.prototype.once); - -goog.exportProperty( - ol.Feature.prototype, - 'un', - ol.Feature.prototype.un); - -goog.exportProperty( - ol.Geolocation.prototype, - 'get', - ol.Geolocation.prototype.get); - -goog.exportProperty( - ol.Geolocation.prototype, - 'getKeys', - ol.Geolocation.prototype.getKeys); - -goog.exportProperty( - ol.Geolocation.prototype, - 'getProperties', - ol.Geolocation.prototype.getProperties); - -goog.exportProperty( - ol.Geolocation.prototype, - 'set', - ol.Geolocation.prototype.set); - -goog.exportProperty( - ol.Geolocation.prototype, - 'setProperties', - ol.Geolocation.prototype.setProperties); - -goog.exportProperty( - ol.Geolocation.prototype, - 'unset', - ol.Geolocation.prototype.unset); - -goog.exportProperty( - ol.Geolocation.prototype, - 'changed', - ol.Geolocation.prototype.changed); - -goog.exportProperty( - ol.Geolocation.prototype, - 'dispatchEvent', - ol.Geolocation.prototype.dispatchEvent); - -goog.exportProperty( - ol.Geolocation.prototype, - 'getRevision', - ol.Geolocation.prototype.getRevision); - -goog.exportProperty( - ol.Geolocation.prototype, - 'on', - ol.Geolocation.prototype.on); - -goog.exportProperty( - ol.Geolocation.prototype, - 'once', - ol.Geolocation.prototype.once); - -goog.exportProperty( - ol.Geolocation.prototype, - 'un', - ol.Geolocation.prototype.un); - -goog.exportProperty( - ol.ImageTile.prototype, - 'getTileCoord', - ol.ImageTile.prototype.getTileCoord); - -goog.exportProperty( - ol.ImageTile.prototype, - 'load', - ol.ImageTile.prototype.load); - -goog.exportProperty( - ol.Map.prototype, - 'addControl', - ol.Map.prototype.addControl); - -goog.exportProperty( - ol.Map.prototype, - 'addInteraction', - ol.Map.prototype.addInteraction); - -goog.exportProperty( - ol.Map.prototype, - 'addLayer', - ol.Map.prototype.addLayer); - -goog.exportProperty( - ol.Map.prototype, - 'addOverlay', - ol.Map.prototype.addOverlay); - -goog.exportProperty( - ol.Map.prototype, - 'forEachFeatureAtPixel', - ol.Map.prototype.forEachFeatureAtPixel); - -goog.exportProperty( - ol.Map.prototype, - 'getFeaturesAtPixel', - ol.Map.prototype.getFeaturesAtPixel); - -goog.exportProperty( - ol.Map.prototype, - 'forEachLayerAtPixel', - ol.Map.prototype.forEachLayerAtPixel); - -goog.exportProperty( - ol.Map.prototype, - 'hasFeatureAtPixel', - ol.Map.prototype.hasFeatureAtPixel); - -goog.exportProperty( - ol.Map.prototype, - 'getEventCoordinate', - ol.Map.prototype.getEventCoordinate); - -goog.exportProperty( - ol.Map.prototype, - 'getEventPixel', - ol.Map.prototype.getEventPixel); - -goog.exportProperty( - ol.Map.prototype, - 'getTarget', - ol.Map.prototype.getTarget); - -goog.exportProperty( - ol.Map.prototype, - 'getTargetElement', - ol.Map.prototype.getTargetElement); - -goog.exportProperty( - ol.Map.prototype, - 'getCoordinateFromPixel', - ol.Map.prototype.getCoordinateFromPixel); - -goog.exportProperty( - ol.Map.prototype, - 'getControls', - ol.Map.prototype.getControls); - -goog.exportProperty( - ol.Map.prototype, - 'getOverlays', - ol.Map.prototype.getOverlays); - -goog.exportProperty( - ol.Map.prototype, - 'getOverlayById', - ol.Map.prototype.getOverlayById); - -goog.exportProperty( - ol.Map.prototype, - 'getInteractions', - ol.Map.prototype.getInteractions); - -goog.exportProperty( - ol.Map.prototype, - 'getLayerGroup', - ol.Map.prototype.getLayerGroup); - -goog.exportProperty( - ol.Map.prototype, - 'getLayers', - ol.Map.prototype.getLayers); - -goog.exportProperty( - ol.Map.prototype, - 'getPixelFromCoordinate', - ol.Map.prototype.getPixelFromCoordinate); - -goog.exportProperty( - ol.Map.prototype, - 'getSize', - ol.Map.prototype.getSize); - -goog.exportProperty( - ol.Map.prototype, - 'getView', - ol.Map.prototype.getView); - -goog.exportProperty( - ol.Map.prototype, - 'getViewport', - ol.Map.prototype.getViewport); - -goog.exportProperty( - ol.Map.prototype, - 'renderSync', - ol.Map.prototype.renderSync); - -goog.exportProperty( - ol.Map.prototype, - 'render', - ol.Map.prototype.render); - -goog.exportProperty( - ol.Map.prototype, - 'removeControl', - ol.Map.prototype.removeControl); - -goog.exportProperty( - ol.Map.prototype, - 'removeInteraction', - ol.Map.prototype.removeInteraction); - -goog.exportProperty( - ol.Map.prototype, - 'removeLayer', - ol.Map.prototype.removeLayer); - -goog.exportProperty( - ol.Map.prototype, - 'removeOverlay', - ol.Map.prototype.removeOverlay); - -goog.exportProperty( - ol.Map.prototype, - 'setLayerGroup', - ol.Map.prototype.setLayerGroup); - -goog.exportProperty( - ol.Map.prototype, - 'setSize', - ol.Map.prototype.setSize); - -goog.exportProperty( - ol.Map.prototype, - 'setTarget', - ol.Map.prototype.setTarget); - -goog.exportProperty( - ol.Map.prototype, - 'setView', - ol.Map.prototype.setView); - -goog.exportProperty( - ol.Map.prototype, - 'updateSize', - ol.Map.prototype.updateSize); - -goog.exportProperty( - ol.Map.prototype, - 'get', - ol.Map.prototype.get); - -goog.exportProperty( - ol.Map.prototype, - 'getKeys', - ol.Map.prototype.getKeys); - -goog.exportProperty( - ol.Map.prototype, - 'getProperties', - ol.Map.prototype.getProperties); - -goog.exportProperty( - ol.Map.prototype, - 'set', - ol.Map.prototype.set); - -goog.exportProperty( - ol.Map.prototype, - 'setProperties', - ol.Map.prototype.setProperties); - -goog.exportProperty( - ol.Map.prototype, - 'unset', - ol.Map.prototype.unset); - -goog.exportProperty( - ol.Map.prototype, - 'changed', - ol.Map.prototype.changed); - -goog.exportProperty( - ol.Map.prototype, - 'dispatchEvent', - ol.Map.prototype.dispatchEvent); - -goog.exportProperty( - ol.Map.prototype, - 'getRevision', - ol.Map.prototype.getRevision); - -goog.exportProperty( - ol.Map.prototype, - 'on', - ol.Map.prototype.on); - -goog.exportProperty( - ol.Map.prototype, - 'once', - ol.Map.prototype.once); - -goog.exportProperty( - ol.Map.prototype, - 'un', - ol.Map.prototype.un); - -goog.exportProperty( - ol.MapEvent.prototype, - 'type', - ol.MapEvent.prototype.type); - -goog.exportProperty( - ol.MapEvent.prototype, - 'target', - ol.MapEvent.prototype.target); - -goog.exportProperty( - ol.MapEvent.prototype, - 'preventDefault', - ol.MapEvent.prototype.preventDefault); - -goog.exportProperty( - ol.MapEvent.prototype, - 'stopPropagation', - ol.MapEvent.prototype.stopPropagation); - -goog.exportProperty( - ol.MapBrowserEvent.prototype, - 'map', - ol.MapBrowserEvent.prototype.map); - -goog.exportProperty( - ol.MapBrowserEvent.prototype, - 'frameState', - ol.MapBrowserEvent.prototype.frameState); - -goog.exportProperty( - ol.MapBrowserEvent.prototype, - 'type', - ol.MapBrowserEvent.prototype.type); - -goog.exportProperty( - ol.MapBrowserEvent.prototype, - 'target', - ol.MapBrowserEvent.prototype.target); - -goog.exportProperty( - ol.MapBrowserEvent.prototype, - 'preventDefault', - ol.MapBrowserEvent.prototype.preventDefault); - -goog.exportProperty( - ol.MapBrowserEvent.prototype, - 'stopPropagation', - ol.MapBrowserEvent.prototype.stopPropagation); - -goog.exportProperty( - ol.MapBrowserPointerEvent.prototype, - 'originalEvent', - ol.MapBrowserPointerEvent.prototype.originalEvent); - -goog.exportProperty( - ol.MapBrowserPointerEvent.prototype, - 'pixel', - ol.MapBrowserPointerEvent.prototype.pixel); - -goog.exportProperty( - ol.MapBrowserPointerEvent.prototype, - 'coordinate', - ol.MapBrowserPointerEvent.prototype.coordinate); - -goog.exportProperty( - ol.MapBrowserPointerEvent.prototype, - 'dragging', - ol.MapBrowserPointerEvent.prototype.dragging); - -goog.exportProperty( - ol.MapBrowserPointerEvent.prototype, - 'preventDefault', - ol.MapBrowserPointerEvent.prototype.preventDefault); - -goog.exportProperty( - ol.MapBrowserPointerEvent.prototype, - 'stopPropagation', - ol.MapBrowserPointerEvent.prototype.stopPropagation); - -goog.exportProperty( - ol.MapBrowserPointerEvent.prototype, - 'map', - ol.MapBrowserPointerEvent.prototype.map); - -goog.exportProperty( - ol.MapBrowserPointerEvent.prototype, - 'frameState', - ol.MapBrowserPointerEvent.prototype.frameState); - -goog.exportProperty( - ol.MapBrowserPointerEvent.prototype, - 'type', - ol.MapBrowserPointerEvent.prototype.type); - -goog.exportProperty( - ol.MapBrowserPointerEvent.prototype, - 'target', - ol.MapBrowserPointerEvent.prototype.target); - -goog.exportProperty( - ol.Object.Event.prototype, - 'type', - ol.Object.Event.prototype.type); - -goog.exportProperty( - ol.Object.Event.prototype, - 'target', - ol.Object.Event.prototype.target); - -goog.exportProperty( - ol.Object.Event.prototype, - 'preventDefault', - ol.Object.Event.prototype.preventDefault); - -goog.exportProperty( - ol.Object.Event.prototype, - 'stopPropagation', - ol.Object.Event.prototype.stopPropagation); - -goog.exportProperty( - ol.Overlay.prototype, - 'get', - ol.Overlay.prototype.get); - -goog.exportProperty( - ol.Overlay.prototype, - 'getKeys', - ol.Overlay.prototype.getKeys); - -goog.exportProperty( - ol.Overlay.prototype, - 'getProperties', - ol.Overlay.prototype.getProperties); - -goog.exportProperty( - ol.Overlay.prototype, - 'set', - ol.Overlay.prototype.set); - -goog.exportProperty( - ol.Overlay.prototype, - 'setProperties', - ol.Overlay.prototype.setProperties); - -goog.exportProperty( - ol.Overlay.prototype, - 'unset', - ol.Overlay.prototype.unset); - -goog.exportProperty( - ol.Overlay.prototype, - 'changed', - ol.Overlay.prototype.changed); - -goog.exportProperty( - ol.Overlay.prototype, - 'dispatchEvent', - ol.Overlay.prototype.dispatchEvent); - -goog.exportProperty( - ol.Overlay.prototype, - 'getRevision', - ol.Overlay.prototype.getRevision); - -goog.exportProperty( - ol.Overlay.prototype, - 'on', - ol.Overlay.prototype.on); - -goog.exportProperty( - ol.Overlay.prototype, - 'once', - ol.Overlay.prototype.once); - -goog.exportProperty( - ol.Overlay.prototype, - 'un', - ol.Overlay.prototype.un); - -goog.exportProperty( - ol.VectorImageTile.prototype, - 'getTileCoord', - ol.VectorImageTile.prototype.getTileCoord); - -goog.exportProperty( - ol.VectorImageTile.prototype, - 'load', - ol.VectorImageTile.prototype.load); - -goog.exportProperty( - ol.VectorTile.prototype, - 'getTileCoord', - ol.VectorTile.prototype.getTileCoord); - -goog.exportProperty( - ol.VectorTile.prototype, - 'load', - ol.VectorTile.prototype.load); - -goog.exportProperty( - ol.View.prototype, - 'get', - ol.View.prototype.get); - -goog.exportProperty( - ol.View.prototype, - 'getKeys', - ol.View.prototype.getKeys); - -goog.exportProperty( - ol.View.prototype, - 'getProperties', - ol.View.prototype.getProperties); - -goog.exportProperty( - ol.View.prototype, - 'set', - ol.View.prototype.set); - -goog.exportProperty( - ol.View.prototype, - 'setProperties', - ol.View.prototype.setProperties); - -goog.exportProperty( - ol.View.prototype, - 'unset', - ol.View.prototype.unset); - -goog.exportProperty( - ol.View.prototype, - 'changed', - ol.View.prototype.changed); - -goog.exportProperty( - ol.View.prototype, - 'dispatchEvent', - ol.View.prototype.dispatchEvent); - -goog.exportProperty( - ol.View.prototype, - 'getRevision', - ol.View.prototype.getRevision); - -goog.exportProperty( - ol.View.prototype, - 'on', - ol.View.prototype.on); - -goog.exportProperty( - ol.View.prototype, - 'once', - ol.View.prototype.once); - -goog.exportProperty( - ol.View.prototype, - 'un', - ol.View.prototype.un); - -goog.exportProperty( - ol.tilegrid.WMTS.prototype, - 'forEachTileCoord', - ol.tilegrid.WMTS.prototype.forEachTileCoord); - -goog.exportProperty( - ol.tilegrid.WMTS.prototype, - 'getMaxZoom', - ol.tilegrid.WMTS.prototype.getMaxZoom); - -goog.exportProperty( - ol.tilegrid.WMTS.prototype, - 'getMinZoom', - ol.tilegrid.WMTS.prototype.getMinZoom); - -goog.exportProperty( - ol.tilegrid.WMTS.prototype, - 'getOrigin', - ol.tilegrid.WMTS.prototype.getOrigin); - -goog.exportProperty( - ol.tilegrid.WMTS.prototype, - 'getResolution', - ol.tilegrid.WMTS.prototype.getResolution); - -goog.exportProperty( - ol.tilegrid.WMTS.prototype, - 'getResolutions', - ol.tilegrid.WMTS.prototype.getResolutions); - -goog.exportProperty( - ol.tilegrid.WMTS.prototype, - 'getTileCoordExtent', - ol.tilegrid.WMTS.prototype.getTileCoordExtent); - -goog.exportProperty( - ol.tilegrid.WMTS.prototype, - 'getTileCoordForCoordAndResolution', - ol.tilegrid.WMTS.prototype.getTileCoordForCoordAndResolution); - -goog.exportProperty( - ol.tilegrid.WMTS.prototype, - 'getTileCoordForCoordAndZ', - ol.tilegrid.WMTS.prototype.getTileCoordForCoordAndZ); - -goog.exportProperty( - ol.tilegrid.WMTS.prototype, - 'getTileSize', - ol.tilegrid.WMTS.prototype.getTileSize); - -goog.exportProperty( - ol.tilegrid.WMTS.prototype, - 'getZForResolution', - ol.tilegrid.WMTS.prototype.getZForResolution); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'getOpacity', - ol.style.RegularShape.prototype.getOpacity); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'getRotateWithView', - ol.style.RegularShape.prototype.getRotateWithView); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'getRotation', - ol.style.RegularShape.prototype.getRotation); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'getScale', - ol.style.RegularShape.prototype.getScale); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'getSnapToPixel', - ol.style.RegularShape.prototype.getSnapToPixel); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'setOpacity', - ol.style.RegularShape.prototype.setOpacity); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'setRotation', - ol.style.RegularShape.prototype.setRotation); - -goog.exportProperty( - ol.style.RegularShape.prototype, - 'setScale', - ol.style.RegularShape.prototype.setScale); - -goog.exportProperty( - ol.style.Circle.prototype, - 'clone', - ol.style.Circle.prototype.clone); - -goog.exportProperty( - ol.style.Circle.prototype, - 'getAngle', - ol.style.Circle.prototype.getAngle); - -goog.exportProperty( - ol.style.Circle.prototype, - 'getFill', - ol.style.Circle.prototype.getFill); - -goog.exportProperty( - ol.style.Circle.prototype, - 'getPoints', - ol.style.Circle.prototype.getPoints); - -goog.exportProperty( - ol.style.Circle.prototype, - 'getRadius', - ol.style.Circle.prototype.getRadius); - -goog.exportProperty( - ol.style.Circle.prototype, - 'getRadius2', - ol.style.Circle.prototype.getRadius2); - -goog.exportProperty( - ol.style.Circle.prototype, - 'getStroke', - ol.style.Circle.prototype.getStroke); - -goog.exportProperty( - ol.style.Circle.prototype, - 'getOpacity', - ol.style.Circle.prototype.getOpacity); - -goog.exportProperty( - ol.style.Circle.prototype, - 'getRotateWithView', - ol.style.Circle.prototype.getRotateWithView); - -goog.exportProperty( - ol.style.Circle.prototype, - 'getRotation', - ol.style.Circle.prototype.getRotation); - -goog.exportProperty( - ol.style.Circle.prototype, - 'getScale', - ol.style.Circle.prototype.getScale); - -goog.exportProperty( - ol.style.Circle.prototype, - 'getSnapToPixel', - ol.style.Circle.prototype.getSnapToPixel); - -goog.exportProperty( - ol.style.Circle.prototype, - 'setOpacity', - ol.style.Circle.prototype.setOpacity); - -goog.exportProperty( - ol.style.Circle.prototype, - 'setRotation', - ol.style.Circle.prototype.setRotation); - -goog.exportProperty( - ol.style.Circle.prototype, - 'setScale', - ol.style.Circle.prototype.setScale); - -goog.exportProperty( - ol.style.Icon.prototype, - 'getOpacity', - ol.style.Icon.prototype.getOpacity); - -goog.exportProperty( - ol.style.Icon.prototype, - 'getRotateWithView', - ol.style.Icon.prototype.getRotateWithView); - -goog.exportProperty( - ol.style.Icon.prototype, - 'getRotation', - ol.style.Icon.prototype.getRotation); - -goog.exportProperty( - ol.style.Icon.prototype, - 'getScale', - ol.style.Icon.prototype.getScale); - -goog.exportProperty( - ol.style.Icon.prototype, - 'getSnapToPixel', - ol.style.Icon.prototype.getSnapToPixel); - -goog.exportProperty( - ol.style.Icon.prototype, - 'setOpacity', - ol.style.Icon.prototype.setOpacity); - -goog.exportProperty( - ol.style.Icon.prototype, - 'setRotation', - ol.style.Icon.prototype.setRotation); - -goog.exportProperty( - ol.style.Icon.prototype, - 'setScale', - ol.style.Icon.prototype.setScale); - -goog.exportProperty( - ol.source.Source.prototype, - 'get', - ol.source.Source.prototype.get); - -goog.exportProperty( - ol.source.Source.prototype, - 'getKeys', - ol.source.Source.prototype.getKeys); - -goog.exportProperty( - ol.source.Source.prototype, - 'getProperties', - ol.source.Source.prototype.getProperties); - -goog.exportProperty( - ol.source.Source.prototype, - 'set', - ol.source.Source.prototype.set); - -goog.exportProperty( - ol.source.Source.prototype, - 'setProperties', - ol.source.Source.prototype.setProperties); - -goog.exportProperty( - ol.source.Source.prototype, - 'unset', - ol.source.Source.prototype.unset); - -goog.exportProperty( - ol.source.Source.prototype, - 'changed', - ol.source.Source.prototype.changed); - -goog.exportProperty( - ol.source.Source.prototype, - 'dispatchEvent', - ol.source.Source.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.Source.prototype, - 'getRevision', - ol.source.Source.prototype.getRevision); - -goog.exportProperty( - ol.source.Source.prototype, - 'on', - ol.source.Source.prototype.on); - -goog.exportProperty( - ol.source.Source.prototype, - 'once', - ol.source.Source.prototype.once); - -goog.exportProperty( - ol.source.Source.prototype, - 'un', - ol.source.Source.prototype.un); - -goog.exportProperty( - ol.source.Tile.prototype, - 'getAttributions', - ol.source.Tile.prototype.getAttributions); - -goog.exportProperty( - ol.source.Tile.prototype, - 'getLogo', - ol.source.Tile.prototype.getLogo); - -goog.exportProperty( - ol.source.Tile.prototype, - 'getProjection', - ol.source.Tile.prototype.getProjection); - -goog.exportProperty( - ol.source.Tile.prototype, - 'getState', - ol.source.Tile.prototype.getState); - -goog.exportProperty( - ol.source.Tile.prototype, - 'refresh', - ol.source.Tile.prototype.refresh); - -goog.exportProperty( - ol.source.Tile.prototype, - 'setAttributions', - ol.source.Tile.prototype.setAttributions); - -goog.exportProperty( - ol.source.Tile.prototype, - 'get', - ol.source.Tile.prototype.get); - -goog.exportProperty( - ol.source.Tile.prototype, - 'getKeys', - ol.source.Tile.prototype.getKeys); - -goog.exportProperty( - ol.source.Tile.prototype, - 'getProperties', - ol.source.Tile.prototype.getProperties); - -goog.exportProperty( - ol.source.Tile.prototype, - 'set', - ol.source.Tile.prototype.set); - -goog.exportProperty( - ol.source.Tile.prototype, - 'setProperties', - ol.source.Tile.prototype.setProperties); - -goog.exportProperty( - ol.source.Tile.prototype, - 'unset', - ol.source.Tile.prototype.unset); - -goog.exportProperty( - ol.source.Tile.prototype, - 'changed', - ol.source.Tile.prototype.changed); - -goog.exportProperty( - ol.source.Tile.prototype, - 'dispatchEvent', - ol.source.Tile.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.Tile.prototype, - 'getRevision', - ol.source.Tile.prototype.getRevision); - -goog.exportProperty( - ol.source.Tile.prototype, - 'on', - ol.source.Tile.prototype.on); - -goog.exportProperty( - ol.source.Tile.prototype, - 'once', - ol.source.Tile.prototype.once); - -goog.exportProperty( - ol.source.Tile.prototype, - 'un', - ol.source.Tile.prototype.un); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'getTileGrid', - ol.source.UrlTile.prototype.getTileGrid); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'refresh', - ol.source.UrlTile.prototype.refresh); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'getAttributions', - ol.source.UrlTile.prototype.getAttributions); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'getLogo', - ol.source.UrlTile.prototype.getLogo); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'getProjection', - ol.source.UrlTile.prototype.getProjection); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'getState', - ol.source.UrlTile.prototype.getState); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'setAttributions', - ol.source.UrlTile.prototype.setAttributions); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'get', - ol.source.UrlTile.prototype.get); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'getKeys', - ol.source.UrlTile.prototype.getKeys); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'getProperties', - ol.source.UrlTile.prototype.getProperties); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'set', - ol.source.UrlTile.prototype.set); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'setProperties', - ol.source.UrlTile.prototype.setProperties); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'unset', - ol.source.UrlTile.prototype.unset); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'changed', - ol.source.UrlTile.prototype.changed); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'dispatchEvent', - ol.source.UrlTile.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'getRevision', - ol.source.UrlTile.prototype.getRevision); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'on', - ol.source.UrlTile.prototype.on); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'once', - ol.source.UrlTile.prototype.once); - -goog.exportProperty( - ol.source.UrlTile.prototype, - 'un', - ol.source.UrlTile.prototype.un); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'getTileLoadFunction', - ol.source.TileImage.prototype.getTileLoadFunction); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'getTileUrlFunction', - ol.source.TileImage.prototype.getTileUrlFunction); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'getUrls', - ol.source.TileImage.prototype.getUrls); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'setTileLoadFunction', - ol.source.TileImage.prototype.setTileLoadFunction); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'setTileUrlFunction', - ol.source.TileImage.prototype.setTileUrlFunction); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'setUrl', - ol.source.TileImage.prototype.setUrl); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'setUrls', - ol.source.TileImage.prototype.setUrls); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'getTileGrid', - ol.source.TileImage.prototype.getTileGrid); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'refresh', - ol.source.TileImage.prototype.refresh); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'getAttributions', - ol.source.TileImage.prototype.getAttributions); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'getLogo', - ol.source.TileImage.prototype.getLogo); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'getProjection', - ol.source.TileImage.prototype.getProjection); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'getState', - ol.source.TileImage.prototype.getState); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'setAttributions', - ol.source.TileImage.prototype.setAttributions); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'get', - ol.source.TileImage.prototype.get); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'getKeys', - ol.source.TileImage.prototype.getKeys); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'getProperties', - ol.source.TileImage.prototype.getProperties); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'set', - ol.source.TileImage.prototype.set); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'setProperties', - ol.source.TileImage.prototype.setProperties); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'unset', - ol.source.TileImage.prototype.unset); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'changed', - ol.source.TileImage.prototype.changed); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'dispatchEvent', - ol.source.TileImage.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'getRevision', - ol.source.TileImage.prototype.getRevision); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'on', - ol.source.TileImage.prototype.on); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'once', - ol.source.TileImage.prototype.once); - -goog.exportProperty( - ol.source.TileImage.prototype, - 'un', - ol.source.TileImage.prototype.un); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'setRenderReprojectionEdges', - ol.source.BingMaps.prototype.setRenderReprojectionEdges); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'setTileGridForProjection', - ol.source.BingMaps.prototype.setTileGridForProjection); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'getTileLoadFunction', - ol.source.BingMaps.prototype.getTileLoadFunction); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'getTileUrlFunction', - ol.source.BingMaps.prototype.getTileUrlFunction); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'getUrls', - ol.source.BingMaps.prototype.getUrls); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'setTileLoadFunction', - ol.source.BingMaps.prototype.setTileLoadFunction); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'setTileUrlFunction', - ol.source.BingMaps.prototype.setTileUrlFunction); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'setUrl', - ol.source.BingMaps.prototype.setUrl); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'setUrls', - ol.source.BingMaps.prototype.setUrls); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'getTileGrid', - ol.source.BingMaps.prototype.getTileGrid); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'refresh', - ol.source.BingMaps.prototype.refresh); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'getAttributions', - ol.source.BingMaps.prototype.getAttributions); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'getLogo', - ol.source.BingMaps.prototype.getLogo); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'getProjection', - ol.source.BingMaps.prototype.getProjection); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'getState', - ol.source.BingMaps.prototype.getState); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'setAttributions', - ol.source.BingMaps.prototype.setAttributions); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'get', - ol.source.BingMaps.prototype.get); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'getKeys', - ol.source.BingMaps.prototype.getKeys); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'getProperties', - ol.source.BingMaps.prototype.getProperties); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'set', - ol.source.BingMaps.prototype.set); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'setProperties', - ol.source.BingMaps.prototype.setProperties); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'unset', - ol.source.BingMaps.prototype.unset); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'changed', - ol.source.BingMaps.prototype.changed); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'dispatchEvent', - ol.source.BingMaps.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'getRevision', - ol.source.BingMaps.prototype.getRevision); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'on', - ol.source.BingMaps.prototype.on); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'once', - ol.source.BingMaps.prototype.once); - -goog.exportProperty( - ol.source.BingMaps.prototype, - 'un', - ol.source.BingMaps.prototype.un); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'setRenderReprojectionEdges', - ol.source.XYZ.prototype.setRenderReprojectionEdges); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'setTileGridForProjection', - ol.source.XYZ.prototype.setTileGridForProjection); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'getTileLoadFunction', - ol.source.XYZ.prototype.getTileLoadFunction); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'getTileUrlFunction', - ol.source.XYZ.prototype.getTileUrlFunction); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'getUrls', - ol.source.XYZ.prototype.getUrls); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'setTileLoadFunction', - ol.source.XYZ.prototype.setTileLoadFunction); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'setTileUrlFunction', - ol.source.XYZ.prototype.setTileUrlFunction); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'setUrl', - ol.source.XYZ.prototype.setUrl); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'setUrls', - ol.source.XYZ.prototype.setUrls); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'getTileGrid', - ol.source.XYZ.prototype.getTileGrid); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'refresh', - ol.source.XYZ.prototype.refresh); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'getAttributions', - ol.source.XYZ.prototype.getAttributions); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'getLogo', - ol.source.XYZ.prototype.getLogo); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'getProjection', - ol.source.XYZ.prototype.getProjection); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'getState', - ol.source.XYZ.prototype.getState); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'setAttributions', - ol.source.XYZ.prototype.setAttributions); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'get', - ol.source.XYZ.prototype.get); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'getKeys', - ol.source.XYZ.prototype.getKeys); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'getProperties', - ol.source.XYZ.prototype.getProperties); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'set', - ol.source.XYZ.prototype.set); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'setProperties', - ol.source.XYZ.prototype.setProperties); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'unset', - ol.source.XYZ.prototype.unset); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'changed', - ol.source.XYZ.prototype.changed); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'dispatchEvent', - ol.source.XYZ.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'getRevision', - ol.source.XYZ.prototype.getRevision); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'on', - ol.source.XYZ.prototype.on); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'once', - ol.source.XYZ.prototype.once); - -goog.exportProperty( - ol.source.XYZ.prototype, - 'un', - ol.source.XYZ.prototype.un); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'setRenderReprojectionEdges', - ol.source.CartoDB.prototype.setRenderReprojectionEdges); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'setTileGridForProjection', - ol.source.CartoDB.prototype.setTileGridForProjection); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'getTileLoadFunction', - ol.source.CartoDB.prototype.getTileLoadFunction); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'getTileUrlFunction', - ol.source.CartoDB.prototype.getTileUrlFunction); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'getUrls', - ol.source.CartoDB.prototype.getUrls); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'setTileLoadFunction', - ol.source.CartoDB.prototype.setTileLoadFunction); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'setTileUrlFunction', - ol.source.CartoDB.prototype.setTileUrlFunction); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'setUrl', - ol.source.CartoDB.prototype.setUrl); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'setUrls', - ol.source.CartoDB.prototype.setUrls); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'getTileGrid', - ol.source.CartoDB.prototype.getTileGrid); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'refresh', - ol.source.CartoDB.prototype.refresh); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'getAttributions', - ol.source.CartoDB.prototype.getAttributions); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'getLogo', - ol.source.CartoDB.prototype.getLogo); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'getProjection', - ol.source.CartoDB.prototype.getProjection); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'getState', - ol.source.CartoDB.prototype.getState); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'setAttributions', - ol.source.CartoDB.prototype.setAttributions); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'get', - ol.source.CartoDB.prototype.get); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'getKeys', - ol.source.CartoDB.prototype.getKeys); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'getProperties', - ol.source.CartoDB.prototype.getProperties); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'set', - ol.source.CartoDB.prototype.set); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'setProperties', - ol.source.CartoDB.prototype.setProperties); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'unset', - ol.source.CartoDB.prototype.unset); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'changed', - ol.source.CartoDB.prototype.changed); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'dispatchEvent', - ol.source.CartoDB.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'getRevision', - ol.source.CartoDB.prototype.getRevision); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'on', - ol.source.CartoDB.prototype.on); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'once', - ol.source.CartoDB.prototype.once); - -goog.exportProperty( - ol.source.CartoDB.prototype, - 'un', - ol.source.CartoDB.prototype.un); - -goog.exportProperty( - ol.source.Vector.prototype, - 'getAttributions', - ol.source.Vector.prototype.getAttributions); - -goog.exportProperty( - ol.source.Vector.prototype, - 'getLogo', - ol.source.Vector.prototype.getLogo); - -goog.exportProperty( - ol.source.Vector.prototype, - 'getProjection', - ol.source.Vector.prototype.getProjection); - -goog.exportProperty( - ol.source.Vector.prototype, - 'getState', - ol.source.Vector.prototype.getState); - -goog.exportProperty( - ol.source.Vector.prototype, - 'refresh', - ol.source.Vector.prototype.refresh); - -goog.exportProperty( - ol.source.Vector.prototype, - 'setAttributions', - ol.source.Vector.prototype.setAttributions); - -goog.exportProperty( - ol.source.Vector.prototype, - 'get', - ol.source.Vector.prototype.get); - -goog.exportProperty( - ol.source.Vector.prototype, - 'getKeys', - ol.source.Vector.prototype.getKeys); - -goog.exportProperty( - ol.source.Vector.prototype, - 'getProperties', - ol.source.Vector.prototype.getProperties); - -goog.exportProperty( - ol.source.Vector.prototype, - 'set', - ol.source.Vector.prototype.set); - -goog.exportProperty( - ol.source.Vector.prototype, - 'setProperties', - ol.source.Vector.prototype.setProperties); - -goog.exportProperty( - ol.source.Vector.prototype, - 'unset', - ol.source.Vector.prototype.unset); - -goog.exportProperty( - ol.source.Vector.prototype, - 'changed', - ol.source.Vector.prototype.changed); - -goog.exportProperty( - ol.source.Vector.prototype, - 'dispatchEvent', - ol.source.Vector.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.Vector.prototype, - 'getRevision', - ol.source.Vector.prototype.getRevision); - -goog.exportProperty( - ol.source.Vector.prototype, - 'on', - ol.source.Vector.prototype.on); - -goog.exportProperty( - ol.source.Vector.prototype, - 'once', - ol.source.Vector.prototype.once); - -goog.exportProperty( - ol.source.Vector.prototype, - 'un', - ol.source.Vector.prototype.un); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'addFeature', - ol.source.Cluster.prototype.addFeature); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'addFeatures', - ol.source.Cluster.prototype.addFeatures); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'clear', - ol.source.Cluster.prototype.clear); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'forEachFeature', - ol.source.Cluster.prototype.forEachFeature); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'forEachFeatureInExtent', - ol.source.Cluster.prototype.forEachFeatureInExtent); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'forEachFeatureIntersectingExtent', - ol.source.Cluster.prototype.forEachFeatureIntersectingExtent); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getFeaturesCollection', - ol.source.Cluster.prototype.getFeaturesCollection); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getFeatures', - ol.source.Cluster.prototype.getFeatures); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getFeaturesAtCoordinate', - ol.source.Cluster.prototype.getFeaturesAtCoordinate); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getFeaturesInExtent', - ol.source.Cluster.prototype.getFeaturesInExtent); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getClosestFeatureToCoordinate', - ol.source.Cluster.prototype.getClosestFeatureToCoordinate); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getExtent', - ol.source.Cluster.prototype.getExtent); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getFeatureById', - ol.source.Cluster.prototype.getFeatureById); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getFormat', - ol.source.Cluster.prototype.getFormat); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getUrl', - ol.source.Cluster.prototype.getUrl); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'removeFeature', - ol.source.Cluster.prototype.removeFeature); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'setLoader', - ol.source.Cluster.prototype.setLoader); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getAttributions', - ol.source.Cluster.prototype.getAttributions); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getLogo', - ol.source.Cluster.prototype.getLogo); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getProjection', - ol.source.Cluster.prototype.getProjection); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getState', - ol.source.Cluster.prototype.getState); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'refresh', - ol.source.Cluster.prototype.refresh); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'setAttributions', - ol.source.Cluster.prototype.setAttributions); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'get', - ol.source.Cluster.prototype.get); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getKeys', - ol.source.Cluster.prototype.getKeys); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getProperties', - ol.source.Cluster.prototype.getProperties); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'set', - ol.source.Cluster.prototype.set); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'setProperties', - ol.source.Cluster.prototype.setProperties); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'unset', - ol.source.Cluster.prototype.unset); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'changed', - ol.source.Cluster.prototype.changed); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'dispatchEvent', - ol.source.Cluster.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'getRevision', - ol.source.Cluster.prototype.getRevision); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'on', - ol.source.Cluster.prototype.on); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'once', - ol.source.Cluster.prototype.once); - -goog.exportProperty( - ol.source.Cluster.prototype, - 'un', - ol.source.Cluster.prototype.un); - -goog.exportProperty( - ol.source.Image.prototype, - 'getAttributions', - ol.source.Image.prototype.getAttributions); - -goog.exportProperty( - ol.source.Image.prototype, - 'getLogo', - ol.source.Image.prototype.getLogo); - -goog.exportProperty( - ol.source.Image.prototype, - 'getProjection', - ol.source.Image.prototype.getProjection); - -goog.exportProperty( - ol.source.Image.prototype, - 'getState', - ol.source.Image.prototype.getState); - -goog.exportProperty( - ol.source.Image.prototype, - 'refresh', - ol.source.Image.prototype.refresh); - -goog.exportProperty( - ol.source.Image.prototype, - 'setAttributions', - ol.source.Image.prototype.setAttributions); - -goog.exportProperty( - ol.source.Image.prototype, - 'get', - ol.source.Image.prototype.get); - -goog.exportProperty( - ol.source.Image.prototype, - 'getKeys', - ol.source.Image.prototype.getKeys); - -goog.exportProperty( - ol.source.Image.prototype, - 'getProperties', - ol.source.Image.prototype.getProperties); - -goog.exportProperty( - ol.source.Image.prototype, - 'set', - ol.source.Image.prototype.set); - -goog.exportProperty( - ol.source.Image.prototype, - 'setProperties', - ol.source.Image.prototype.setProperties); - -goog.exportProperty( - ol.source.Image.prototype, - 'unset', - ol.source.Image.prototype.unset); - -goog.exportProperty( - ol.source.Image.prototype, - 'changed', - ol.source.Image.prototype.changed); - -goog.exportProperty( - ol.source.Image.prototype, - 'dispatchEvent', - ol.source.Image.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.Image.prototype, - 'getRevision', - ol.source.Image.prototype.getRevision); - -goog.exportProperty( - ol.source.Image.prototype, - 'on', - ol.source.Image.prototype.on); - -goog.exportProperty( - ol.source.Image.prototype, - 'once', - ol.source.Image.prototype.once); - -goog.exportProperty( - ol.source.Image.prototype, - 'un', - ol.source.Image.prototype.un); - -goog.exportProperty( - ol.source.Image.Event.prototype, - 'type', - ol.source.Image.Event.prototype.type); - -goog.exportProperty( - ol.source.Image.Event.prototype, - 'target', - ol.source.Image.Event.prototype.target); - -goog.exportProperty( - ol.source.Image.Event.prototype, - 'preventDefault', - ol.source.Image.Event.prototype.preventDefault); - -goog.exportProperty( - ol.source.Image.Event.prototype, - 'stopPropagation', - ol.source.Image.Event.prototype.stopPropagation); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'getAttributions', - ol.source.ImageArcGISRest.prototype.getAttributions); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'getLogo', - ol.source.ImageArcGISRest.prototype.getLogo); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'getProjection', - ol.source.ImageArcGISRest.prototype.getProjection); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'getState', - ol.source.ImageArcGISRest.prototype.getState); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'refresh', - ol.source.ImageArcGISRest.prototype.refresh); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'setAttributions', - ol.source.ImageArcGISRest.prototype.setAttributions); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'get', - ol.source.ImageArcGISRest.prototype.get); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'getKeys', - ol.source.ImageArcGISRest.prototype.getKeys); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'getProperties', - ol.source.ImageArcGISRest.prototype.getProperties); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'set', - ol.source.ImageArcGISRest.prototype.set); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'setProperties', - ol.source.ImageArcGISRest.prototype.setProperties); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'unset', - ol.source.ImageArcGISRest.prototype.unset); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'changed', - ol.source.ImageArcGISRest.prototype.changed); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'dispatchEvent', - ol.source.ImageArcGISRest.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'getRevision', - ol.source.ImageArcGISRest.prototype.getRevision); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'on', - ol.source.ImageArcGISRest.prototype.on); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'once', - ol.source.ImageArcGISRest.prototype.once); - -goog.exportProperty( - ol.source.ImageArcGISRest.prototype, - 'un', - ol.source.ImageArcGISRest.prototype.un); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'getAttributions', - ol.source.ImageCanvas.prototype.getAttributions); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'getLogo', - ol.source.ImageCanvas.prototype.getLogo); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'getProjection', - ol.source.ImageCanvas.prototype.getProjection); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'getState', - ol.source.ImageCanvas.prototype.getState); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'refresh', - ol.source.ImageCanvas.prototype.refresh); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'setAttributions', - ol.source.ImageCanvas.prototype.setAttributions); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'get', - ol.source.ImageCanvas.prototype.get); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'getKeys', - ol.source.ImageCanvas.prototype.getKeys); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'getProperties', - ol.source.ImageCanvas.prototype.getProperties); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'set', - ol.source.ImageCanvas.prototype.set); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'setProperties', - ol.source.ImageCanvas.prototype.setProperties); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'unset', - ol.source.ImageCanvas.prototype.unset); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'changed', - ol.source.ImageCanvas.prototype.changed); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'dispatchEvent', - ol.source.ImageCanvas.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'getRevision', - ol.source.ImageCanvas.prototype.getRevision); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'on', - ol.source.ImageCanvas.prototype.on); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'once', - ol.source.ImageCanvas.prototype.once); - -goog.exportProperty( - ol.source.ImageCanvas.prototype, - 'un', - ol.source.ImageCanvas.prototype.un); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'getAttributions', - ol.source.ImageMapGuide.prototype.getAttributions); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'getLogo', - ol.source.ImageMapGuide.prototype.getLogo); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'getProjection', - ol.source.ImageMapGuide.prototype.getProjection); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'getState', - ol.source.ImageMapGuide.prototype.getState); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'refresh', - ol.source.ImageMapGuide.prototype.refresh); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'setAttributions', - ol.source.ImageMapGuide.prototype.setAttributions); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'get', - ol.source.ImageMapGuide.prototype.get); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'getKeys', - ol.source.ImageMapGuide.prototype.getKeys); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'getProperties', - ol.source.ImageMapGuide.prototype.getProperties); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'set', - ol.source.ImageMapGuide.prototype.set); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'setProperties', - ol.source.ImageMapGuide.prototype.setProperties); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'unset', - ol.source.ImageMapGuide.prototype.unset); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'changed', - ol.source.ImageMapGuide.prototype.changed); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'dispatchEvent', - ol.source.ImageMapGuide.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'getRevision', - ol.source.ImageMapGuide.prototype.getRevision); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'on', - ol.source.ImageMapGuide.prototype.on); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'once', - ol.source.ImageMapGuide.prototype.once); - -goog.exportProperty( - ol.source.ImageMapGuide.prototype, - 'un', - ol.source.ImageMapGuide.prototype.un); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'getAttributions', - ol.source.ImageStatic.prototype.getAttributions); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'getLogo', - ol.source.ImageStatic.prototype.getLogo); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'getProjection', - ol.source.ImageStatic.prototype.getProjection); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'getState', - ol.source.ImageStatic.prototype.getState); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'refresh', - ol.source.ImageStatic.prototype.refresh); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'setAttributions', - ol.source.ImageStatic.prototype.setAttributions); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'get', - ol.source.ImageStatic.prototype.get); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'getKeys', - ol.source.ImageStatic.prototype.getKeys); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'getProperties', - ol.source.ImageStatic.prototype.getProperties); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'set', - ol.source.ImageStatic.prototype.set); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'setProperties', - ol.source.ImageStatic.prototype.setProperties); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'unset', - ol.source.ImageStatic.prototype.unset); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'changed', - ol.source.ImageStatic.prototype.changed); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'dispatchEvent', - ol.source.ImageStatic.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'getRevision', - ol.source.ImageStatic.prototype.getRevision); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'on', - ol.source.ImageStatic.prototype.on); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'once', - ol.source.ImageStatic.prototype.once); - -goog.exportProperty( - ol.source.ImageStatic.prototype, - 'un', - ol.source.ImageStatic.prototype.un); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'getAttributions', - ol.source.ImageVector.prototype.getAttributions); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'getLogo', - ol.source.ImageVector.prototype.getLogo); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'getProjection', - ol.source.ImageVector.prototype.getProjection); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'getState', - ol.source.ImageVector.prototype.getState); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'refresh', - ol.source.ImageVector.prototype.refresh); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'setAttributions', - ol.source.ImageVector.prototype.setAttributions); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'get', - ol.source.ImageVector.prototype.get); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'getKeys', - ol.source.ImageVector.prototype.getKeys); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'getProperties', - ol.source.ImageVector.prototype.getProperties); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'set', - ol.source.ImageVector.prototype.set); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'setProperties', - ol.source.ImageVector.prototype.setProperties); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'unset', - ol.source.ImageVector.prototype.unset); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'changed', - ol.source.ImageVector.prototype.changed); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'dispatchEvent', - ol.source.ImageVector.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'getRevision', - ol.source.ImageVector.prototype.getRevision); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'on', - ol.source.ImageVector.prototype.on); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'once', - ol.source.ImageVector.prototype.once); - -goog.exportProperty( - ol.source.ImageVector.prototype, - 'un', - ol.source.ImageVector.prototype.un); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'getAttributions', - ol.source.ImageWMS.prototype.getAttributions); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'getLogo', - ol.source.ImageWMS.prototype.getLogo); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'getProjection', - ol.source.ImageWMS.prototype.getProjection); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'getState', - ol.source.ImageWMS.prototype.getState); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'refresh', - ol.source.ImageWMS.prototype.refresh); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'setAttributions', - ol.source.ImageWMS.prototype.setAttributions); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'get', - ol.source.ImageWMS.prototype.get); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'getKeys', - ol.source.ImageWMS.prototype.getKeys); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'getProperties', - ol.source.ImageWMS.prototype.getProperties); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'set', - ol.source.ImageWMS.prototype.set); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'setProperties', - ol.source.ImageWMS.prototype.setProperties); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'unset', - ol.source.ImageWMS.prototype.unset); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'changed', - ol.source.ImageWMS.prototype.changed); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'dispatchEvent', - ol.source.ImageWMS.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'getRevision', - ol.source.ImageWMS.prototype.getRevision); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'on', - ol.source.ImageWMS.prototype.on); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'once', - ol.source.ImageWMS.prototype.once); - -goog.exportProperty( - ol.source.ImageWMS.prototype, - 'un', - ol.source.ImageWMS.prototype.un); - -goog.exportProperty( - ol.source.OSM.prototype, - 'setRenderReprojectionEdges', - ol.source.OSM.prototype.setRenderReprojectionEdges); - -goog.exportProperty( - ol.source.OSM.prototype, - 'setTileGridForProjection', - ol.source.OSM.prototype.setTileGridForProjection); - -goog.exportProperty( - ol.source.OSM.prototype, - 'getTileLoadFunction', - ol.source.OSM.prototype.getTileLoadFunction); - -goog.exportProperty( - ol.source.OSM.prototype, - 'getTileUrlFunction', - ol.source.OSM.prototype.getTileUrlFunction); - -goog.exportProperty( - ol.source.OSM.prototype, - 'getUrls', - ol.source.OSM.prototype.getUrls); - -goog.exportProperty( - ol.source.OSM.prototype, - 'setTileLoadFunction', - ol.source.OSM.prototype.setTileLoadFunction); - -goog.exportProperty( - ol.source.OSM.prototype, - 'setTileUrlFunction', - ol.source.OSM.prototype.setTileUrlFunction); - -goog.exportProperty( - ol.source.OSM.prototype, - 'setUrl', - ol.source.OSM.prototype.setUrl); - -goog.exportProperty( - ol.source.OSM.prototype, - 'setUrls', - ol.source.OSM.prototype.setUrls); - -goog.exportProperty( - ol.source.OSM.prototype, - 'getTileGrid', - ol.source.OSM.prototype.getTileGrid); - -goog.exportProperty( - ol.source.OSM.prototype, - 'refresh', - ol.source.OSM.prototype.refresh); - -goog.exportProperty( - ol.source.OSM.prototype, - 'getAttributions', - ol.source.OSM.prototype.getAttributions); - -goog.exportProperty( - ol.source.OSM.prototype, - 'getLogo', - ol.source.OSM.prototype.getLogo); - -goog.exportProperty( - ol.source.OSM.prototype, - 'getProjection', - ol.source.OSM.prototype.getProjection); - -goog.exportProperty( - ol.source.OSM.prototype, - 'getState', - ol.source.OSM.prototype.getState); - -goog.exportProperty( - ol.source.OSM.prototype, - 'setAttributions', - ol.source.OSM.prototype.setAttributions); - -goog.exportProperty( - ol.source.OSM.prototype, - 'get', - ol.source.OSM.prototype.get); - -goog.exportProperty( - ol.source.OSM.prototype, - 'getKeys', - ol.source.OSM.prototype.getKeys); - -goog.exportProperty( - ol.source.OSM.prototype, - 'getProperties', - ol.source.OSM.prototype.getProperties); - -goog.exportProperty( - ol.source.OSM.prototype, - 'set', - ol.source.OSM.prototype.set); - -goog.exportProperty( - ol.source.OSM.prototype, - 'setProperties', - ol.source.OSM.prototype.setProperties); - -goog.exportProperty( - ol.source.OSM.prototype, - 'unset', - ol.source.OSM.prototype.unset); - -goog.exportProperty( - ol.source.OSM.prototype, - 'changed', - ol.source.OSM.prototype.changed); - -goog.exportProperty( - ol.source.OSM.prototype, - 'dispatchEvent', - ol.source.OSM.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.OSM.prototype, - 'getRevision', - ol.source.OSM.prototype.getRevision); - -goog.exportProperty( - ol.source.OSM.prototype, - 'on', - ol.source.OSM.prototype.on); - -goog.exportProperty( - ol.source.OSM.prototype, - 'once', - ol.source.OSM.prototype.once); - -goog.exportProperty( - ol.source.OSM.prototype, - 'un', - ol.source.OSM.prototype.un); - -goog.exportProperty( - ol.source.Raster.prototype, - 'getAttributions', - ol.source.Raster.prototype.getAttributions); - -goog.exportProperty( - ol.source.Raster.prototype, - 'getLogo', - ol.source.Raster.prototype.getLogo); - -goog.exportProperty( - ol.source.Raster.prototype, - 'getProjection', - ol.source.Raster.prototype.getProjection); - -goog.exportProperty( - ol.source.Raster.prototype, - 'getState', - ol.source.Raster.prototype.getState); - -goog.exportProperty( - ol.source.Raster.prototype, - 'refresh', - ol.source.Raster.prototype.refresh); - -goog.exportProperty( - ol.source.Raster.prototype, - 'setAttributions', - ol.source.Raster.prototype.setAttributions); - -goog.exportProperty( - ol.source.Raster.prototype, - 'get', - ol.source.Raster.prototype.get); - -goog.exportProperty( - ol.source.Raster.prototype, - 'getKeys', - ol.source.Raster.prototype.getKeys); - -goog.exportProperty( - ol.source.Raster.prototype, - 'getProperties', - ol.source.Raster.prototype.getProperties); - -goog.exportProperty( - ol.source.Raster.prototype, - 'set', - ol.source.Raster.prototype.set); - -goog.exportProperty( - ol.source.Raster.prototype, - 'setProperties', - ol.source.Raster.prototype.setProperties); - -goog.exportProperty( - ol.source.Raster.prototype, - 'unset', - ol.source.Raster.prototype.unset); - -goog.exportProperty( - ol.source.Raster.prototype, - 'changed', - ol.source.Raster.prototype.changed); - -goog.exportProperty( - ol.source.Raster.prototype, - 'dispatchEvent', - ol.source.Raster.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.Raster.prototype, - 'getRevision', - ol.source.Raster.prototype.getRevision); - -goog.exportProperty( - ol.source.Raster.prototype, - 'on', - ol.source.Raster.prototype.on); - -goog.exportProperty( - ol.source.Raster.prototype, - 'once', - ol.source.Raster.prototype.once); - -goog.exportProperty( - ol.source.Raster.prototype, - 'un', - ol.source.Raster.prototype.un); - -goog.exportProperty( - ol.source.Raster.Event.prototype, - 'type', - ol.source.Raster.Event.prototype.type); - -goog.exportProperty( - ol.source.Raster.Event.prototype, - 'target', - ol.source.Raster.Event.prototype.target); - -goog.exportProperty( - ol.source.Raster.Event.prototype, - 'preventDefault', - ol.source.Raster.Event.prototype.preventDefault); - -goog.exportProperty( - ol.source.Raster.Event.prototype, - 'stopPropagation', - ol.source.Raster.Event.prototype.stopPropagation); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'setRenderReprojectionEdges', - ol.source.Stamen.prototype.setRenderReprojectionEdges); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'setTileGridForProjection', - ol.source.Stamen.prototype.setTileGridForProjection); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'getTileLoadFunction', - ol.source.Stamen.prototype.getTileLoadFunction); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'getTileUrlFunction', - ol.source.Stamen.prototype.getTileUrlFunction); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'getUrls', - ol.source.Stamen.prototype.getUrls); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'setTileLoadFunction', - ol.source.Stamen.prototype.setTileLoadFunction); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'setTileUrlFunction', - ol.source.Stamen.prototype.setTileUrlFunction); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'setUrl', - ol.source.Stamen.prototype.setUrl); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'setUrls', - ol.source.Stamen.prototype.setUrls); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'getTileGrid', - ol.source.Stamen.prototype.getTileGrid); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'refresh', - ol.source.Stamen.prototype.refresh); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'getAttributions', - ol.source.Stamen.prototype.getAttributions); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'getLogo', - ol.source.Stamen.prototype.getLogo); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'getProjection', - ol.source.Stamen.prototype.getProjection); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'getState', - ol.source.Stamen.prototype.getState); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'setAttributions', - ol.source.Stamen.prototype.setAttributions); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'get', - ol.source.Stamen.prototype.get); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'getKeys', - ol.source.Stamen.prototype.getKeys); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'getProperties', - ol.source.Stamen.prototype.getProperties); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'set', - ol.source.Stamen.prototype.set); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'setProperties', - ol.source.Stamen.prototype.setProperties); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'unset', - ol.source.Stamen.prototype.unset); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'changed', - ol.source.Stamen.prototype.changed); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'dispatchEvent', - ol.source.Stamen.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'getRevision', - ol.source.Stamen.prototype.getRevision); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'on', - ol.source.Stamen.prototype.on); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'once', - ol.source.Stamen.prototype.once); - -goog.exportProperty( - ol.source.Stamen.prototype, - 'un', - ol.source.Stamen.prototype.un); - -goog.exportProperty( - ol.source.Tile.Event.prototype, - 'type', - ol.source.Tile.Event.prototype.type); - -goog.exportProperty( - ol.source.Tile.Event.prototype, - 'target', - ol.source.Tile.Event.prototype.target); - -goog.exportProperty( - ol.source.Tile.Event.prototype, - 'preventDefault', - ol.source.Tile.Event.prototype.preventDefault); - -goog.exportProperty( - ol.source.Tile.Event.prototype, - 'stopPropagation', - ol.source.Tile.Event.prototype.stopPropagation); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'setRenderReprojectionEdges', - ol.source.TileArcGISRest.prototype.setRenderReprojectionEdges); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'setTileGridForProjection', - ol.source.TileArcGISRest.prototype.setTileGridForProjection); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'getTileLoadFunction', - ol.source.TileArcGISRest.prototype.getTileLoadFunction); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'getTileUrlFunction', - ol.source.TileArcGISRest.prototype.getTileUrlFunction); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'getUrls', - ol.source.TileArcGISRest.prototype.getUrls); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'setTileLoadFunction', - ol.source.TileArcGISRest.prototype.setTileLoadFunction); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'setTileUrlFunction', - ol.source.TileArcGISRest.prototype.setTileUrlFunction); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'setUrl', - ol.source.TileArcGISRest.prototype.setUrl); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'setUrls', - ol.source.TileArcGISRest.prototype.setUrls); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'getTileGrid', - ol.source.TileArcGISRest.prototype.getTileGrid); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'refresh', - ol.source.TileArcGISRest.prototype.refresh); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'getAttributions', - ol.source.TileArcGISRest.prototype.getAttributions); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'getLogo', - ol.source.TileArcGISRest.prototype.getLogo); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'getProjection', - ol.source.TileArcGISRest.prototype.getProjection); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'getState', - ol.source.TileArcGISRest.prototype.getState); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'setAttributions', - ol.source.TileArcGISRest.prototype.setAttributions); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'get', - ol.source.TileArcGISRest.prototype.get); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'getKeys', - ol.source.TileArcGISRest.prototype.getKeys); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'getProperties', - ol.source.TileArcGISRest.prototype.getProperties); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'set', - ol.source.TileArcGISRest.prototype.set); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'setProperties', - ol.source.TileArcGISRest.prototype.setProperties); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'unset', - ol.source.TileArcGISRest.prototype.unset); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'changed', - ol.source.TileArcGISRest.prototype.changed); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'dispatchEvent', - ol.source.TileArcGISRest.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'getRevision', - ol.source.TileArcGISRest.prototype.getRevision); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'on', - ol.source.TileArcGISRest.prototype.on); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'once', - ol.source.TileArcGISRest.prototype.once); - -goog.exportProperty( - ol.source.TileArcGISRest.prototype, - 'un', - ol.source.TileArcGISRest.prototype.un); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'getTileGrid', - ol.source.TileDebug.prototype.getTileGrid); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'refresh', - ol.source.TileDebug.prototype.refresh); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'getAttributions', - ol.source.TileDebug.prototype.getAttributions); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'getLogo', - ol.source.TileDebug.prototype.getLogo); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'getProjection', - ol.source.TileDebug.prototype.getProjection); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'getState', - ol.source.TileDebug.prototype.getState); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'setAttributions', - ol.source.TileDebug.prototype.setAttributions); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'get', - ol.source.TileDebug.prototype.get); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'getKeys', - ol.source.TileDebug.prototype.getKeys); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'getProperties', - ol.source.TileDebug.prototype.getProperties); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'set', - ol.source.TileDebug.prototype.set); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'setProperties', - ol.source.TileDebug.prototype.setProperties); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'unset', - ol.source.TileDebug.prototype.unset); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'changed', - ol.source.TileDebug.prototype.changed); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'dispatchEvent', - ol.source.TileDebug.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'getRevision', - ol.source.TileDebug.prototype.getRevision); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'on', - ol.source.TileDebug.prototype.on); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'once', - ol.source.TileDebug.prototype.once); - -goog.exportProperty( - ol.source.TileDebug.prototype, - 'un', - ol.source.TileDebug.prototype.un); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'setRenderReprojectionEdges', - ol.source.TileJSON.prototype.setRenderReprojectionEdges); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'setTileGridForProjection', - ol.source.TileJSON.prototype.setTileGridForProjection); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'getTileLoadFunction', - ol.source.TileJSON.prototype.getTileLoadFunction); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'getTileUrlFunction', - ol.source.TileJSON.prototype.getTileUrlFunction); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'getUrls', - ol.source.TileJSON.prototype.getUrls); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'setTileLoadFunction', - ol.source.TileJSON.prototype.setTileLoadFunction); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'setTileUrlFunction', - ol.source.TileJSON.prototype.setTileUrlFunction); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'setUrl', - ol.source.TileJSON.prototype.setUrl); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'setUrls', - ol.source.TileJSON.prototype.setUrls); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'getTileGrid', - ol.source.TileJSON.prototype.getTileGrid); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'refresh', - ol.source.TileJSON.prototype.refresh); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'getAttributions', - ol.source.TileJSON.prototype.getAttributions); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'getLogo', - ol.source.TileJSON.prototype.getLogo); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'getProjection', - ol.source.TileJSON.prototype.getProjection); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'getState', - ol.source.TileJSON.prototype.getState); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'setAttributions', - ol.source.TileJSON.prototype.setAttributions); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'get', - ol.source.TileJSON.prototype.get); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'getKeys', - ol.source.TileJSON.prototype.getKeys); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'getProperties', - ol.source.TileJSON.prototype.getProperties); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'set', - ol.source.TileJSON.prototype.set); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'setProperties', - ol.source.TileJSON.prototype.setProperties); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'unset', - ol.source.TileJSON.prototype.unset); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'changed', - ol.source.TileJSON.prototype.changed); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'dispatchEvent', - ol.source.TileJSON.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'getRevision', - ol.source.TileJSON.prototype.getRevision); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'on', - ol.source.TileJSON.prototype.on); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'once', - ol.source.TileJSON.prototype.once); - -goog.exportProperty( - ol.source.TileJSON.prototype, - 'un', - ol.source.TileJSON.prototype.un); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'getTileGrid', - ol.source.TileUTFGrid.prototype.getTileGrid); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'refresh', - ol.source.TileUTFGrid.prototype.refresh); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'getAttributions', - ol.source.TileUTFGrid.prototype.getAttributions); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'getLogo', - ol.source.TileUTFGrid.prototype.getLogo); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'getProjection', - ol.source.TileUTFGrid.prototype.getProjection); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'getState', - ol.source.TileUTFGrid.prototype.getState); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'setAttributions', - ol.source.TileUTFGrid.prototype.setAttributions); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'get', - ol.source.TileUTFGrid.prototype.get); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'getKeys', - ol.source.TileUTFGrid.prototype.getKeys); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'getProperties', - ol.source.TileUTFGrid.prototype.getProperties); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'set', - ol.source.TileUTFGrid.prototype.set); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'setProperties', - ol.source.TileUTFGrid.prototype.setProperties); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'unset', - ol.source.TileUTFGrid.prototype.unset); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'changed', - ol.source.TileUTFGrid.prototype.changed); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'dispatchEvent', - ol.source.TileUTFGrid.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'getRevision', - ol.source.TileUTFGrid.prototype.getRevision); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'on', - ol.source.TileUTFGrid.prototype.on); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'once', - ol.source.TileUTFGrid.prototype.once); - -goog.exportProperty( - ol.source.TileUTFGrid.prototype, - 'un', - ol.source.TileUTFGrid.prototype.un); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'setRenderReprojectionEdges', - ol.source.TileWMS.prototype.setRenderReprojectionEdges); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'setTileGridForProjection', - ol.source.TileWMS.prototype.setTileGridForProjection); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'getTileLoadFunction', - ol.source.TileWMS.prototype.getTileLoadFunction); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'getTileUrlFunction', - ol.source.TileWMS.prototype.getTileUrlFunction); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'getUrls', - ol.source.TileWMS.prototype.getUrls); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'setTileLoadFunction', - ol.source.TileWMS.prototype.setTileLoadFunction); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'setTileUrlFunction', - ol.source.TileWMS.prototype.setTileUrlFunction); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'setUrl', - ol.source.TileWMS.prototype.setUrl); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'setUrls', - ol.source.TileWMS.prototype.setUrls); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'getTileGrid', - ol.source.TileWMS.prototype.getTileGrid); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'refresh', - ol.source.TileWMS.prototype.refresh); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'getAttributions', - ol.source.TileWMS.prototype.getAttributions); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'getLogo', - ol.source.TileWMS.prototype.getLogo); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'getProjection', - ol.source.TileWMS.prototype.getProjection); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'getState', - ol.source.TileWMS.prototype.getState); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'setAttributions', - ol.source.TileWMS.prototype.setAttributions); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'get', - ol.source.TileWMS.prototype.get); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'getKeys', - ol.source.TileWMS.prototype.getKeys); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'getProperties', - ol.source.TileWMS.prototype.getProperties); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'set', - ol.source.TileWMS.prototype.set); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'setProperties', - ol.source.TileWMS.prototype.setProperties); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'unset', - ol.source.TileWMS.prototype.unset); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'changed', - ol.source.TileWMS.prototype.changed); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'dispatchEvent', - ol.source.TileWMS.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'getRevision', - ol.source.TileWMS.prototype.getRevision); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'on', - ol.source.TileWMS.prototype.on); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'once', - ol.source.TileWMS.prototype.once); - -goog.exportProperty( - ol.source.TileWMS.prototype, - 'un', - ol.source.TileWMS.prototype.un); - -goog.exportProperty( - ol.source.Vector.Event.prototype, - 'type', - ol.source.Vector.Event.prototype.type); - -goog.exportProperty( - ol.source.Vector.Event.prototype, - 'target', - ol.source.Vector.Event.prototype.target); - -goog.exportProperty( - ol.source.Vector.Event.prototype, - 'preventDefault', - ol.source.Vector.Event.prototype.preventDefault); - -goog.exportProperty( - ol.source.Vector.Event.prototype, - 'stopPropagation', - ol.source.Vector.Event.prototype.stopPropagation); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'getTileLoadFunction', - ol.source.VectorTile.prototype.getTileLoadFunction); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'getTileUrlFunction', - ol.source.VectorTile.prototype.getTileUrlFunction); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'getUrls', - ol.source.VectorTile.prototype.getUrls); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'setTileLoadFunction', - ol.source.VectorTile.prototype.setTileLoadFunction); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'setTileUrlFunction', - ol.source.VectorTile.prototype.setTileUrlFunction); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'setUrl', - ol.source.VectorTile.prototype.setUrl); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'setUrls', - ol.source.VectorTile.prototype.setUrls); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'getTileGrid', - ol.source.VectorTile.prototype.getTileGrid); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'refresh', - ol.source.VectorTile.prototype.refresh); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'getAttributions', - ol.source.VectorTile.prototype.getAttributions); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'getLogo', - ol.source.VectorTile.prototype.getLogo); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'getProjection', - ol.source.VectorTile.prototype.getProjection); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'getState', - ol.source.VectorTile.prototype.getState); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'setAttributions', - ol.source.VectorTile.prototype.setAttributions); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'get', - ol.source.VectorTile.prototype.get); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'getKeys', - ol.source.VectorTile.prototype.getKeys); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'getProperties', - ol.source.VectorTile.prototype.getProperties); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'set', - ol.source.VectorTile.prototype.set); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'setProperties', - ol.source.VectorTile.prototype.setProperties); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'unset', - ol.source.VectorTile.prototype.unset); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'changed', - ol.source.VectorTile.prototype.changed); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'dispatchEvent', - ol.source.VectorTile.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'getRevision', - ol.source.VectorTile.prototype.getRevision); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'on', - ol.source.VectorTile.prototype.on); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'once', - ol.source.VectorTile.prototype.once); - -goog.exportProperty( - ol.source.VectorTile.prototype, - 'un', - ol.source.VectorTile.prototype.un); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'setRenderReprojectionEdges', - ol.source.WMTS.prototype.setRenderReprojectionEdges); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'setTileGridForProjection', - ol.source.WMTS.prototype.setTileGridForProjection); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getTileLoadFunction', - ol.source.WMTS.prototype.getTileLoadFunction); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getTileUrlFunction', - ol.source.WMTS.prototype.getTileUrlFunction); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getUrls', - ol.source.WMTS.prototype.getUrls); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'setTileLoadFunction', - ol.source.WMTS.prototype.setTileLoadFunction); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'setTileUrlFunction', - ol.source.WMTS.prototype.setTileUrlFunction); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'setUrl', - ol.source.WMTS.prototype.setUrl); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'setUrls', - ol.source.WMTS.prototype.setUrls); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getTileGrid', - ol.source.WMTS.prototype.getTileGrid); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'refresh', - ol.source.WMTS.prototype.refresh); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getAttributions', - ol.source.WMTS.prototype.getAttributions); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getLogo', - ol.source.WMTS.prototype.getLogo); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getProjection', - ol.source.WMTS.prototype.getProjection); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getState', - ol.source.WMTS.prototype.getState); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'setAttributions', - ol.source.WMTS.prototype.setAttributions); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'get', - ol.source.WMTS.prototype.get); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getKeys', - ol.source.WMTS.prototype.getKeys); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getProperties', - ol.source.WMTS.prototype.getProperties); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'set', - ol.source.WMTS.prototype.set); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'setProperties', - ol.source.WMTS.prototype.setProperties); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'unset', - ol.source.WMTS.prototype.unset); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'changed', - ol.source.WMTS.prototype.changed); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'dispatchEvent', - ol.source.WMTS.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'getRevision', - ol.source.WMTS.prototype.getRevision); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'on', - ol.source.WMTS.prototype.on); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'once', - ol.source.WMTS.prototype.once); - -goog.exportProperty( - ol.source.WMTS.prototype, - 'un', - ol.source.WMTS.prototype.un); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'setRenderReprojectionEdges', - ol.source.Zoomify.prototype.setRenderReprojectionEdges); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'setTileGridForProjection', - ol.source.Zoomify.prototype.setTileGridForProjection); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'getTileLoadFunction', - ol.source.Zoomify.prototype.getTileLoadFunction); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'getTileUrlFunction', - ol.source.Zoomify.prototype.getTileUrlFunction); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'getUrls', - ol.source.Zoomify.prototype.getUrls); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'setTileLoadFunction', - ol.source.Zoomify.prototype.setTileLoadFunction); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'setTileUrlFunction', - ol.source.Zoomify.prototype.setTileUrlFunction); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'setUrl', - ol.source.Zoomify.prototype.setUrl); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'setUrls', - ol.source.Zoomify.prototype.setUrls); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'getTileGrid', - ol.source.Zoomify.prototype.getTileGrid); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'refresh', - ol.source.Zoomify.prototype.refresh); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'getAttributions', - ol.source.Zoomify.prototype.getAttributions); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'getLogo', - ol.source.Zoomify.prototype.getLogo); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'getProjection', - ol.source.Zoomify.prototype.getProjection); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'getState', - ol.source.Zoomify.prototype.getState); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'setAttributions', - ol.source.Zoomify.prototype.setAttributions); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'get', - ol.source.Zoomify.prototype.get); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'getKeys', - ol.source.Zoomify.prototype.getKeys); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'getProperties', - ol.source.Zoomify.prototype.getProperties); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'set', - ol.source.Zoomify.prototype.set); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'setProperties', - ol.source.Zoomify.prototype.setProperties); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'unset', - ol.source.Zoomify.prototype.unset); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'changed', - ol.source.Zoomify.prototype.changed); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'dispatchEvent', - ol.source.Zoomify.prototype.dispatchEvent); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'getRevision', - ol.source.Zoomify.prototype.getRevision); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'on', - ol.source.Zoomify.prototype.on); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'once', - ol.source.Zoomify.prototype.once); - -goog.exportProperty( - ol.source.Zoomify.prototype, - 'un', - ol.source.Zoomify.prototype.un); - -goog.exportProperty( - ol.reproj.Tile.prototype, - 'getTileCoord', - ol.reproj.Tile.prototype.getTileCoord); - -goog.exportProperty( - ol.reproj.Tile.prototype, - 'load', - ol.reproj.Tile.prototype.load); - -goog.exportProperty( - ol.renderer.Layer.prototype, - 'changed', - ol.renderer.Layer.prototype.changed); - -goog.exportProperty( - ol.renderer.Layer.prototype, - 'dispatchEvent', - ol.renderer.Layer.prototype.dispatchEvent); - -goog.exportProperty( - ol.renderer.Layer.prototype, - 'getRevision', - ol.renderer.Layer.prototype.getRevision); - -goog.exportProperty( - ol.renderer.Layer.prototype, - 'on', - ol.renderer.Layer.prototype.on); - -goog.exportProperty( - ol.renderer.Layer.prototype, - 'once', - ol.renderer.Layer.prototype.once); - -goog.exportProperty( - ol.renderer.Layer.prototype, - 'un', - ol.renderer.Layer.prototype.un); - -goog.exportProperty( - ol.renderer.webgl.Layer.prototype, - 'changed', - ol.renderer.webgl.Layer.prototype.changed); - -goog.exportProperty( - ol.renderer.webgl.Layer.prototype, - 'dispatchEvent', - ol.renderer.webgl.Layer.prototype.dispatchEvent); - -goog.exportProperty( - ol.renderer.webgl.Layer.prototype, - 'getRevision', - ol.renderer.webgl.Layer.prototype.getRevision); - -goog.exportProperty( - ol.renderer.webgl.Layer.prototype, - 'on', - ol.renderer.webgl.Layer.prototype.on); - -goog.exportProperty( - ol.renderer.webgl.Layer.prototype, - 'once', - ol.renderer.webgl.Layer.prototype.once); - -goog.exportProperty( - ol.renderer.webgl.Layer.prototype, - 'un', - ol.renderer.webgl.Layer.prototype.un); - -goog.exportProperty( - ol.renderer.webgl.ImageLayer.prototype, - 'changed', - ol.renderer.webgl.ImageLayer.prototype.changed); - -goog.exportProperty( - ol.renderer.webgl.ImageLayer.prototype, - 'dispatchEvent', - ol.renderer.webgl.ImageLayer.prototype.dispatchEvent); - -goog.exportProperty( - ol.renderer.webgl.ImageLayer.prototype, - 'getRevision', - ol.renderer.webgl.ImageLayer.prototype.getRevision); - -goog.exportProperty( - ol.renderer.webgl.ImageLayer.prototype, - 'on', - ol.renderer.webgl.ImageLayer.prototype.on); - -goog.exportProperty( - ol.renderer.webgl.ImageLayer.prototype, - 'once', - ol.renderer.webgl.ImageLayer.prototype.once); - -goog.exportProperty( - ol.renderer.webgl.ImageLayer.prototype, - 'un', - ol.renderer.webgl.ImageLayer.prototype.un); - -goog.exportProperty( - ol.renderer.webgl.TileLayer.prototype, - 'changed', - ol.renderer.webgl.TileLayer.prototype.changed); - -goog.exportProperty( - ol.renderer.webgl.TileLayer.prototype, - 'dispatchEvent', - ol.renderer.webgl.TileLayer.prototype.dispatchEvent); - -goog.exportProperty( - ol.renderer.webgl.TileLayer.prototype, - 'getRevision', - ol.renderer.webgl.TileLayer.prototype.getRevision); - -goog.exportProperty( - ol.renderer.webgl.TileLayer.prototype, - 'on', - ol.renderer.webgl.TileLayer.prototype.on); - -goog.exportProperty( - ol.renderer.webgl.TileLayer.prototype, - 'once', - ol.renderer.webgl.TileLayer.prototype.once); - -goog.exportProperty( - ol.renderer.webgl.TileLayer.prototype, - 'un', - ol.renderer.webgl.TileLayer.prototype.un); - -goog.exportProperty( - ol.renderer.webgl.VectorLayer.prototype, - 'changed', - ol.renderer.webgl.VectorLayer.prototype.changed); - -goog.exportProperty( - ol.renderer.webgl.VectorLayer.prototype, - 'dispatchEvent', - ol.renderer.webgl.VectorLayer.prototype.dispatchEvent); - -goog.exportProperty( - ol.renderer.webgl.VectorLayer.prototype, - 'getRevision', - ol.renderer.webgl.VectorLayer.prototype.getRevision); - -goog.exportProperty( - ol.renderer.webgl.VectorLayer.prototype, - 'on', - ol.renderer.webgl.VectorLayer.prototype.on); - -goog.exportProperty( - ol.renderer.webgl.VectorLayer.prototype, - 'once', - ol.renderer.webgl.VectorLayer.prototype.once); - -goog.exportProperty( - ol.renderer.webgl.VectorLayer.prototype, - 'un', - ol.renderer.webgl.VectorLayer.prototype.un); - -goog.exportProperty( - ol.renderer.canvas.Layer.prototype, - 'changed', - ol.renderer.canvas.Layer.prototype.changed); - -goog.exportProperty( - ol.renderer.canvas.Layer.prototype, - 'dispatchEvent', - ol.renderer.canvas.Layer.prototype.dispatchEvent); - -goog.exportProperty( - ol.renderer.canvas.Layer.prototype, - 'getRevision', - ol.renderer.canvas.Layer.prototype.getRevision); - -goog.exportProperty( - ol.renderer.canvas.Layer.prototype, - 'on', - ol.renderer.canvas.Layer.prototype.on); - -goog.exportProperty( - ol.renderer.canvas.Layer.prototype, - 'once', - ol.renderer.canvas.Layer.prototype.once); - -goog.exportProperty( - ol.renderer.canvas.Layer.prototype, - 'un', - ol.renderer.canvas.Layer.prototype.un); - -goog.exportProperty( - ol.renderer.canvas.IntermediateCanvas.prototype, - 'changed', - ol.renderer.canvas.IntermediateCanvas.prototype.changed); - -goog.exportProperty( - ol.renderer.canvas.IntermediateCanvas.prototype, - 'dispatchEvent', - ol.renderer.canvas.IntermediateCanvas.prototype.dispatchEvent); - -goog.exportProperty( - ol.renderer.canvas.IntermediateCanvas.prototype, - 'getRevision', - ol.renderer.canvas.IntermediateCanvas.prototype.getRevision); - -goog.exportProperty( - ol.renderer.canvas.IntermediateCanvas.prototype, - 'on', - ol.renderer.canvas.IntermediateCanvas.prototype.on); - -goog.exportProperty( - ol.renderer.canvas.IntermediateCanvas.prototype, - 'once', - ol.renderer.canvas.IntermediateCanvas.prototype.once); - -goog.exportProperty( - ol.renderer.canvas.IntermediateCanvas.prototype, - 'un', - ol.renderer.canvas.IntermediateCanvas.prototype.un); - -goog.exportProperty( - ol.renderer.canvas.ImageLayer.prototype, - 'changed', - ol.renderer.canvas.ImageLayer.prototype.changed); - -goog.exportProperty( - ol.renderer.canvas.ImageLayer.prototype, - 'dispatchEvent', - ol.renderer.canvas.ImageLayer.prototype.dispatchEvent); - -goog.exportProperty( - ol.renderer.canvas.ImageLayer.prototype, - 'getRevision', - ol.renderer.canvas.ImageLayer.prototype.getRevision); - -goog.exportProperty( - ol.renderer.canvas.ImageLayer.prototype, - 'on', - ol.renderer.canvas.ImageLayer.prototype.on); - -goog.exportProperty( - ol.renderer.canvas.ImageLayer.prototype, - 'once', - ol.renderer.canvas.ImageLayer.prototype.once); - -goog.exportProperty( - ol.renderer.canvas.ImageLayer.prototype, - 'un', - ol.renderer.canvas.ImageLayer.prototype.un); - -goog.exportProperty( - ol.renderer.canvas.TileLayer.prototype, - 'changed', - ol.renderer.canvas.TileLayer.prototype.changed); - -goog.exportProperty( - ol.renderer.canvas.TileLayer.prototype, - 'dispatchEvent', - ol.renderer.canvas.TileLayer.prototype.dispatchEvent); - -goog.exportProperty( - ol.renderer.canvas.TileLayer.prototype, - 'getRevision', - ol.renderer.canvas.TileLayer.prototype.getRevision); - -goog.exportProperty( - ol.renderer.canvas.TileLayer.prototype, - 'on', - ol.renderer.canvas.TileLayer.prototype.on); - -goog.exportProperty( - ol.renderer.canvas.TileLayer.prototype, - 'once', - ol.renderer.canvas.TileLayer.prototype.once); - -goog.exportProperty( - ol.renderer.canvas.TileLayer.prototype, - 'un', - ol.renderer.canvas.TileLayer.prototype.un); - -goog.exportProperty( - ol.renderer.canvas.VectorLayer.prototype, - 'changed', - ol.renderer.canvas.VectorLayer.prototype.changed); - -goog.exportProperty( - ol.renderer.canvas.VectorLayer.prototype, - 'dispatchEvent', - ol.renderer.canvas.VectorLayer.prototype.dispatchEvent); - -goog.exportProperty( - ol.renderer.canvas.VectorLayer.prototype, - 'getRevision', - ol.renderer.canvas.VectorLayer.prototype.getRevision); - -goog.exportProperty( - ol.renderer.canvas.VectorLayer.prototype, - 'on', - ol.renderer.canvas.VectorLayer.prototype.on); - -goog.exportProperty( - ol.renderer.canvas.VectorLayer.prototype, - 'once', - ol.renderer.canvas.VectorLayer.prototype.once); - -goog.exportProperty( - ol.renderer.canvas.VectorLayer.prototype, - 'un', - ol.renderer.canvas.VectorLayer.prototype.un); - -goog.exportProperty( - ol.renderer.canvas.VectorTileLayer.prototype, - 'changed', - ol.renderer.canvas.VectorTileLayer.prototype.changed); - -goog.exportProperty( - ol.renderer.canvas.VectorTileLayer.prototype, - 'dispatchEvent', - ol.renderer.canvas.VectorTileLayer.prototype.dispatchEvent); - -goog.exportProperty( - ol.renderer.canvas.VectorTileLayer.prototype, - 'getRevision', - ol.renderer.canvas.VectorTileLayer.prototype.getRevision); - -goog.exportProperty( - ol.renderer.canvas.VectorTileLayer.prototype, - 'on', - ol.renderer.canvas.VectorTileLayer.prototype.on); - -goog.exportProperty( - ol.renderer.canvas.VectorTileLayer.prototype, - 'once', - ol.renderer.canvas.VectorTileLayer.prototype.once); - -goog.exportProperty( - ol.renderer.canvas.VectorTileLayer.prototype, - 'un', - ol.renderer.canvas.VectorTileLayer.prototype.un); - -goog.exportProperty( - ol.render.Event.prototype, - 'type', - ol.render.Event.prototype.type); - -goog.exportProperty( - ol.render.Event.prototype, - 'target', - ol.render.Event.prototype.target); - -goog.exportProperty( - ol.render.Event.prototype, - 'preventDefault', - ol.render.Event.prototype.preventDefault); - -goog.exportProperty( - ol.render.Event.prototype, - 'stopPropagation', - ol.render.Event.prototype.stopPropagation); - -goog.exportProperty( - ol.pointer.PointerEvent.prototype, - 'type', - ol.pointer.PointerEvent.prototype.type); - -goog.exportProperty( - ol.pointer.PointerEvent.prototype, - 'target', - ol.pointer.PointerEvent.prototype.target); - -goog.exportProperty( - ol.pointer.PointerEvent.prototype, - 'preventDefault', - ol.pointer.PointerEvent.prototype.preventDefault); - -goog.exportProperty( - ol.pointer.PointerEvent.prototype, - 'stopPropagation', - ol.pointer.PointerEvent.prototype.stopPropagation); - -goog.exportProperty( - ol.layer.Base.prototype, - 'get', - ol.layer.Base.prototype.get); - -goog.exportProperty( - ol.layer.Base.prototype, - 'getKeys', - ol.layer.Base.prototype.getKeys); - -goog.exportProperty( - ol.layer.Base.prototype, - 'getProperties', - ol.layer.Base.prototype.getProperties); - -goog.exportProperty( - ol.layer.Base.prototype, - 'set', - ol.layer.Base.prototype.set); - -goog.exportProperty( - ol.layer.Base.prototype, - 'setProperties', - ol.layer.Base.prototype.setProperties); - -goog.exportProperty( - ol.layer.Base.prototype, - 'unset', - ol.layer.Base.prototype.unset); - -goog.exportProperty( - ol.layer.Base.prototype, - 'changed', - ol.layer.Base.prototype.changed); - -goog.exportProperty( - ol.layer.Base.prototype, - 'dispatchEvent', - ol.layer.Base.prototype.dispatchEvent); - -goog.exportProperty( - ol.layer.Base.prototype, - 'getRevision', - ol.layer.Base.prototype.getRevision); - -goog.exportProperty( - ol.layer.Base.prototype, - 'on', - ol.layer.Base.prototype.on); - -goog.exportProperty( - ol.layer.Base.prototype, - 'once', - ol.layer.Base.prototype.once); - -goog.exportProperty( - ol.layer.Base.prototype, - 'un', - ol.layer.Base.prototype.un); - -goog.exportProperty( - ol.layer.Group.prototype, - 'getExtent', - ol.layer.Group.prototype.getExtent); - -goog.exportProperty( - ol.layer.Group.prototype, - 'getMaxResolution', - ol.layer.Group.prototype.getMaxResolution); - -goog.exportProperty( - ol.layer.Group.prototype, - 'getMinResolution', - ol.layer.Group.prototype.getMinResolution); - -goog.exportProperty( - ol.layer.Group.prototype, - 'getOpacity', - ol.layer.Group.prototype.getOpacity); - -goog.exportProperty( - ol.layer.Group.prototype, - 'getVisible', - ol.layer.Group.prototype.getVisible); - -goog.exportProperty( - ol.layer.Group.prototype, - 'getZIndex', - ol.layer.Group.prototype.getZIndex); - -goog.exportProperty( - ol.layer.Group.prototype, - 'setExtent', - ol.layer.Group.prototype.setExtent); - -goog.exportProperty( - ol.layer.Group.prototype, - 'setMaxResolution', - ol.layer.Group.prototype.setMaxResolution); - -goog.exportProperty( - ol.layer.Group.prototype, - 'setMinResolution', - ol.layer.Group.prototype.setMinResolution); - -goog.exportProperty( - ol.layer.Group.prototype, - 'setOpacity', - ol.layer.Group.prototype.setOpacity); - -goog.exportProperty( - ol.layer.Group.prototype, - 'setVisible', - ol.layer.Group.prototype.setVisible); - -goog.exportProperty( - ol.layer.Group.prototype, - 'setZIndex', - ol.layer.Group.prototype.setZIndex); - -goog.exportProperty( - ol.layer.Group.prototype, - 'get', - ol.layer.Group.prototype.get); - -goog.exportProperty( - ol.layer.Group.prototype, - 'getKeys', - ol.layer.Group.prototype.getKeys); - -goog.exportProperty( - ol.layer.Group.prototype, - 'getProperties', - ol.layer.Group.prototype.getProperties); - -goog.exportProperty( - ol.layer.Group.prototype, - 'set', - ol.layer.Group.prototype.set); - -goog.exportProperty( - ol.layer.Group.prototype, - 'setProperties', - ol.layer.Group.prototype.setProperties); - -goog.exportProperty( - ol.layer.Group.prototype, - 'unset', - ol.layer.Group.prototype.unset); - -goog.exportProperty( - ol.layer.Group.prototype, - 'changed', - ol.layer.Group.prototype.changed); - -goog.exportProperty( - ol.layer.Group.prototype, - 'dispatchEvent', - ol.layer.Group.prototype.dispatchEvent); - -goog.exportProperty( - ol.layer.Group.prototype, - 'getRevision', - ol.layer.Group.prototype.getRevision); - -goog.exportProperty( - ol.layer.Group.prototype, - 'on', - ol.layer.Group.prototype.on); - -goog.exportProperty( - ol.layer.Group.prototype, - 'once', - ol.layer.Group.prototype.once); - -goog.exportProperty( - ol.layer.Group.prototype, - 'un', - ol.layer.Group.prototype.un); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'getExtent', - ol.layer.Layer.prototype.getExtent); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'getMaxResolution', - ol.layer.Layer.prototype.getMaxResolution); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'getMinResolution', - ol.layer.Layer.prototype.getMinResolution); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'getOpacity', - ol.layer.Layer.prototype.getOpacity); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'getVisible', - ol.layer.Layer.prototype.getVisible); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'getZIndex', - ol.layer.Layer.prototype.getZIndex); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'setExtent', - ol.layer.Layer.prototype.setExtent); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'setMaxResolution', - ol.layer.Layer.prototype.setMaxResolution); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'setMinResolution', - ol.layer.Layer.prototype.setMinResolution); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'setOpacity', - ol.layer.Layer.prototype.setOpacity); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'setVisible', - ol.layer.Layer.prototype.setVisible); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'setZIndex', - ol.layer.Layer.prototype.setZIndex); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'get', - ol.layer.Layer.prototype.get); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'getKeys', - ol.layer.Layer.prototype.getKeys); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'getProperties', - ol.layer.Layer.prototype.getProperties); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'set', - ol.layer.Layer.prototype.set); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'setProperties', - ol.layer.Layer.prototype.setProperties); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'unset', - ol.layer.Layer.prototype.unset); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'changed', - ol.layer.Layer.prototype.changed); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'dispatchEvent', - ol.layer.Layer.prototype.dispatchEvent); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'getRevision', - ol.layer.Layer.prototype.getRevision); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'on', - ol.layer.Layer.prototype.on); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'once', - ol.layer.Layer.prototype.once); - -goog.exportProperty( - ol.layer.Layer.prototype, - 'un', - ol.layer.Layer.prototype.un); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'setMap', - ol.layer.Vector.prototype.setMap); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'setSource', - ol.layer.Vector.prototype.setSource); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'getExtent', - ol.layer.Vector.prototype.getExtent); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'getMaxResolution', - ol.layer.Vector.prototype.getMaxResolution); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'getMinResolution', - ol.layer.Vector.prototype.getMinResolution); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'getOpacity', - ol.layer.Vector.prototype.getOpacity); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'getVisible', - ol.layer.Vector.prototype.getVisible); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'getZIndex', - ol.layer.Vector.prototype.getZIndex); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'setExtent', - ol.layer.Vector.prototype.setExtent); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'setMaxResolution', - ol.layer.Vector.prototype.setMaxResolution); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'setMinResolution', - ol.layer.Vector.prototype.setMinResolution); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'setOpacity', - ol.layer.Vector.prototype.setOpacity); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'setVisible', - ol.layer.Vector.prototype.setVisible); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'setZIndex', - ol.layer.Vector.prototype.setZIndex); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'get', - ol.layer.Vector.prototype.get); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'getKeys', - ol.layer.Vector.prototype.getKeys); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'getProperties', - ol.layer.Vector.prototype.getProperties); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'set', - ol.layer.Vector.prototype.set); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'setProperties', - ol.layer.Vector.prototype.setProperties); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'unset', - ol.layer.Vector.prototype.unset); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'changed', - ol.layer.Vector.prototype.changed); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'dispatchEvent', - ol.layer.Vector.prototype.dispatchEvent); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'getRevision', - ol.layer.Vector.prototype.getRevision); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'on', - ol.layer.Vector.prototype.on); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'once', - ol.layer.Vector.prototype.once); - -goog.exportProperty( - ol.layer.Vector.prototype, - 'un', - ol.layer.Vector.prototype.un); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'getSource', - ol.layer.Heatmap.prototype.getSource); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'getStyle', - ol.layer.Heatmap.prototype.getStyle); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'getStyleFunction', - ol.layer.Heatmap.prototype.getStyleFunction); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'setStyle', - ol.layer.Heatmap.prototype.setStyle); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'setMap', - ol.layer.Heatmap.prototype.setMap); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'setSource', - ol.layer.Heatmap.prototype.setSource); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'getExtent', - ol.layer.Heatmap.prototype.getExtent); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'getMaxResolution', - ol.layer.Heatmap.prototype.getMaxResolution); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'getMinResolution', - ol.layer.Heatmap.prototype.getMinResolution); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'getOpacity', - ol.layer.Heatmap.prototype.getOpacity); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'getVisible', - ol.layer.Heatmap.prototype.getVisible); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'getZIndex', - ol.layer.Heatmap.prototype.getZIndex); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'setExtent', - ol.layer.Heatmap.prototype.setExtent); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'setMaxResolution', - ol.layer.Heatmap.prototype.setMaxResolution); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'setMinResolution', - ol.layer.Heatmap.prototype.setMinResolution); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'setOpacity', - ol.layer.Heatmap.prototype.setOpacity); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'setVisible', - ol.layer.Heatmap.prototype.setVisible); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'setZIndex', - ol.layer.Heatmap.prototype.setZIndex); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'get', - ol.layer.Heatmap.prototype.get); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'getKeys', - ol.layer.Heatmap.prototype.getKeys); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'getProperties', - ol.layer.Heatmap.prototype.getProperties); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'set', - ol.layer.Heatmap.prototype.set); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'setProperties', - ol.layer.Heatmap.prototype.setProperties); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'unset', - ol.layer.Heatmap.prototype.unset); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'changed', - ol.layer.Heatmap.prototype.changed); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'dispatchEvent', - ol.layer.Heatmap.prototype.dispatchEvent); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'getRevision', - ol.layer.Heatmap.prototype.getRevision); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'on', - ol.layer.Heatmap.prototype.on); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'once', - ol.layer.Heatmap.prototype.once); - -goog.exportProperty( - ol.layer.Heatmap.prototype, - 'un', - ol.layer.Heatmap.prototype.un); - -goog.exportProperty( - ol.layer.Image.prototype, - 'setMap', - ol.layer.Image.prototype.setMap); - -goog.exportProperty( - ol.layer.Image.prototype, - 'setSource', - ol.layer.Image.prototype.setSource); - -goog.exportProperty( - ol.layer.Image.prototype, - 'getExtent', - ol.layer.Image.prototype.getExtent); - -goog.exportProperty( - ol.layer.Image.prototype, - 'getMaxResolution', - ol.layer.Image.prototype.getMaxResolution); - -goog.exportProperty( - ol.layer.Image.prototype, - 'getMinResolution', - ol.layer.Image.prototype.getMinResolution); - -goog.exportProperty( - ol.layer.Image.prototype, - 'getOpacity', - ol.layer.Image.prototype.getOpacity); - -goog.exportProperty( - ol.layer.Image.prototype, - 'getVisible', - ol.layer.Image.prototype.getVisible); - -goog.exportProperty( - ol.layer.Image.prototype, - 'getZIndex', - ol.layer.Image.prototype.getZIndex); - -goog.exportProperty( - ol.layer.Image.prototype, - 'setExtent', - ol.layer.Image.prototype.setExtent); - -goog.exportProperty( - ol.layer.Image.prototype, - 'setMaxResolution', - ol.layer.Image.prototype.setMaxResolution); - -goog.exportProperty( - ol.layer.Image.prototype, - 'setMinResolution', - ol.layer.Image.prototype.setMinResolution); - -goog.exportProperty( - ol.layer.Image.prototype, - 'setOpacity', - ol.layer.Image.prototype.setOpacity); - -goog.exportProperty( - ol.layer.Image.prototype, - 'setVisible', - ol.layer.Image.prototype.setVisible); - -goog.exportProperty( - ol.layer.Image.prototype, - 'setZIndex', - ol.layer.Image.prototype.setZIndex); - -goog.exportProperty( - ol.layer.Image.prototype, - 'get', - ol.layer.Image.prototype.get); - -goog.exportProperty( - ol.layer.Image.prototype, - 'getKeys', - ol.layer.Image.prototype.getKeys); - -goog.exportProperty( - ol.layer.Image.prototype, - 'getProperties', - ol.layer.Image.prototype.getProperties); - -goog.exportProperty( - ol.layer.Image.prototype, - 'set', - ol.layer.Image.prototype.set); - -goog.exportProperty( - ol.layer.Image.prototype, - 'setProperties', - ol.layer.Image.prototype.setProperties); - -goog.exportProperty( - ol.layer.Image.prototype, - 'unset', - ol.layer.Image.prototype.unset); - -goog.exportProperty( - ol.layer.Image.prototype, - 'changed', - ol.layer.Image.prototype.changed); - -goog.exportProperty( - ol.layer.Image.prototype, - 'dispatchEvent', - ol.layer.Image.prototype.dispatchEvent); - -goog.exportProperty( - ol.layer.Image.prototype, - 'getRevision', - ol.layer.Image.prototype.getRevision); - -goog.exportProperty( - ol.layer.Image.prototype, - 'on', - ol.layer.Image.prototype.on); - -goog.exportProperty( - ol.layer.Image.prototype, - 'once', - ol.layer.Image.prototype.once); - -goog.exportProperty( - ol.layer.Image.prototype, - 'un', - ol.layer.Image.prototype.un); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'setMap', - ol.layer.Tile.prototype.setMap); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'setSource', - ol.layer.Tile.prototype.setSource); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'getExtent', - ol.layer.Tile.prototype.getExtent); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'getMaxResolution', - ol.layer.Tile.prototype.getMaxResolution); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'getMinResolution', - ol.layer.Tile.prototype.getMinResolution); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'getOpacity', - ol.layer.Tile.prototype.getOpacity); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'getVisible', - ol.layer.Tile.prototype.getVisible); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'getZIndex', - ol.layer.Tile.prototype.getZIndex); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'setExtent', - ol.layer.Tile.prototype.setExtent); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'setMaxResolution', - ol.layer.Tile.prototype.setMaxResolution); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'setMinResolution', - ol.layer.Tile.prototype.setMinResolution); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'setOpacity', - ol.layer.Tile.prototype.setOpacity); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'setVisible', - ol.layer.Tile.prototype.setVisible); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'setZIndex', - ol.layer.Tile.prototype.setZIndex); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'get', - ol.layer.Tile.prototype.get); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'getKeys', - ol.layer.Tile.prototype.getKeys); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'getProperties', - ol.layer.Tile.prototype.getProperties); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'set', - ol.layer.Tile.prototype.set); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'setProperties', - ol.layer.Tile.prototype.setProperties); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'unset', - ol.layer.Tile.prototype.unset); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'changed', - ol.layer.Tile.prototype.changed); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'dispatchEvent', - ol.layer.Tile.prototype.dispatchEvent); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'getRevision', - ol.layer.Tile.prototype.getRevision); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'on', - ol.layer.Tile.prototype.on); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'once', - ol.layer.Tile.prototype.once); - -goog.exportProperty( - ol.layer.Tile.prototype, - 'un', - ol.layer.Tile.prototype.un); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'getStyle', - ol.layer.VectorTile.prototype.getStyle); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'getStyleFunction', - ol.layer.VectorTile.prototype.getStyleFunction); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'setStyle', - ol.layer.VectorTile.prototype.setStyle); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'setMap', - ol.layer.VectorTile.prototype.setMap); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'setSource', - ol.layer.VectorTile.prototype.setSource); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'getExtent', - ol.layer.VectorTile.prototype.getExtent); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'getMaxResolution', - ol.layer.VectorTile.prototype.getMaxResolution); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'getMinResolution', - ol.layer.VectorTile.prototype.getMinResolution); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'getOpacity', - ol.layer.VectorTile.prototype.getOpacity); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'getVisible', - ol.layer.VectorTile.prototype.getVisible); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'getZIndex', - ol.layer.VectorTile.prototype.getZIndex); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'setExtent', - ol.layer.VectorTile.prototype.setExtent); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'setMaxResolution', - ol.layer.VectorTile.prototype.setMaxResolution); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'setMinResolution', - ol.layer.VectorTile.prototype.setMinResolution); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'setOpacity', - ol.layer.VectorTile.prototype.setOpacity); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'setVisible', - ol.layer.VectorTile.prototype.setVisible); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'setZIndex', - ol.layer.VectorTile.prototype.setZIndex); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'get', - ol.layer.VectorTile.prototype.get); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'getKeys', - ol.layer.VectorTile.prototype.getKeys); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'getProperties', - ol.layer.VectorTile.prototype.getProperties); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'set', - ol.layer.VectorTile.prototype.set); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'setProperties', - ol.layer.VectorTile.prototype.setProperties); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'unset', - ol.layer.VectorTile.prototype.unset); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'changed', - ol.layer.VectorTile.prototype.changed); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'dispatchEvent', - ol.layer.VectorTile.prototype.dispatchEvent); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'getRevision', - ol.layer.VectorTile.prototype.getRevision); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'on', - ol.layer.VectorTile.prototype.on); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'once', - ol.layer.VectorTile.prototype.once); - -goog.exportProperty( - ol.layer.VectorTile.prototype, - 'un', - ol.layer.VectorTile.prototype.un); - -goog.exportProperty( - ol.interaction.Interaction.prototype, - 'get', - ol.interaction.Interaction.prototype.get); - -goog.exportProperty( - ol.interaction.Interaction.prototype, - 'getKeys', - ol.interaction.Interaction.prototype.getKeys); - -goog.exportProperty( - ol.interaction.Interaction.prototype, - 'getProperties', - ol.interaction.Interaction.prototype.getProperties); - -goog.exportProperty( - ol.interaction.Interaction.prototype, - 'set', - ol.interaction.Interaction.prototype.set); - -goog.exportProperty( - ol.interaction.Interaction.prototype, - 'setProperties', - ol.interaction.Interaction.prototype.setProperties); - -goog.exportProperty( - ol.interaction.Interaction.prototype, - 'unset', - ol.interaction.Interaction.prototype.unset); - -goog.exportProperty( - ol.interaction.Interaction.prototype, - 'changed', - ol.interaction.Interaction.prototype.changed); - -goog.exportProperty( - ol.interaction.Interaction.prototype, - 'dispatchEvent', - ol.interaction.Interaction.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.Interaction.prototype, - 'getRevision', - ol.interaction.Interaction.prototype.getRevision); - -goog.exportProperty( - ol.interaction.Interaction.prototype, - 'on', - ol.interaction.Interaction.prototype.on); - -goog.exportProperty( - ol.interaction.Interaction.prototype, - 'once', - ol.interaction.Interaction.prototype.once); - -goog.exportProperty( - ol.interaction.Interaction.prototype, - 'un', - ol.interaction.Interaction.prototype.un); - -goog.exportProperty( - ol.interaction.DoubleClickZoom.prototype, - 'getActive', - ol.interaction.DoubleClickZoom.prototype.getActive); - -goog.exportProperty( - ol.interaction.DoubleClickZoom.prototype, - 'getMap', - ol.interaction.DoubleClickZoom.prototype.getMap); - -goog.exportProperty( - ol.interaction.DoubleClickZoom.prototype, - 'setActive', - ol.interaction.DoubleClickZoom.prototype.setActive); - -goog.exportProperty( - ol.interaction.DoubleClickZoom.prototype, - 'get', - ol.interaction.DoubleClickZoom.prototype.get); - -goog.exportProperty( - ol.interaction.DoubleClickZoom.prototype, - 'getKeys', - ol.interaction.DoubleClickZoom.prototype.getKeys); - -goog.exportProperty( - ol.interaction.DoubleClickZoom.prototype, - 'getProperties', - ol.interaction.DoubleClickZoom.prototype.getProperties); - -goog.exportProperty( - ol.interaction.DoubleClickZoom.prototype, - 'set', - ol.interaction.DoubleClickZoom.prototype.set); - -goog.exportProperty( - ol.interaction.DoubleClickZoom.prototype, - 'setProperties', - ol.interaction.DoubleClickZoom.prototype.setProperties); - -goog.exportProperty( - ol.interaction.DoubleClickZoom.prototype, - 'unset', - ol.interaction.DoubleClickZoom.prototype.unset); - -goog.exportProperty( - ol.interaction.DoubleClickZoom.prototype, - 'changed', - ol.interaction.DoubleClickZoom.prototype.changed); - -goog.exportProperty( - ol.interaction.DoubleClickZoom.prototype, - 'dispatchEvent', - ol.interaction.DoubleClickZoom.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.DoubleClickZoom.prototype, - 'getRevision', - ol.interaction.DoubleClickZoom.prototype.getRevision); - -goog.exportProperty( - ol.interaction.DoubleClickZoom.prototype, - 'on', - ol.interaction.DoubleClickZoom.prototype.on); - -goog.exportProperty( - ol.interaction.DoubleClickZoom.prototype, - 'once', - ol.interaction.DoubleClickZoom.prototype.once); - -goog.exportProperty( - ol.interaction.DoubleClickZoom.prototype, - 'un', - ol.interaction.DoubleClickZoom.prototype.un); - -goog.exportProperty( - ol.interaction.DragAndDrop.prototype, - 'getActive', - ol.interaction.DragAndDrop.prototype.getActive); - -goog.exportProperty( - ol.interaction.DragAndDrop.prototype, - 'getMap', - ol.interaction.DragAndDrop.prototype.getMap); - -goog.exportProperty( - ol.interaction.DragAndDrop.prototype, - 'setActive', - ol.interaction.DragAndDrop.prototype.setActive); - -goog.exportProperty( - ol.interaction.DragAndDrop.prototype, - 'get', - ol.interaction.DragAndDrop.prototype.get); - -goog.exportProperty( - ol.interaction.DragAndDrop.prototype, - 'getKeys', - ol.interaction.DragAndDrop.prototype.getKeys); - -goog.exportProperty( - ol.interaction.DragAndDrop.prototype, - 'getProperties', - ol.interaction.DragAndDrop.prototype.getProperties); - -goog.exportProperty( - ol.interaction.DragAndDrop.prototype, - 'set', - ol.interaction.DragAndDrop.prototype.set); - -goog.exportProperty( - ol.interaction.DragAndDrop.prototype, - 'setProperties', - ol.interaction.DragAndDrop.prototype.setProperties); - -goog.exportProperty( - ol.interaction.DragAndDrop.prototype, - 'unset', - ol.interaction.DragAndDrop.prototype.unset); - -goog.exportProperty( - ol.interaction.DragAndDrop.prototype, - 'changed', - ol.interaction.DragAndDrop.prototype.changed); - -goog.exportProperty( - ol.interaction.DragAndDrop.prototype, - 'dispatchEvent', - ol.interaction.DragAndDrop.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.DragAndDrop.prototype, - 'getRevision', - ol.interaction.DragAndDrop.prototype.getRevision); - -goog.exportProperty( - ol.interaction.DragAndDrop.prototype, - 'on', - ol.interaction.DragAndDrop.prototype.on); - -goog.exportProperty( - ol.interaction.DragAndDrop.prototype, - 'once', - ol.interaction.DragAndDrop.prototype.once); - -goog.exportProperty( - ol.interaction.DragAndDrop.prototype, - 'un', - ol.interaction.DragAndDrop.prototype.un); - -goog.exportProperty( - ol.interaction.DragAndDrop.Event.prototype, - 'type', - ol.interaction.DragAndDrop.Event.prototype.type); - -goog.exportProperty( - ol.interaction.DragAndDrop.Event.prototype, - 'target', - ol.interaction.DragAndDrop.Event.prototype.target); - -goog.exportProperty( - ol.interaction.DragAndDrop.Event.prototype, - 'preventDefault', - ol.interaction.DragAndDrop.Event.prototype.preventDefault); - -goog.exportProperty( - ol.interaction.DragAndDrop.Event.prototype, - 'stopPropagation', - ol.interaction.DragAndDrop.Event.prototype.stopPropagation); - -goog.exportProperty( - ol.interaction.Pointer.prototype, - 'getActive', - ol.interaction.Pointer.prototype.getActive); - -goog.exportProperty( - ol.interaction.Pointer.prototype, - 'getMap', - ol.interaction.Pointer.prototype.getMap); - -goog.exportProperty( - ol.interaction.Pointer.prototype, - 'setActive', - ol.interaction.Pointer.prototype.setActive); - -goog.exportProperty( - ol.interaction.Pointer.prototype, - 'get', - ol.interaction.Pointer.prototype.get); - -goog.exportProperty( - ol.interaction.Pointer.prototype, - 'getKeys', - ol.interaction.Pointer.prototype.getKeys); - -goog.exportProperty( - ol.interaction.Pointer.prototype, - 'getProperties', - ol.interaction.Pointer.prototype.getProperties); - -goog.exportProperty( - ol.interaction.Pointer.prototype, - 'set', - ol.interaction.Pointer.prototype.set); - -goog.exportProperty( - ol.interaction.Pointer.prototype, - 'setProperties', - ol.interaction.Pointer.prototype.setProperties); - -goog.exportProperty( - ol.interaction.Pointer.prototype, - 'unset', - ol.interaction.Pointer.prototype.unset); - -goog.exportProperty( - ol.interaction.Pointer.prototype, - 'changed', - ol.interaction.Pointer.prototype.changed); - -goog.exportProperty( - ol.interaction.Pointer.prototype, - 'dispatchEvent', - ol.interaction.Pointer.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.Pointer.prototype, - 'getRevision', - ol.interaction.Pointer.prototype.getRevision); - -goog.exportProperty( - ol.interaction.Pointer.prototype, - 'on', - ol.interaction.Pointer.prototype.on); - -goog.exportProperty( - ol.interaction.Pointer.prototype, - 'once', - ol.interaction.Pointer.prototype.once); - -goog.exportProperty( - ol.interaction.Pointer.prototype, - 'un', - ol.interaction.Pointer.prototype.un); - -goog.exportProperty( - ol.interaction.DragBox.prototype, - 'getActive', - ol.interaction.DragBox.prototype.getActive); - -goog.exportProperty( - ol.interaction.DragBox.prototype, - 'getMap', - ol.interaction.DragBox.prototype.getMap); - -goog.exportProperty( - ol.interaction.DragBox.prototype, - 'setActive', - ol.interaction.DragBox.prototype.setActive); - -goog.exportProperty( - ol.interaction.DragBox.prototype, - 'get', - ol.interaction.DragBox.prototype.get); - -goog.exportProperty( - ol.interaction.DragBox.prototype, - 'getKeys', - ol.interaction.DragBox.prototype.getKeys); - -goog.exportProperty( - ol.interaction.DragBox.prototype, - 'getProperties', - ol.interaction.DragBox.prototype.getProperties); - -goog.exportProperty( - ol.interaction.DragBox.prototype, - 'set', - ol.interaction.DragBox.prototype.set); - -goog.exportProperty( - ol.interaction.DragBox.prototype, - 'setProperties', - ol.interaction.DragBox.prototype.setProperties); - -goog.exportProperty( - ol.interaction.DragBox.prototype, - 'unset', - ol.interaction.DragBox.prototype.unset); - -goog.exportProperty( - ol.interaction.DragBox.prototype, - 'changed', - ol.interaction.DragBox.prototype.changed); - -goog.exportProperty( - ol.interaction.DragBox.prototype, - 'dispatchEvent', - ol.interaction.DragBox.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.DragBox.prototype, - 'getRevision', - ol.interaction.DragBox.prototype.getRevision); - -goog.exportProperty( - ol.interaction.DragBox.prototype, - 'on', - ol.interaction.DragBox.prototype.on); - -goog.exportProperty( - ol.interaction.DragBox.prototype, - 'once', - ol.interaction.DragBox.prototype.once); - -goog.exportProperty( - ol.interaction.DragBox.prototype, - 'un', - ol.interaction.DragBox.prototype.un); - -goog.exportProperty( - ol.interaction.DragBox.Event.prototype, - 'type', - ol.interaction.DragBox.Event.prototype.type); - -goog.exportProperty( - ol.interaction.DragBox.Event.prototype, - 'target', - ol.interaction.DragBox.Event.prototype.target); - -goog.exportProperty( - ol.interaction.DragBox.Event.prototype, - 'preventDefault', - ol.interaction.DragBox.Event.prototype.preventDefault); - -goog.exportProperty( - ol.interaction.DragBox.Event.prototype, - 'stopPropagation', - ol.interaction.DragBox.Event.prototype.stopPropagation); - -goog.exportProperty( - ol.interaction.DragPan.prototype, - 'getActive', - ol.interaction.DragPan.prototype.getActive); - -goog.exportProperty( - ol.interaction.DragPan.prototype, - 'getMap', - ol.interaction.DragPan.prototype.getMap); - -goog.exportProperty( - ol.interaction.DragPan.prototype, - 'setActive', - ol.interaction.DragPan.prototype.setActive); - -goog.exportProperty( - ol.interaction.DragPan.prototype, - 'get', - ol.interaction.DragPan.prototype.get); - -goog.exportProperty( - ol.interaction.DragPan.prototype, - 'getKeys', - ol.interaction.DragPan.prototype.getKeys); - -goog.exportProperty( - ol.interaction.DragPan.prototype, - 'getProperties', - ol.interaction.DragPan.prototype.getProperties); - -goog.exportProperty( - ol.interaction.DragPan.prototype, - 'set', - ol.interaction.DragPan.prototype.set); - -goog.exportProperty( - ol.interaction.DragPan.prototype, - 'setProperties', - ol.interaction.DragPan.prototype.setProperties); - -goog.exportProperty( - ol.interaction.DragPan.prototype, - 'unset', - ol.interaction.DragPan.prototype.unset); - -goog.exportProperty( - ol.interaction.DragPan.prototype, - 'changed', - ol.interaction.DragPan.prototype.changed); - -goog.exportProperty( - ol.interaction.DragPan.prototype, - 'dispatchEvent', - ol.interaction.DragPan.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.DragPan.prototype, - 'getRevision', - ol.interaction.DragPan.prototype.getRevision); - -goog.exportProperty( - ol.interaction.DragPan.prototype, - 'on', - ol.interaction.DragPan.prototype.on); - -goog.exportProperty( - ol.interaction.DragPan.prototype, - 'once', - ol.interaction.DragPan.prototype.once); - -goog.exportProperty( - ol.interaction.DragPan.prototype, - 'un', - ol.interaction.DragPan.prototype.un); - -goog.exportProperty( - ol.interaction.DragRotate.prototype, - 'getActive', - ol.interaction.DragRotate.prototype.getActive); - -goog.exportProperty( - ol.interaction.DragRotate.prototype, - 'getMap', - ol.interaction.DragRotate.prototype.getMap); - -goog.exportProperty( - ol.interaction.DragRotate.prototype, - 'setActive', - ol.interaction.DragRotate.prototype.setActive); - -goog.exportProperty( - ol.interaction.DragRotate.prototype, - 'get', - ol.interaction.DragRotate.prototype.get); - -goog.exportProperty( - ol.interaction.DragRotate.prototype, - 'getKeys', - ol.interaction.DragRotate.prototype.getKeys); - -goog.exportProperty( - ol.interaction.DragRotate.prototype, - 'getProperties', - ol.interaction.DragRotate.prototype.getProperties); - -goog.exportProperty( - ol.interaction.DragRotate.prototype, - 'set', - ol.interaction.DragRotate.prototype.set); - -goog.exportProperty( - ol.interaction.DragRotate.prototype, - 'setProperties', - ol.interaction.DragRotate.prototype.setProperties); - -goog.exportProperty( - ol.interaction.DragRotate.prototype, - 'unset', - ol.interaction.DragRotate.prototype.unset); - -goog.exportProperty( - ol.interaction.DragRotate.prototype, - 'changed', - ol.interaction.DragRotate.prototype.changed); - -goog.exportProperty( - ol.interaction.DragRotate.prototype, - 'dispatchEvent', - ol.interaction.DragRotate.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.DragRotate.prototype, - 'getRevision', - ol.interaction.DragRotate.prototype.getRevision); - -goog.exportProperty( - ol.interaction.DragRotate.prototype, - 'on', - ol.interaction.DragRotate.prototype.on); - -goog.exportProperty( - ol.interaction.DragRotate.prototype, - 'once', - ol.interaction.DragRotate.prototype.once); - -goog.exportProperty( - ol.interaction.DragRotate.prototype, - 'un', - ol.interaction.DragRotate.prototype.un); - -goog.exportProperty( - ol.interaction.DragRotateAndZoom.prototype, - 'getActive', - ol.interaction.DragRotateAndZoom.prototype.getActive); - -goog.exportProperty( - ol.interaction.DragRotateAndZoom.prototype, - 'getMap', - ol.interaction.DragRotateAndZoom.prototype.getMap); - -goog.exportProperty( - ol.interaction.DragRotateAndZoom.prototype, - 'setActive', - ol.interaction.DragRotateAndZoom.prototype.setActive); - -goog.exportProperty( - ol.interaction.DragRotateAndZoom.prototype, - 'get', - ol.interaction.DragRotateAndZoom.prototype.get); - -goog.exportProperty( - ol.interaction.DragRotateAndZoom.prototype, - 'getKeys', - ol.interaction.DragRotateAndZoom.prototype.getKeys); - -goog.exportProperty( - ol.interaction.DragRotateAndZoom.prototype, - 'getProperties', - ol.interaction.DragRotateAndZoom.prototype.getProperties); - -goog.exportProperty( - ol.interaction.DragRotateAndZoom.prototype, - 'set', - ol.interaction.DragRotateAndZoom.prototype.set); - -goog.exportProperty( - ol.interaction.DragRotateAndZoom.prototype, - 'setProperties', - ol.interaction.DragRotateAndZoom.prototype.setProperties); - -goog.exportProperty( - ol.interaction.DragRotateAndZoom.prototype, - 'unset', - ol.interaction.DragRotateAndZoom.prototype.unset); - -goog.exportProperty( - ol.interaction.DragRotateAndZoom.prototype, - 'changed', - ol.interaction.DragRotateAndZoom.prototype.changed); - -goog.exportProperty( - ol.interaction.DragRotateAndZoom.prototype, - 'dispatchEvent', - ol.interaction.DragRotateAndZoom.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.DragRotateAndZoom.prototype, - 'getRevision', - ol.interaction.DragRotateAndZoom.prototype.getRevision); - -goog.exportProperty( - ol.interaction.DragRotateAndZoom.prototype, - 'on', - ol.interaction.DragRotateAndZoom.prototype.on); - -goog.exportProperty( - ol.interaction.DragRotateAndZoom.prototype, - 'once', - ol.interaction.DragRotateAndZoom.prototype.once); - -goog.exportProperty( - ol.interaction.DragRotateAndZoom.prototype, - 'un', - ol.interaction.DragRotateAndZoom.prototype.un); - -goog.exportProperty( - ol.interaction.DragZoom.prototype, - 'getGeometry', - ol.interaction.DragZoom.prototype.getGeometry); - -goog.exportProperty( - ol.interaction.DragZoom.prototype, - 'getActive', - ol.interaction.DragZoom.prototype.getActive); - -goog.exportProperty( - ol.interaction.DragZoom.prototype, - 'getMap', - ol.interaction.DragZoom.prototype.getMap); - -goog.exportProperty( - ol.interaction.DragZoom.prototype, - 'setActive', - ol.interaction.DragZoom.prototype.setActive); - -goog.exportProperty( - ol.interaction.DragZoom.prototype, - 'get', - ol.interaction.DragZoom.prototype.get); - -goog.exportProperty( - ol.interaction.DragZoom.prototype, - 'getKeys', - ol.interaction.DragZoom.prototype.getKeys); - -goog.exportProperty( - ol.interaction.DragZoom.prototype, - 'getProperties', - ol.interaction.DragZoom.prototype.getProperties); - -goog.exportProperty( - ol.interaction.DragZoom.prototype, - 'set', - ol.interaction.DragZoom.prototype.set); - -goog.exportProperty( - ol.interaction.DragZoom.prototype, - 'setProperties', - ol.interaction.DragZoom.prototype.setProperties); - -goog.exportProperty( - ol.interaction.DragZoom.prototype, - 'unset', - ol.interaction.DragZoom.prototype.unset); - -goog.exportProperty( - ol.interaction.DragZoom.prototype, - 'changed', - ol.interaction.DragZoom.prototype.changed); - -goog.exportProperty( - ol.interaction.DragZoom.prototype, - 'dispatchEvent', - ol.interaction.DragZoom.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.DragZoom.prototype, - 'getRevision', - ol.interaction.DragZoom.prototype.getRevision); - -goog.exportProperty( - ol.interaction.DragZoom.prototype, - 'on', - ol.interaction.DragZoom.prototype.on); - -goog.exportProperty( - ol.interaction.DragZoom.prototype, - 'once', - ol.interaction.DragZoom.prototype.once); - -goog.exportProperty( - ol.interaction.DragZoom.prototype, - 'un', - ol.interaction.DragZoom.prototype.un); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'getActive', - ol.interaction.Draw.prototype.getActive); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'getMap', - ol.interaction.Draw.prototype.getMap); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'setActive', - ol.interaction.Draw.prototype.setActive); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'get', - ol.interaction.Draw.prototype.get); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'getKeys', - ol.interaction.Draw.prototype.getKeys); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'getProperties', - ol.interaction.Draw.prototype.getProperties); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'set', - ol.interaction.Draw.prototype.set); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'setProperties', - ol.interaction.Draw.prototype.setProperties); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'unset', - ol.interaction.Draw.prototype.unset); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'changed', - ol.interaction.Draw.prototype.changed); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'dispatchEvent', - ol.interaction.Draw.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'getRevision', - ol.interaction.Draw.prototype.getRevision); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'on', - ol.interaction.Draw.prototype.on); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'once', - ol.interaction.Draw.prototype.once); - -goog.exportProperty( - ol.interaction.Draw.prototype, - 'un', - ol.interaction.Draw.prototype.un); - -goog.exportProperty( - ol.interaction.Draw.Event.prototype, - 'type', - ol.interaction.Draw.Event.prototype.type); - -goog.exportProperty( - ol.interaction.Draw.Event.prototype, - 'target', - ol.interaction.Draw.Event.prototype.target); - -goog.exportProperty( - ol.interaction.Draw.Event.prototype, - 'preventDefault', - ol.interaction.Draw.Event.prototype.preventDefault); - -goog.exportProperty( - ol.interaction.Draw.Event.prototype, - 'stopPropagation', - ol.interaction.Draw.Event.prototype.stopPropagation); - -goog.exportProperty( - ol.interaction.Extent.prototype, - 'getActive', - ol.interaction.Extent.prototype.getActive); - -goog.exportProperty( - ol.interaction.Extent.prototype, - 'getMap', - ol.interaction.Extent.prototype.getMap); - -goog.exportProperty( - ol.interaction.Extent.prototype, - 'setActive', - ol.interaction.Extent.prototype.setActive); - -goog.exportProperty( - ol.interaction.Extent.prototype, - 'get', - ol.interaction.Extent.prototype.get); - -goog.exportProperty( - ol.interaction.Extent.prototype, - 'getKeys', - ol.interaction.Extent.prototype.getKeys); - -goog.exportProperty( - ol.interaction.Extent.prototype, - 'getProperties', - ol.interaction.Extent.prototype.getProperties); - -goog.exportProperty( - ol.interaction.Extent.prototype, - 'set', - ol.interaction.Extent.prototype.set); - -goog.exportProperty( - ol.interaction.Extent.prototype, - 'setProperties', - ol.interaction.Extent.prototype.setProperties); - -goog.exportProperty( - ol.interaction.Extent.prototype, - 'unset', - ol.interaction.Extent.prototype.unset); - -goog.exportProperty( - ol.interaction.Extent.prototype, - 'changed', - ol.interaction.Extent.prototype.changed); - -goog.exportProperty( - ol.interaction.Extent.prototype, - 'dispatchEvent', - ol.interaction.Extent.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.Extent.prototype, - 'getRevision', - ol.interaction.Extent.prototype.getRevision); - -goog.exportProperty( - ol.interaction.Extent.prototype, - 'on', - ol.interaction.Extent.prototype.on); - -goog.exportProperty( - ol.interaction.Extent.prototype, - 'once', - ol.interaction.Extent.prototype.once); - -goog.exportProperty( - ol.interaction.Extent.prototype, - 'un', - ol.interaction.Extent.prototype.un); - -goog.exportProperty( - ol.interaction.Extent.Event.prototype, - 'type', - ol.interaction.Extent.Event.prototype.type); - -goog.exportProperty( - ol.interaction.Extent.Event.prototype, - 'target', - ol.interaction.Extent.Event.prototype.target); - -goog.exportProperty( - ol.interaction.Extent.Event.prototype, - 'preventDefault', - ol.interaction.Extent.Event.prototype.preventDefault); - -goog.exportProperty( - ol.interaction.Extent.Event.prototype, - 'stopPropagation', - ol.interaction.Extent.Event.prototype.stopPropagation); - -goog.exportProperty( - ol.interaction.KeyboardPan.prototype, - 'getActive', - ol.interaction.KeyboardPan.prototype.getActive); - -goog.exportProperty( - ol.interaction.KeyboardPan.prototype, - 'getMap', - ol.interaction.KeyboardPan.prototype.getMap); - -goog.exportProperty( - ol.interaction.KeyboardPan.prototype, - 'setActive', - ol.interaction.KeyboardPan.prototype.setActive); - -goog.exportProperty( - ol.interaction.KeyboardPan.prototype, - 'get', - ol.interaction.KeyboardPan.prototype.get); - -goog.exportProperty( - ol.interaction.KeyboardPan.prototype, - 'getKeys', - ol.interaction.KeyboardPan.prototype.getKeys); - -goog.exportProperty( - ol.interaction.KeyboardPan.prototype, - 'getProperties', - ol.interaction.KeyboardPan.prototype.getProperties); - -goog.exportProperty( - ol.interaction.KeyboardPan.prototype, - 'set', - ol.interaction.KeyboardPan.prototype.set); - -goog.exportProperty( - ol.interaction.KeyboardPan.prototype, - 'setProperties', - ol.interaction.KeyboardPan.prototype.setProperties); - -goog.exportProperty( - ol.interaction.KeyboardPan.prototype, - 'unset', - ol.interaction.KeyboardPan.prototype.unset); - -goog.exportProperty( - ol.interaction.KeyboardPan.prototype, - 'changed', - ol.interaction.KeyboardPan.prototype.changed); - -goog.exportProperty( - ol.interaction.KeyboardPan.prototype, - 'dispatchEvent', - ol.interaction.KeyboardPan.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.KeyboardPan.prototype, - 'getRevision', - ol.interaction.KeyboardPan.prototype.getRevision); - -goog.exportProperty( - ol.interaction.KeyboardPan.prototype, - 'on', - ol.interaction.KeyboardPan.prototype.on); - -goog.exportProperty( - ol.interaction.KeyboardPan.prototype, - 'once', - ol.interaction.KeyboardPan.prototype.once); - -goog.exportProperty( - ol.interaction.KeyboardPan.prototype, - 'un', - ol.interaction.KeyboardPan.prototype.un); - -goog.exportProperty( - ol.interaction.KeyboardZoom.prototype, - 'getActive', - ol.interaction.KeyboardZoom.prototype.getActive); - -goog.exportProperty( - ol.interaction.KeyboardZoom.prototype, - 'getMap', - ol.interaction.KeyboardZoom.prototype.getMap); - -goog.exportProperty( - ol.interaction.KeyboardZoom.prototype, - 'setActive', - ol.interaction.KeyboardZoom.prototype.setActive); - -goog.exportProperty( - ol.interaction.KeyboardZoom.prototype, - 'get', - ol.interaction.KeyboardZoom.prototype.get); - -goog.exportProperty( - ol.interaction.KeyboardZoom.prototype, - 'getKeys', - ol.interaction.KeyboardZoom.prototype.getKeys); - -goog.exportProperty( - ol.interaction.KeyboardZoom.prototype, - 'getProperties', - ol.interaction.KeyboardZoom.prototype.getProperties); - -goog.exportProperty( - ol.interaction.KeyboardZoom.prototype, - 'set', - ol.interaction.KeyboardZoom.prototype.set); - -goog.exportProperty( - ol.interaction.KeyboardZoom.prototype, - 'setProperties', - ol.interaction.KeyboardZoom.prototype.setProperties); - -goog.exportProperty( - ol.interaction.KeyboardZoom.prototype, - 'unset', - ol.interaction.KeyboardZoom.prototype.unset); - -goog.exportProperty( - ol.interaction.KeyboardZoom.prototype, - 'changed', - ol.interaction.KeyboardZoom.prototype.changed); - -goog.exportProperty( - ol.interaction.KeyboardZoom.prototype, - 'dispatchEvent', - ol.interaction.KeyboardZoom.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.KeyboardZoom.prototype, - 'getRevision', - ol.interaction.KeyboardZoom.prototype.getRevision); - -goog.exportProperty( - ol.interaction.KeyboardZoom.prototype, - 'on', - ol.interaction.KeyboardZoom.prototype.on); - -goog.exportProperty( - ol.interaction.KeyboardZoom.prototype, - 'once', - ol.interaction.KeyboardZoom.prototype.once); - -goog.exportProperty( - ol.interaction.KeyboardZoom.prototype, - 'un', - ol.interaction.KeyboardZoom.prototype.un); - -goog.exportProperty( - ol.interaction.Modify.prototype, - 'getActive', - ol.interaction.Modify.prototype.getActive); - -goog.exportProperty( - ol.interaction.Modify.prototype, - 'getMap', - ol.interaction.Modify.prototype.getMap); - -goog.exportProperty( - ol.interaction.Modify.prototype, - 'setActive', - ol.interaction.Modify.prototype.setActive); - -goog.exportProperty( - ol.interaction.Modify.prototype, - 'get', - ol.interaction.Modify.prototype.get); - -goog.exportProperty( - ol.interaction.Modify.prototype, - 'getKeys', - ol.interaction.Modify.prototype.getKeys); - -goog.exportProperty( - ol.interaction.Modify.prototype, - 'getProperties', - ol.interaction.Modify.prototype.getProperties); - -goog.exportProperty( - ol.interaction.Modify.prototype, - 'set', - ol.interaction.Modify.prototype.set); - -goog.exportProperty( - ol.interaction.Modify.prototype, - 'setProperties', - ol.interaction.Modify.prototype.setProperties); - -goog.exportProperty( - ol.interaction.Modify.prototype, - 'unset', - ol.interaction.Modify.prototype.unset); - -goog.exportProperty( - ol.interaction.Modify.prototype, - 'changed', - ol.interaction.Modify.prototype.changed); - -goog.exportProperty( - ol.interaction.Modify.prototype, - 'dispatchEvent', - ol.interaction.Modify.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.Modify.prototype, - 'getRevision', - ol.interaction.Modify.prototype.getRevision); - -goog.exportProperty( - ol.interaction.Modify.prototype, - 'on', - ol.interaction.Modify.prototype.on); - -goog.exportProperty( - ol.interaction.Modify.prototype, - 'once', - ol.interaction.Modify.prototype.once); - -goog.exportProperty( - ol.interaction.Modify.prototype, - 'un', - ol.interaction.Modify.prototype.un); - -goog.exportProperty( - ol.interaction.Modify.Event.prototype, - 'type', - ol.interaction.Modify.Event.prototype.type); - -goog.exportProperty( - ol.interaction.Modify.Event.prototype, - 'target', - ol.interaction.Modify.Event.prototype.target); - -goog.exportProperty( - ol.interaction.Modify.Event.prototype, - 'preventDefault', - ol.interaction.Modify.Event.prototype.preventDefault); - -goog.exportProperty( - ol.interaction.Modify.Event.prototype, - 'stopPropagation', - ol.interaction.Modify.Event.prototype.stopPropagation); - -goog.exportProperty( - ol.interaction.MouseWheelZoom.prototype, - 'getActive', - ol.interaction.MouseWheelZoom.prototype.getActive); - -goog.exportProperty( - ol.interaction.MouseWheelZoom.prototype, - 'getMap', - ol.interaction.MouseWheelZoom.prototype.getMap); - -goog.exportProperty( - ol.interaction.MouseWheelZoom.prototype, - 'setActive', - ol.interaction.MouseWheelZoom.prototype.setActive); - -goog.exportProperty( - ol.interaction.MouseWheelZoom.prototype, - 'get', - ol.interaction.MouseWheelZoom.prototype.get); - -goog.exportProperty( - ol.interaction.MouseWheelZoom.prototype, - 'getKeys', - ol.interaction.MouseWheelZoom.prototype.getKeys); - -goog.exportProperty( - ol.interaction.MouseWheelZoom.prototype, - 'getProperties', - ol.interaction.MouseWheelZoom.prototype.getProperties); - -goog.exportProperty( - ol.interaction.MouseWheelZoom.prototype, - 'set', - ol.interaction.MouseWheelZoom.prototype.set); - -goog.exportProperty( - ol.interaction.MouseWheelZoom.prototype, - 'setProperties', - ol.interaction.MouseWheelZoom.prototype.setProperties); - -goog.exportProperty( - ol.interaction.MouseWheelZoom.prototype, - 'unset', - ol.interaction.MouseWheelZoom.prototype.unset); - -goog.exportProperty( - ol.interaction.MouseWheelZoom.prototype, - 'changed', - ol.interaction.MouseWheelZoom.prototype.changed); - -goog.exportProperty( - ol.interaction.MouseWheelZoom.prototype, - 'dispatchEvent', - ol.interaction.MouseWheelZoom.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.MouseWheelZoom.prototype, - 'getRevision', - ol.interaction.MouseWheelZoom.prototype.getRevision); - -goog.exportProperty( - ol.interaction.MouseWheelZoom.prototype, - 'on', - ol.interaction.MouseWheelZoom.prototype.on); - -goog.exportProperty( - ol.interaction.MouseWheelZoom.prototype, - 'once', - ol.interaction.MouseWheelZoom.prototype.once); - -goog.exportProperty( - ol.interaction.MouseWheelZoom.prototype, - 'un', - ol.interaction.MouseWheelZoom.prototype.un); - -goog.exportProperty( - ol.interaction.PinchRotate.prototype, - 'getActive', - ol.interaction.PinchRotate.prototype.getActive); - -goog.exportProperty( - ol.interaction.PinchRotate.prototype, - 'getMap', - ol.interaction.PinchRotate.prototype.getMap); - -goog.exportProperty( - ol.interaction.PinchRotate.prototype, - 'setActive', - ol.interaction.PinchRotate.prototype.setActive); - -goog.exportProperty( - ol.interaction.PinchRotate.prototype, - 'get', - ol.interaction.PinchRotate.prototype.get); - -goog.exportProperty( - ol.interaction.PinchRotate.prototype, - 'getKeys', - ol.interaction.PinchRotate.prototype.getKeys); - -goog.exportProperty( - ol.interaction.PinchRotate.prototype, - 'getProperties', - ol.interaction.PinchRotate.prototype.getProperties); - -goog.exportProperty( - ol.interaction.PinchRotate.prototype, - 'set', - ol.interaction.PinchRotate.prototype.set); - -goog.exportProperty( - ol.interaction.PinchRotate.prototype, - 'setProperties', - ol.interaction.PinchRotate.prototype.setProperties); - -goog.exportProperty( - ol.interaction.PinchRotate.prototype, - 'unset', - ol.interaction.PinchRotate.prototype.unset); - -goog.exportProperty( - ol.interaction.PinchRotate.prototype, - 'changed', - ol.interaction.PinchRotate.prototype.changed); - -goog.exportProperty( - ol.interaction.PinchRotate.prototype, - 'dispatchEvent', - ol.interaction.PinchRotate.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.PinchRotate.prototype, - 'getRevision', - ol.interaction.PinchRotate.prototype.getRevision); - -goog.exportProperty( - ol.interaction.PinchRotate.prototype, - 'on', - ol.interaction.PinchRotate.prototype.on); - -goog.exportProperty( - ol.interaction.PinchRotate.prototype, - 'once', - ol.interaction.PinchRotate.prototype.once); - -goog.exportProperty( - ol.interaction.PinchRotate.prototype, - 'un', - ol.interaction.PinchRotate.prototype.un); - -goog.exportProperty( - ol.interaction.PinchZoom.prototype, - 'getActive', - ol.interaction.PinchZoom.prototype.getActive); - -goog.exportProperty( - ol.interaction.PinchZoom.prototype, - 'getMap', - ol.interaction.PinchZoom.prototype.getMap); - -goog.exportProperty( - ol.interaction.PinchZoom.prototype, - 'setActive', - ol.interaction.PinchZoom.prototype.setActive); - -goog.exportProperty( - ol.interaction.PinchZoom.prototype, - 'get', - ol.interaction.PinchZoom.prototype.get); - -goog.exportProperty( - ol.interaction.PinchZoom.prototype, - 'getKeys', - ol.interaction.PinchZoom.prototype.getKeys); - -goog.exportProperty( - ol.interaction.PinchZoom.prototype, - 'getProperties', - ol.interaction.PinchZoom.prototype.getProperties); - -goog.exportProperty( - ol.interaction.PinchZoom.prototype, - 'set', - ol.interaction.PinchZoom.prototype.set); - -goog.exportProperty( - ol.interaction.PinchZoom.prototype, - 'setProperties', - ol.interaction.PinchZoom.prototype.setProperties); - -goog.exportProperty( - ol.interaction.PinchZoom.prototype, - 'unset', - ol.interaction.PinchZoom.prototype.unset); - -goog.exportProperty( - ol.interaction.PinchZoom.prototype, - 'changed', - ol.interaction.PinchZoom.prototype.changed); - -goog.exportProperty( - ol.interaction.PinchZoom.prototype, - 'dispatchEvent', - ol.interaction.PinchZoom.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.PinchZoom.prototype, - 'getRevision', - ol.interaction.PinchZoom.prototype.getRevision); - -goog.exportProperty( - ol.interaction.PinchZoom.prototype, - 'on', - ol.interaction.PinchZoom.prototype.on); - -goog.exportProperty( - ol.interaction.PinchZoom.prototype, - 'once', - ol.interaction.PinchZoom.prototype.once); - -goog.exportProperty( - ol.interaction.PinchZoom.prototype, - 'un', - ol.interaction.PinchZoom.prototype.un); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'getActive', - ol.interaction.Select.prototype.getActive); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'getMap', - ol.interaction.Select.prototype.getMap); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'setActive', - ol.interaction.Select.prototype.setActive); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'get', - ol.interaction.Select.prototype.get); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'getKeys', - ol.interaction.Select.prototype.getKeys); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'getProperties', - ol.interaction.Select.prototype.getProperties); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'set', - ol.interaction.Select.prototype.set); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'setProperties', - ol.interaction.Select.prototype.setProperties); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'unset', - ol.interaction.Select.prototype.unset); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'changed', - ol.interaction.Select.prototype.changed); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'dispatchEvent', - ol.interaction.Select.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'getRevision', - ol.interaction.Select.prototype.getRevision); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'on', - ol.interaction.Select.prototype.on); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'once', - ol.interaction.Select.prototype.once); - -goog.exportProperty( - ol.interaction.Select.prototype, - 'un', - ol.interaction.Select.prototype.un); - -goog.exportProperty( - ol.interaction.Select.Event.prototype, - 'type', - ol.interaction.Select.Event.prototype.type); - -goog.exportProperty( - ol.interaction.Select.Event.prototype, - 'target', - ol.interaction.Select.Event.prototype.target); - -goog.exportProperty( - ol.interaction.Select.Event.prototype, - 'preventDefault', - ol.interaction.Select.Event.prototype.preventDefault); - -goog.exportProperty( - ol.interaction.Select.Event.prototype, - 'stopPropagation', - ol.interaction.Select.Event.prototype.stopPropagation); - -goog.exportProperty( - ol.interaction.Snap.prototype, - 'getActive', - ol.interaction.Snap.prototype.getActive); - -goog.exportProperty( - ol.interaction.Snap.prototype, - 'getMap', - ol.interaction.Snap.prototype.getMap); - -goog.exportProperty( - ol.interaction.Snap.prototype, - 'setActive', - ol.interaction.Snap.prototype.setActive); - -goog.exportProperty( - ol.interaction.Snap.prototype, - 'get', - ol.interaction.Snap.prototype.get); - -goog.exportProperty( - ol.interaction.Snap.prototype, - 'getKeys', - ol.interaction.Snap.prototype.getKeys); - -goog.exportProperty( - ol.interaction.Snap.prototype, - 'getProperties', - ol.interaction.Snap.prototype.getProperties); - -goog.exportProperty( - ol.interaction.Snap.prototype, - 'set', - ol.interaction.Snap.prototype.set); - -goog.exportProperty( - ol.interaction.Snap.prototype, - 'setProperties', - ol.interaction.Snap.prototype.setProperties); - -goog.exportProperty( - ol.interaction.Snap.prototype, - 'unset', - ol.interaction.Snap.prototype.unset); - -goog.exportProperty( - ol.interaction.Snap.prototype, - 'changed', - ol.interaction.Snap.prototype.changed); - -goog.exportProperty( - ol.interaction.Snap.prototype, - 'dispatchEvent', - ol.interaction.Snap.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.Snap.prototype, - 'getRevision', - ol.interaction.Snap.prototype.getRevision); - -goog.exportProperty( - ol.interaction.Snap.prototype, - 'on', - ol.interaction.Snap.prototype.on); - -goog.exportProperty( - ol.interaction.Snap.prototype, - 'once', - ol.interaction.Snap.prototype.once); - -goog.exportProperty( - ol.interaction.Snap.prototype, - 'un', - ol.interaction.Snap.prototype.un); - -goog.exportProperty( - ol.interaction.Translate.prototype, - 'getActive', - ol.interaction.Translate.prototype.getActive); - -goog.exportProperty( - ol.interaction.Translate.prototype, - 'getMap', - ol.interaction.Translate.prototype.getMap); - -goog.exportProperty( - ol.interaction.Translate.prototype, - 'setActive', - ol.interaction.Translate.prototype.setActive); - -goog.exportProperty( - ol.interaction.Translate.prototype, - 'get', - ol.interaction.Translate.prototype.get); - -goog.exportProperty( - ol.interaction.Translate.prototype, - 'getKeys', - ol.interaction.Translate.prototype.getKeys); - -goog.exportProperty( - ol.interaction.Translate.prototype, - 'getProperties', - ol.interaction.Translate.prototype.getProperties); - -goog.exportProperty( - ol.interaction.Translate.prototype, - 'set', - ol.interaction.Translate.prototype.set); - -goog.exportProperty( - ol.interaction.Translate.prototype, - 'setProperties', - ol.interaction.Translate.prototype.setProperties); - -goog.exportProperty( - ol.interaction.Translate.prototype, - 'unset', - ol.interaction.Translate.prototype.unset); - -goog.exportProperty( - ol.interaction.Translate.prototype, - 'changed', - ol.interaction.Translate.prototype.changed); - -goog.exportProperty( - ol.interaction.Translate.prototype, - 'dispatchEvent', - ol.interaction.Translate.prototype.dispatchEvent); - -goog.exportProperty( - ol.interaction.Translate.prototype, - 'getRevision', - ol.interaction.Translate.prototype.getRevision); - -goog.exportProperty( - ol.interaction.Translate.prototype, - 'on', - ol.interaction.Translate.prototype.on); - -goog.exportProperty( - ol.interaction.Translate.prototype, - 'once', - ol.interaction.Translate.prototype.once); - -goog.exportProperty( - ol.interaction.Translate.prototype, - 'un', - ol.interaction.Translate.prototype.un); - -goog.exportProperty( - ol.interaction.Translate.Event.prototype, - 'type', - ol.interaction.Translate.Event.prototype.type); - -goog.exportProperty( - ol.interaction.Translate.Event.prototype, - 'target', - ol.interaction.Translate.Event.prototype.target); - -goog.exportProperty( - ol.interaction.Translate.Event.prototype, - 'preventDefault', - ol.interaction.Translate.Event.prototype.preventDefault); - -goog.exportProperty( - ol.interaction.Translate.Event.prototype, - 'stopPropagation', - ol.interaction.Translate.Event.prototype.stopPropagation); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'get', - ol.geom.Geometry.prototype.get); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'getKeys', - ol.geom.Geometry.prototype.getKeys); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'getProperties', - ol.geom.Geometry.prototype.getProperties); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'set', - ol.geom.Geometry.prototype.set); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'setProperties', - ol.geom.Geometry.prototype.setProperties); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'unset', - ol.geom.Geometry.prototype.unset); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'changed', - ol.geom.Geometry.prototype.changed); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'dispatchEvent', - ol.geom.Geometry.prototype.dispatchEvent); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'getRevision', - ol.geom.Geometry.prototype.getRevision); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'on', - ol.geom.Geometry.prototype.on); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'once', - ol.geom.Geometry.prototype.once); - -goog.exportProperty( - ol.geom.Geometry.prototype, - 'un', - ol.geom.Geometry.prototype.un); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'getClosestPoint', - ol.geom.SimpleGeometry.prototype.getClosestPoint); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'intersectsCoordinate', - ol.geom.SimpleGeometry.prototype.intersectsCoordinate); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'getExtent', - ol.geom.SimpleGeometry.prototype.getExtent); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'rotate', - ol.geom.SimpleGeometry.prototype.rotate); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'scale', - ol.geom.SimpleGeometry.prototype.scale); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'simplify', - ol.geom.SimpleGeometry.prototype.simplify); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'transform', - ol.geom.SimpleGeometry.prototype.transform); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'get', - ol.geom.SimpleGeometry.prototype.get); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'getKeys', - ol.geom.SimpleGeometry.prototype.getKeys); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'getProperties', - ol.geom.SimpleGeometry.prototype.getProperties); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'set', - ol.geom.SimpleGeometry.prototype.set); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'setProperties', - ol.geom.SimpleGeometry.prototype.setProperties); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'unset', - ol.geom.SimpleGeometry.prototype.unset); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'changed', - ol.geom.SimpleGeometry.prototype.changed); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'dispatchEvent', - ol.geom.SimpleGeometry.prototype.dispatchEvent); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'getRevision', - ol.geom.SimpleGeometry.prototype.getRevision); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'on', - ol.geom.SimpleGeometry.prototype.on); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'once', - ol.geom.SimpleGeometry.prototype.once); - -goog.exportProperty( - ol.geom.SimpleGeometry.prototype, - 'un', - ol.geom.SimpleGeometry.prototype.un); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'getFirstCoordinate', - ol.geom.Circle.prototype.getFirstCoordinate); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'getLastCoordinate', - ol.geom.Circle.prototype.getLastCoordinate); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'getLayout', - ol.geom.Circle.prototype.getLayout); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'rotate', - ol.geom.Circle.prototype.rotate); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'scale', - ol.geom.Circle.prototype.scale); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'getClosestPoint', - ol.geom.Circle.prototype.getClosestPoint); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'intersectsCoordinate', - ol.geom.Circle.prototype.intersectsCoordinate); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'getExtent', - ol.geom.Circle.prototype.getExtent); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'simplify', - ol.geom.Circle.prototype.simplify); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'get', - ol.geom.Circle.prototype.get); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'getKeys', - ol.geom.Circle.prototype.getKeys); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'getProperties', - ol.geom.Circle.prototype.getProperties); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'set', - ol.geom.Circle.prototype.set); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'setProperties', - ol.geom.Circle.prototype.setProperties); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'unset', - ol.geom.Circle.prototype.unset); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'changed', - ol.geom.Circle.prototype.changed); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'dispatchEvent', - ol.geom.Circle.prototype.dispatchEvent); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'getRevision', - ol.geom.Circle.prototype.getRevision); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'on', - ol.geom.Circle.prototype.on); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'once', - ol.geom.Circle.prototype.once); - -goog.exportProperty( - ol.geom.Circle.prototype, - 'un', - ol.geom.Circle.prototype.un); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'getClosestPoint', - ol.geom.GeometryCollection.prototype.getClosestPoint); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'intersectsCoordinate', - ol.geom.GeometryCollection.prototype.intersectsCoordinate); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'getExtent', - ol.geom.GeometryCollection.prototype.getExtent); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'rotate', - ol.geom.GeometryCollection.prototype.rotate); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'scale', - ol.geom.GeometryCollection.prototype.scale); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'simplify', - ol.geom.GeometryCollection.prototype.simplify); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'transform', - ol.geom.GeometryCollection.prototype.transform); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'get', - ol.geom.GeometryCollection.prototype.get); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'getKeys', - ol.geom.GeometryCollection.prototype.getKeys); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'getProperties', - ol.geom.GeometryCollection.prototype.getProperties); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'set', - ol.geom.GeometryCollection.prototype.set); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'setProperties', - ol.geom.GeometryCollection.prototype.setProperties); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'unset', - ol.geom.GeometryCollection.prototype.unset); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'changed', - ol.geom.GeometryCollection.prototype.changed); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'dispatchEvent', - ol.geom.GeometryCollection.prototype.dispatchEvent); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'getRevision', - ol.geom.GeometryCollection.prototype.getRevision); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'on', - ol.geom.GeometryCollection.prototype.on); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'once', - ol.geom.GeometryCollection.prototype.once); - -goog.exportProperty( - ol.geom.GeometryCollection.prototype, - 'un', - ol.geom.GeometryCollection.prototype.un); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'getFirstCoordinate', - ol.geom.LinearRing.prototype.getFirstCoordinate); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'getLastCoordinate', - ol.geom.LinearRing.prototype.getLastCoordinate); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'getLayout', - ol.geom.LinearRing.prototype.getLayout); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'rotate', - ol.geom.LinearRing.prototype.rotate); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'scale', - ol.geom.LinearRing.prototype.scale); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'getClosestPoint', - ol.geom.LinearRing.prototype.getClosestPoint); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'intersectsCoordinate', - ol.geom.LinearRing.prototype.intersectsCoordinate); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'getExtent', - ol.geom.LinearRing.prototype.getExtent); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'simplify', - ol.geom.LinearRing.prototype.simplify); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'transform', - ol.geom.LinearRing.prototype.transform); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'get', - ol.geom.LinearRing.prototype.get); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'getKeys', - ol.geom.LinearRing.prototype.getKeys); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'getProperties', - ol.geom.LinearRing.prototype.getProperties); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'set', - ol.geom.LinearRing.prototype.set); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'setProperties', - ol.geom.LinearRing.prototype.setProperties); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'unset', - ol.geom.LinearRing.prototype.unset); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'changed', - ol.geom.LinearRing.prototype.changed); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'dispatchEvent', - ol.geom.LinearRing.prototype.dispatchEvent); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'getRevision', - ol.geom.LinearRing.prototype.getRevision); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'on', - ol.geom.LinearRing.prototype.on); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'once', - ol.geom.LinearRing.prototype.once); - -goog.exportProperty( - ol.geom.LinearRing.prototype, - 'un', - ol.geom.LinearRing.prototype.un); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'getFirstCoordinate', - ol.geom.LineString.prototype.getFirstCoordinate); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'getLastCoordinate', - ol.geom.LineString.prototype.getLastCoordinate); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'getLayout', - ol.geom.LineString.prototype.getLayout); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'rotate', - ol.geom.LineString.prototype.rotate); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'scale', - ol.geom.LineString.prototype.scale); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'getClosestPoint', - ol.geom.LineString.prototype.getClosestPoint); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'intersectsCoordinate', - ol.geom.LineString.prototype.intersectsCoordinate); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'getExtent', - ol.geom.LineString.prototype.getExtent); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'simplify', - ol.geom.LineString.prototype.simplify); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'transform', - ol.geom.LineString.prototype.transform); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'get', - ol.geom.LineString.prototype.get); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'getKeys', - ol.geom.LineString.prototype.getKeys); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'getProperties', - ol.geom.LineString.prototype.getProperties); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'set', - ol.geom.LineString.prototype.set); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'setProperties', - ol.geom.LineString.prototype.setProperties); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'unset', - ol.geom.LineString.prototype.unset); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'changed', - ol.geom.LineString.prototype.changed); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'dispatchEvent', - ol.geom.LineString.prototype.dispatchEvent); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'getRevision', - ol.geom.LineString.prototype.getRevision); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'on', - ol.geom.LineString.prototype.on); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'once', - ol.geom.LineString.prototype.once); - -goog.exportProperty( - ol.geom.LineString.prototype, - 'un', - ol.geom.LineString.prototype.un); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'getFirstCoordinate', - ol.geom.MultiLineString.prototype.getFirstCoordinate); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'getLastCoordinate', - ol.geom.MultiLineString.prototype.getLastCoordinate); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'getLayout', - ol.geom.MultiLineString.prototype.getLayout); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'rotate', - ol.geom.MultiLineString.prototype.rotate); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'scale', - ol.geom.MultiLineString.prototype.scale); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'getClosestPoint', - ol.geom.MultiLineString.prototype.getClosestPoint); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'intersectsCoordinate', - ol.geom.MultiLineString.prototype.intersectsCoordinate); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'getExtent', - ol.geom.MultiLineString.prototype.getExtent); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'simplify', - ol.geom.MultiLineString.prototype.simplify); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'transform', - ol.geom.MultiLineString.prototype.transform); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'get', - ol.geom.MultiLineString.prototype.get); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'getKeys', - ol.geom.MultiLineString.prototype.getKeys); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'getProperties', - ol.geom.MultiLineString.prototype.getProperties); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'set', - ol.geom.MultiLineString.prototype.set); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'setProperties', - ol.geom.MultiLineString.prototype.setProperties); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'unset', - ol.geom.MultiLineString.prototype.unset); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'changed', - ol.geom.MultiLineString.prototype.changed); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'dispatchEvent', - ol.geom.MultiLineString.prototype.dispatchEvent); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'getRevision', - ol.geom.MultiLineString.prototype.getRevision); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'on', - ol.geom.MultiLineString.prototype.on); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'once', - ol.geom.MultiLineString.prototype.once); - -goog.exportProperty( - ol.geom.MultiLineString.prototype, - 'un', - ol.geom.MultiLineString.prototype.un); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'getFirstCoordinate', - ol.geom.MultiPoint.prototype.getFirstCoordinate); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'getLastCoordinate', - ol.geom.MultiPoint.prototype.getLastCoordinate); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'getLayout', - ol.geom.MultiPoint.prototype.getLayout); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'rotate', - ol.geom.MultiPoint.prototype.rotate); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'scale', - ol.geom.MultiPoint.prototype.scale); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'getClosestPoint', - ol.geom.MultiPoint.prototype.getClosestPoint); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'intersectsCoordinate', - ol.geom.MultiPoint.prototype.intersectsCoordinate); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'getExtent', - ol.geom.MultiPoint.prototype.getExtent); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'simplify', - ol.geom.MultiPoint.prototype.simplify); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'transform', - ol.geom.MultiPoint.prototype.transform); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'get', - ol.geom.MultiPoint.prototype.get); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'getKeys', - ol.geom.MultiPoint.prototype.getKeys); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'getProperties', - ol.geom.MultiPoint.prototype.getProperties); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'set', - ol.geom.MultiPoint.prototype.set); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'setProperties', - ol.geom.MultiPoint.prototype.setProperties); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'unset', - ol.geom.MultiPoint.prototype.unset); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'changed', - ol.geom.MultiPoint.prototype.changed); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'dispatchEvent', - ol.geom.MultiPoint.prototype.dispatchEvent); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'getRevision', - ol.geom.MultiPoint.prototype.getRevision); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'on', - ol.geom.MultiPoint.prototype.on); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'once', - ol.geom.MultiPoint.prototype.once); - -goog.exportProperty( - ol.geom.MultiPoint.prototype, - 'un', - ol.geom.MultiPoint.prototype.un); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'getFirstCoordinate', - ol.geom.MultiPolygon.prototype.getFirstCoordinate); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'getLastCoordinate', - ol.geom.MultiPolygon.prototype.getLastCoordinate); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'getLayout', - ol.geom.MultiPolygon.prototype.getLayout); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'rotate', - ol.geom.MultiPolygon.prototype.rotate); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'scale', - ol.geom.MultiPolygon.prototype.scale); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'getClosestPoint', - ol.geom.MultiPolygon.prototype.getClosestPoint); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'intersectsCoordinate', - ol.geom.MultiPolygon.prototype.intersectsCoordinate); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'getExtent', - ol.geom.MultiPolygon.prototype.getExtent); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'simplify', - ol.geom.MultiPolygon.prototype.simplify); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'transform', - ol.geom.MultiPolygon.prototype.transform); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'get', - ol.geom.MultiPolygon.prototype.get); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'getKeys', - ol.geom.MultiPolygon.prototype.getKeys); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'getProperties', - ol.geom.MultiPolygon.prototype.getProperties); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'set', - ol.geom.MultiPolygon.prototype.set); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'setProperties', - ol.geom.MultiPolygon.prototype.setProperties); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'unset', - ol.geom.MultiPolygon.prototype.unset); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'changed', - ol.geom.MultiPolygon.prototype.changed); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'dispatchEvent', - ol.geom.MultiPolygon.prototype.dispatchEvent); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'getRevision', - ol.geom.MultiPolygon.prototype.getRevision); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'on', - ol.geom.MultiPolygon.prototype.on); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'once', - ol.geom.MultiPolygon.prototype.once); - -goog.exportProperty( - ol.geom.MultiPolygon.prototype, - 'un', - ol.geom.MultiPolygon.prototype.un); - -goog.exportProperty( - ol.geom.Point.prototype, - 'getFirstCoordinate', - ol.geom.Point.prototype.getFirstCoordinate); - -goog.exportProperty( - ol.geom.Point.prototype, - 'getLastCoordinate', - ol.geom.Point.prototype.getLastCoordinate); - -goog.exportProperty( - ol.geom.Point.prototype, - 'getLayout', - ol.geom.Point.prototype.getLayout); - -goog.exportProperty( - ol.geom.Point.prototype, - 'rotate', - ol.geom.Point.prototype.rotate); - -goog.exportProperty( - ol.geom.Point.prototype, - 'scale', - ol.geom.Point.prototype.scale); - -goog.exportProperty( - ol.geom.Point.prototype, - 'getClosestPoint', - ol.geom.Point.prototype.getClosestPoint); - -goog.exportProperty( - ol.geom.Point.prototype, - 'intersectsCoordinate', - ol.geom.Point.prototype.intersectsCoordinate); - -goog.exportProperty( - ol.geom.Point.prototype, - 'getExtent', - ol.geom.Point.prototype.getExtent); - -goog.exportProperty( - ol.geom.Point.prototype, - 'simplify', - ol.geom.Point.prototype.simplify); - -goog.exportProperty( - ol.geom.Point.prototype, - 'transform', - ol.geom.Point.prototype.transform); - -goog.exportProperty( - ol.geom.Point.prototype, - 'get', - ol.geom.Point.prototype.get); - -goog.exportProperty( - ol.geom.Point.prototype, - 'getKeys', - ol.geom.Point.prototype.getKeys); - -goog.exportProperty( - ol.geom.Point.prototype, - 'getProperties', - ol.geom.Point.prototype.getProperties); - -goog.exportProperty( - ol.geom.Point.prototype, - 'set', - ol.geom.Point.prototype.set); - -goog.exportProperty( - ol.geom.Point.prototype, - 'setProperties', - ol.geom.Point.prototype.setProperties); - -goog.exportProperty( - ol.geom.Point.prototype, - 'unset', - ol.geom.Point.prototype.unset); - -goog.exportProperty( - ol.geom.Point.prototype, - 'changed', - ol.geom.Point.prototype.changed); - -goog.exportProperty( - ol.geom.Point.prototype, - 'dispatchEvent', - ol.geom.Point.prototype.dispatchEvent); - -goog.exportProperty( - ol.geom.Point.prototype, - 'getRevision', - ol.geom.Point.prototype.getRevision); - -goog.exportProperty( - ol.geom.Point.prototype, - 'on', - ol.geom.Point.prototype.on); - -goog.exportProperty( - ol.geom.Point.prototype, - 'once', - ol.geom.Point.prototype.once); - -goog.exportProperty( - ol.geom.Point.prototype, - 'un', - ol.geom.Point.prototype.un); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'getFirstCoordinate', - ol.geom.Polygon.prototype.getFirstCoordinate); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'getLastCoordinate', - ol.geom.Polygon.prototype.getLastCoordinate); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'getLayout', - ol.geom.Polygon.prototype.getLayout); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'rotate', - ol.geom.Polygon.prototype.rotate); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'scale', - ol.geom.Polygon.prototype.scale); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'getClosestPoint', - ol.geom.Polygon.prototype.getClosestPoint); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'intersectsCoordinate', - ol.geom.Polygon.prototype.intersectsCoordinate); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'getExtent', - ol.geom.Polygon.prototype.getExtent); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'simplify', - ol.geom.Polygon.prototype.simplify); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'transform', - ol.geom.Polygon.prototype.transform); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'get', - ol.geom.Polygon.prototype.get); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'getKeys', - ol.geom.Polygon.prototype.getKeys); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'getProperties', - ol.geom.Polygon.prototype.getProperties); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'set', - ol.geom.Polygon.prototype.set); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'setProperties', - ol.geom.Polygon.prototype.setProperties); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'unset', - ol.geom.Polygon.prototype.unset); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'changed', - ol.geom.Polygon.prototype.changed); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'dispatchEvent', - ol.geom.Polygon.prototype.dispatchEvent); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'getRevision', - ol.geom.Polygon.prototype.getRevision); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'on', - ol.geom.Polygon.prototype.on); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'once', - ol.geom.Polygon.prototype.once); - -goog.exportProperty( - ol.geom.Polygon.prototype, - 'un', - ol.geom.Polygon.prototype.un); - -goog.exportProperty( - ol.format.GML.prototype, - 'readFeatures', - ol.format.GML.prototype.readFeatures); - -goog.exportProperty( - ol.format.GML2.prototype, - 'readFeatures', - ol.format.GML2.prototype.readFeatures); - -goog.exportProperty( - ol.format.GML3.prototype, - 'readFeatures', - ol.format.GML3.prototype.readFeatures); - -goog.exportProperty( - ol.control.Control.prototype, - 'get', - ol.control.Control.prototype.get); - -goog.exportProperty( - ol.control.Control.prototype, - 'getKeys', - ol.control.Control.prototype.getKeys); - -goog.exportProperty( - ol.control.Control.prototype, - 'getProperties', - ol.control.Control.prototype.getProperties); - -goog.exportProperty( - ol.control.Control.prototype, - 'set', - ol.control.Control.prototype.set); - -goog.exportProperty( - ol.control.Control.prototype, - 'setProperties', - ol.control.Control.prototype.setProperties); - -goog.exportProperty( - ol.control.Control.prototype, - 'unset', - ol.control.Control.prototype.unset); - -goog.exportProperty( - ol.control.Control.prototype, - 'changed', - ol.control.Control.prototype.changed); - -goog.exportProperty( - ol.control.Control.prototype, - 'dispatchEvent', - ol.control.Control.prototype.dispatchEvent); - -goog.exportProperty( - ol.control.Control.prototype, - 'getRevision', - ol.control.Control.prototype.getRevision); - -goog.exportProperty( - ol.control.Control.prototype, - 'on', - ol.control.Control.prototype.on); - -goog.exportProperty( - ol.control.Control.prototype, - 'once', - ol.control.Control.prototype.once); - -goog.exportProperty( - ol.control.Control.prototype, - 'un', - ol.control.Control.prototype.un); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'getMap', - ol.control.Attribution.prototype.getMap); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'setMap', - ol.control.Attribution.prototype.setMap); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'setTarget', - ol.control.Attribution.prototype.setTarget); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'get', - ol.control.Attribution.prototype.get); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'getKeys', - ol.control.Attribution.prototype.getKeys); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'getProperties', - ol.control.Attribution.prototype.getProperties); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'set', - ol.control.Attribution.prototype.set); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'setProperties', - ol.control.Attribution.prototype.setProperties); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'unset', - ol.control.Attribution.prototype.unset); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'changed', - ol.control.Attribution.prototype.changed); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'dispatchEvent', - ol.control.Attribution.prototype.dispatchEvent); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'getRevision', - ol.control.Attribution.prototype.getRevision); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'on', - ol.control.Attribution.prototype.on); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'once', - ol.control.Attribution.prototype.once); - -goog.exportProperty( - ol.control.Attribution.prototype, - 'un', - ol.control.Attribution.prototype.un); - -goog.exportProperty( - ol.control.FullScreen.prototype, - 'getMap', - ol.control.FullScreen.prototype.getMap); - -goog.exportProperty( - ol.control.FullScreen.prototype, - 'setMap', - ol.control.FullScreen.prototype.setMap); - -goog.exportProperty( - ol.control.FullScreen.prototype, - 'setTarget', - ol.control.FullScreen.prototype.setTarget); - -goog.exportProperty( - ol.control.FullScreen.prototype, - 'get', - ol.control.FullScreen.prototype.get); - -goog.exportProperty( - ol.control.FullScreen.prototype, - 'getKeys', - ol.control.FullScreen.prototype.getKeys); - -goog.exportProperty( - ol.control.FullScreen.prototype, - 'getProperties', - ol.control.FullScreen.prototype.getProperties); - -goog.exportProperty( - ol.control.FullScreen.prototype, - 'set', - ol.control.FullScreen.prototype.set); - -goog.exportProperty( - ol.control.FullScreen.prototype, - 'setProperties', - ol.control.FullScreen.prototype.setProperties); - -goog.exportProperty( - ol.control.FullScreen.prototype, - 'unset', - ol.control.FullScreen.prototype.unset); - -goog.exportProperty( - ol.control.FullScreen.prototype, - 'changed', - ol.control.FullScreen.prototype.changed); - -goog.exportProperty( - ol.control.FullScreen.prototype, - 'dispatchEvent', - ol.control.FullScreen.prototype.dispatchEvent); - -goog.exportProperty( - ol.control.FullScreen.prototype, - 'getRevision', - ol.control.FullScreen.prototype.getRevision); - -goog.exportProperty( - ol.control.FullScreen.prototype, - 'on', - ol.control.FullScreen.prototype.on); - -goog.exportProperty( - ol.control.FullScreen.prototype, - 'once', - ol.control.FullScreen.prototype.once); - -goog.exportProperty( - ol.control.FullScreen.prototype, - 'un', - ol.control.FullScreen.prototype.un); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'getMap', - ol.control.MousePosition.prototype.getMap); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'setMap', - ol.control.MousePosition.prototype.setMap); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'setTarget', - ol.control.MousePosition.prototype.setTarget); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'get', - ol.control.MousePosition.prototype.get); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'getKeys', - ol.control.MousePosition.prototype.getKeys); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'getProperties', - ol.control.MousePosition.prototype.getProperties); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'set', - ol.control.MousePosition.prototype.set); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'setProperties', - ol.control.MousePosition.prototype.setProperties); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'unset', - ol.control.MousePosition.prototype.unset); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'changed', - ol.control.MousePosition.prototype.changed); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'dispatchEvent', - ol.control.MousePosition.prototype.dispatchEvent); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'getRevision', - ol.control.MousePosition.prototype.getRevision); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'on', - ol.control.MousePosition.prototype.on); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'once', - ol.control.MousePosition.prototype.once); - -goog.exportProperty( - ol.control.MousePosition.prototype, - 'un', - ol.control.MousePosition.prototype.un); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'getMap', - ol.control.OverviewMap.prototype.getMap); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'setMap', - ol.control.OverviewMap.prototype.setMap); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'setTarget', - ol.control.OverviewMap.prototype.setTarget); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'get', - ol.control.OverviewMap.prototype.get); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'getKeys', - ol.control.OverviewMap.prototype.getKeys); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'getProperties', - ol.control.OverviewMap.prototype.getProperties); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'set', - ol.control.OverviewMap.prototype.set); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'setProperties', - ol.control.OverviewMap.prototype.setProperties); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'unset', - ol.control.OverviewMap.prototype.unset); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'changed', - ol.control.OverviewMap.prototype.changed); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'dispatchEvent', - ol.control.OverviewMap.prototype.dispatchEvent); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'getRevision', - ol.control.OverviewMap.prototype.getRevision); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'on', - ol.control.OverviewMap.prototype.on); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'once', - ol.control.OverviewMap.prototype.once); - -goog.exportProperty( - ol.control.OverviewMap.prototype, - 'un', - ol.control.OverviewMap.prototype.un); - -goog.exportProperty( - ol.control.Rotate.prototype, - 'getMap', - ol.control.Rotate.prototype.getMap); - -goog.exportProperty( - ol.control.Rotate.prototype, - 'setMap', - ol.control.Rotate.prototype.setMap); - -goog.exportProperty( - ol.control.Rotate.prototype, - 'setTarget', - ol.control.Rotate.prototype.setTarget); - -goog.exportProperty( - ol.control.Rotate.prototype, - 'get', - ol.control.Rotate.prototype.get); - -goog.exportProperty( - ol.control.Rotate.prototype, - 'getKeys', - ol.control.Rotate.prototype.getKeys); - -goog.exportProperty( - ol.control.Rotate.prototype, - 'getProperties', - ol.control.Rotate.prototype.getProperties); - -goog.exportProperty( - ol.control.Rotate.prototype, - 'set', - ol.control.Rotate.prototype.set); - -goog.exportProperty( - ol.control.Rotate.prototype, - 'setProperties', - ol.control.Rotate.prototype.setProperties); - -goog.exportProperty( - ol.control.Rotate.prototype, - 'unset', - ol.control.Rotate.prototype.unset); - -goog.exportProperty( - ol.control.Rotate.prototype, - 'changed', - ol.control.Rotate.prototype.changed); - -goog.exportProperty( - ol.control.Rotate.prototype, - 'dispatchEvent', - ol.control.Rotate.prototype.dispatchEvent); - -goog.exportProperty( - ol.control.Rotate.prototype, - 'getRevision', - ol.control.Rotate.prototype.getRevision); - -goog.exportProperty( - ol.control.Rotate.prototype, - 'on', - ol.control.Rotate.prototype.on); - -goog.exportProperty( - ol.control.Rotate.prototype, - 'once', - ol.control.Rotate.prototype.once); - -goog.exportProperty( - ol.control.Rotate.prototype, - 'un', - ol.control.Rotate.prototype.un); - -goog.exportProperty( - ol.control.ScaleLine.prototype, - 'getMap', - ol.control.ScaleLine.prototype.getMap); - -goog.exportProperty( - ol.control.ScaleLine.prototype, - 'setMap', - ol.control.ScaleLine.prototype.setMap); - -goog.exportProperty( - ol.control.ScaleLine.prototype, - 'setTarget', - ol.control.ScaleLine.prototype.setTarget); - -goog.exportProperty( - ol.control.ScaleLine.prototype, - 'get', - ol.control.ScaleLine.prototype.get); - -goog.exportProperty( - ol.control.ScaleLine.prototype, - 'getKeys', - ol.control.ScaleLine.prototype.getKeys); - -goog.exportProperty( - ol.control.ScaleLine.prototype, - 'getProperties', - ol.control.ScaleLine.prototype.getProperties); - -goog.exportProperty( - ol.control.ScaleLine.prototype, - 'set', - ol.control.ScaleLine.prototype.set); - -goog.exportProperty( - ol.control.ScaleLine.prototype, - 'setProperties', - ol.control.ScaleLine.prototype.setProperties); - -goog.exportProperty( - ol.control.ScaleLine.prototype, - 'unset', - ol.control.ScaleLine.prototype.unset); - -goog.exportProperty( - ol.control.ScaleLine.prototype, - 'changed', - ol.control.ScaleLine.prototype.changed); - -goog.exportProperty( - ol.control.ScaleLine.prototype, - 'dispatchEvent', - ol.control.ScaleLine.prototype.dispatchEvent); - -goog.exportProperty( - ol.control.ScaleLine.prototype, - 'getRevision', - ol.control.ScaleLine.prototype.getRevision); - -goog.exportProperty( - ol.control.ScaleLine.prototype, - 'on', - ol.control.ScaleLine.prototype.on); - -goog.exportProperty( - ol.control.ScaleLine.prototype, - 'once', - ol.control.ScaleLine.prototype.once); - -goog.exportProperty( - ol.control.ScaleLine.prototype, - 'un', - ol.control.ScaleLine.prototype.un); - -goog.exportProperty( - ol.control.Zoom.prototype, - 'getMap', - ol.control.Zoom.prototype.getMap); - -goog.exportProperty( - ol.control.Zoom.prototype, - 'setMap', - ol.control.Zoom.prototype.setMap); - -goog.exportProperty( - ol.control.Zoom.prototype, - 'setTarget', - ol.control.Zoom.prototype.setTarget); - -goog.exportProperty( - ol.control.Zoom.prototype, - 'get', - ol.control.Zoom.prototype.get); - -goog.exportProperty( - ol.control.Zoom.prototype, - 'getKeys', - ol.control.Zoom.prototype.getKeys); - -goog.exportProperty( - ol.control.Zoom.prototype, - 'getProperties', - ol.control.Zoom.prototype.getProperties); - -goog.exportProperty( - ol.control.Zoom.prototype, - 'set', - ol.control.Zoom.prototype.set); - -goog.exportProperty( - ol.control.Zoom.prototype, - 'setProperties', - ol.control.Zoom.prototype.setProperties); - -goog.exportProperty( - ol.control.Zoom.prototype, - 'unset', - ol.control.Zoom.prototype.unset); - -goog.exportProperty( - ol.control.Zoom.prototype, - 'changed', - ol.control.Zoom.prototype.changed); - -goog.exportProperty( - ol.control.Zoom.prototype, - 'dispatchEvent', - ol.control.Zoom.prototype.dispatchEvent); - -goog.exportProperty( - ol.control.Zoom.prototype, - 'getRevision', - ol.control.Zoom.prototype.getRevision); - -goog.exportProperty( - ol.control.Zoom.prototype, - 'on', - ol.control.Zoom.prototype.on); - -goog.exportProperty( - ol.control.Zoom.prototype, - 'once', - ol.control.Zoom.prototype.once); - -goog.exportProperty( - ol.control.Zoom.prototype, - 'un', - ol.control.Zoom.prototype.un); - -goog.exportProperty( - ol.control.ZoomSlider.prototype, - 'getMap', - ol.control.ZoomSlider.prototype.getMap); - -goog.exportProperty( - ol.control.ZoomSlider.prototype, - 'setMap', - ol.control.ZoomSlider.prototype.setMap); - -goog.exportProperty( - ol.control.ZoomSlider.prototype, - 'setTarget', - ol.control.ZoomSlider.prototype.setTarget); - -goog.exportProperty( - ol.control.ZoomSlider.prototype, - 'get', - ol.control.ZoomSlider.prototype.get); - -goog.exportProperty( - ol.control.ZoomSlider.prototype, - 'getKeys', - ol.control.ZoomSlider.prototype.getKeys); - -goog.exportProperty( - ol.control.ZoomSlider.prototype, - 'getProperties', - ol.control.ZoomSlider.prototype.getProperties); - -goog.exportProperty( - ol.control.ZoomSlider.prototype, - 'set', - ol.control.ZoomSlider.prototype.set); - -goog.exportProperty( - ol.control.ZoomSlider.prototype, - 'setProperties', - ol.control.ZoomSlider.prototype.setProperties); - -goog.exportProperty( - ol.control.ZoomSlider.prototype, - 'unset', - ol.control.ZoomSlider.prototype.unset); - -goog.exportProperty( - ol.control.ZoomSlider.prototype, - 'changed', - ol.control.ZoomSlider.prototype.changed); - -goog.exportProperty( - ol.control.ZoomSlider.prototype, - 'dispatchEvent', - ol.control.ZoomSlider.prototype.dispatchEvent); - -goog.exportProperty( - ol.control.ZoomSlider.prototype, - 'getRevision', - ol.control.ZoomSlider.prototype.getRevision); - -goog.exportProperty( - ol.control.ZoomSlider.prototype, - 'on', - ol.control.ZoomSlider.prototype.on); - -goog.exportProperty( - ol.control.ZoomSlider.prototype, - 'once', - ol.control.ZoomSlider.prototype.once); - -goog.exportProperty( - ol.control.ZoomSlider.prototype, - 'un', - ol.control.ZoomSlider.prototype.un); - -goog.exportProperty( - ol.control.ZoomToExtent.prototype, - 'getMap', - ol.control.ZoomToExtent.prototype.getMap); - -goog.exportProperty( - ol.control.ZoomToExtent.prototype, - 'setMap', - ol.control.ZoomToExtent.prototype.setMap); - -goog.exportProperty( - ol.control.ZoomToExtent.prototype, - 'setTarget', - ol.control.ZoomToExtent.prototype.setTarget); - -goog.exportProperty( - ol.control.ZoomToExtent.prototype, - 'get', - ol.control.ZoomToExtent.prototype.get); - -goog.exportProperty( - ol.control.ZoomToExtent.prototype, - 'getKeys', - ol.control.ZoomToExtent.prototype.getKeys); - -goog.exportProperty( - ol.control.ZoomToExtent.prototype, - 'getProperties', - ol.control.ZoomToExtent.prototype.getProperties); - -goog.exportProperty( - ol.control.ZoomToExtent.prototype, - 'set', - ol.control.ZoomToExtent.prototype.set); - -goog.exportProperty( - ol.control.ZoomToExtent.prototype, - 'setProperties', - ol.control.ZoomToExtent.prototype.setProperties); - -goog.exportProperty( - ol.control.ZoomToExtent.prototype, - 'unset', - ol.control.ZoomToExtent.prototype.unset); - -goog.exportProperty( - ol.control.ZoomToExtent.prototype, - 'changed', - ol.control.ZoomToExtent.prototype.changed); - -goog.exportProperty( - ol.control.ZoomToExtent.prototype, - 'dispatchEvent', - ol.control.ZoomToExtent.prototype.dispatchEvent); - -goog.exportProperty( - ol.control.ZoomToExtent.prototype, - 'getRevision', - ol.control.ZoomToExtent.prototype.getRevision); - -goog.exportProperty( - ol.control.ZoomToExtent.prototype, - 'on', - ol.control.ZoomToExtent.prototype.on); - -goog.exportProperty( - ol.control.ZoomToExtent.prototype, - 'once', - ol.control.ZoomToExtent.prototype.once); - -goog.exportProperty( - ol.control.ZoomToExtent.prototype, - 'un', - ol.control.ZoomToExtent.prototype.un); -ol.VERSION = 'v4.4.2'; -OPENLAYERS.ol = ol; - - return OPENLAYERS.ol; -})); diff --git a/app/resources/js/ol.js b/app/resources/js/ol.js deleted file mode 100644 index 6659cac..0000000 --- a/app/resources/js/ol.js +++ /dev/null @@ -1,2 +0,0 @@ -!function(){"use strict";var e=0;function Et(t){return t.ol_uid||(t.ol_uid=++e)}var n=function(i){function t(t){var e="Assertion failed. See https://openlayers.org/en/"+"5.1.3".split("-")[0]+"/doc/errors/#"+t+" for details.";i.call(this,e),this.code=t,this.name="AssertionError",this.message=e}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(Error),h="add",l="remove",a="propertychange",C="function"==typeof Object.assign?Object.assign:function(t,e){var i=arguments;if(null==t)throw new TypeError("Cannot convert undefined or null to object");for(var r=Object(t),n=1,o=arguments.length;n<o;++n){var s=i[n];if(null!=s)for(var a in s)s.hasOwnProperty(a)&&(r[a]=s[a])}return r};function _(t){for(var e in t)delete t[e]}function o(t){var e=[];for(var i in t)e.push(t[i]);return e}function Tt(t){var e;for(e in t)return!1;return!e}function u(t,e,i,r){for(var n,o=0,s=t.length;o<s;++o)if((n=t[o]).listener===e&&n.bindTo===i)return r&&(n.deleteIndex=o),n}function s(t,e){var i=t.ol_lm;return i?i[e]:void 0}function c(t){var e=t.ol_lm;return e||(e=t.ol_lm={}),e}function r(t,e){var i=s(t,e);if(i){for(var r=0,n=i.length;r<n;++r)t.removeEventListener(e,i[r].boundListener),_(i[r]);i.length=0;var o=t.ol_lm;o&&(delete o[e],0===Object.keys(o).length&&delete t.ol_lm)}}function E(t,e,i,r,n){var o=c(t),s=o[e];s||(s=o[e]=[]);var a,h,l=u(s,i,r,!1);return l?n||(l.callOnce=!1):(l={bindTo:r,callOnce:!!n,listener:i,target:t,type:e},t.addEventListener(e,(h=function(t){var e=a.listener,i=a.bindTo||a.target;return a.callOnce&&g(a),e.call(i,t)},(a=l).boundListener=h)),s.push(l)),l}function p(t,e,i,r){return E(t,e,i,r,!0)}function d(t,e,i,r){var n=s(t,e);if(n){var o=u(n,i,r,!0);o&&g(o)}}function g(t){if(t&&t.target){t.target.removeEventListener(t.type,t.boundListener);var e=s(t.target,t.type);if(e){var i="deleteIndex"in t?t.deleteIndex:e.indexOf(t);-1!==i&&e.splice(i,1),0===e.length&&r(t.target,t.type)}_(t)}}function f(t){var e=c(t);for(var i in e)r(t,i)}function y(){return!0}function v(){return!1}function L(){}var t=function(){};t.prototype.dispose=function(){this.disposed_||(this.disposed_=!0,this.disposeInternal())},t.prototype.disposed_=!1,t.prototype.disposeInternal=L;var m=function(t){this.propagationStopped,this.type=t,this.target=null};function x(t){t.stopPropagation()}m.prototype.preventDefault=function(){this.propagationStopped=!0},m.prototype.stopPropagation=function(){this.propagationStopped=!0};var i=function(t){function e(){t.call(this),this.pendingRemovals_={},this.dispatching_={},this.listeners_={}}return t&&(e.__proto__=t),((e.prototype=Object.create(t&&t.prototype)).constructor=e).prototype.addEventListener=function(t,e){var i=this.listeners_[t];i||(i=this.listeners_[t]=[]),-1===i.indexOf(e)&&i.push(e)},e.prototype.dispatchEvent=function(t){var e,i="string"==typeof t?new m(t):t,r=i.type,n=(i.target=this).listeners_[r];if(n){r in this.dispatching_||(this.dispatching_[r]=0,this.pendingRemovals_[r]=0),++this.dispatching_[r];for(var o=0,s=n.length;o<s;++o)if(!1===n[o].call(this,i)||i.propagationStopped){e=!1;break}if(--this.dispatching_[r],0===this.dispatching_[r]){var a=this.pendingRemovals_[r];for(delete this.pendingRemovals_[r];a--;)this.removeEventListener(r,L);delete this.dispatching_[r]}return e}},e.prototype.disposeInternal=function(){f(this)},e.prototype.getListeners=function(t){return this.listeners_[t]},e.prototype.hasListener=function(t){return t?t in this.listeners_:0<Object.keys(this.listeners_).length},e.prototype.removeEventListener=function(t,e){var i=this.listeners_[t];if(i){var r=i.indexOf(e);t in this.pendingRemovals_?(i[r]=L,++this.pendingRemovals_[t]):(i.splice(r,1),0===i.length&&delete this.listeners_[t])}},e}(t),w={CHANGE:"change",CLEAR:"clear",CONTEXTMENU:"contextmenu",CLICK:"click",DBLCLICK:"dblclick",DRAGENTER:"dragenter",DRAGOVER:"dragover",DROP:"drop",ERROR:"error",KEYDOWN:"keydown",KEYPRESS:"keypress",LOAD:"load",MOUSEDOWN:"mousedown",MOUSEMOVE:"mousemove",MOUSEOUT:"mouseout",MOUSEUP:"mouseup",MOUSEWHEEL:"mousewheel",MSPOINTERDOWN:"MSPointerDown",RESIZE:"resize",TOUCHSTART:"touchstart",TOUCHMOVE:"touchmove",TOUCHEND:"touchend",WHEEL:"wheel"},S=function(t){function e(){t.call(this),this.revision_=0}return t&&(e.__proto__=t),((e.prototype=Object.create(t&&t.prototype)).constructor=e).prototype.changed=function(){++this.revision_,this.dispatchEvent(w.CHANGE)},e.prototype.getRevision=function(){return this.revision_},e.prototype.on=function(t,e){if(Array.isArray(t)){for(var i=t.length,r=new Array(i),n=0;n<i;++n)r[n]=E(this,t[n],e);return r}return E(this,t,e)},e.prototype.once=function(t,e){if(Array.isArray(t)){for(var i=t.length,r=new Array(i),n=0;n<i;++n)r[n]=p(this,t[n],e);return r}return p(this,t,e)},e.prototype.un=function(t,e){if(Array.isArray(t))for(var i=0,r=t.length;i<r;++i)d(this,t[i],e);else d(this,t,e)},e}(i);var T=function(r){function t(t,e,i){r.call(this,t),this.key=e,this.oldValue=i}return r&&(t.__proto__=r),(t.prototype=Object.create(r&&r.prototype)).constructor=t}(m),R=function(e){function t(t){e.call(this),Et(this),this.values_={},void 0!==t&&this.setProperties(t)}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.get=function(t){var e;return this.values_.hasOwnProperty(t)&&(e=this.values_[t]),e},t.prototype.getKeys=function(){return Object.keys(this.values_)},t.prototype.getProperties=function(){return C({},this.values_)},t.prototype.notify=function(t,e){var i;i=b(t),this.dispatchEvent(new T(i,t,e)),i=a,this.dispatchEvent(new T(i,t,e))},t.prototype.set=function(t,e,i){if(i)this.values_[t]=e;else{var r=this.values_[t];r!==(this.values_[t]=e)&&this.notify(t,r)}},t.prototype.setProperties=function(t,e){for(var i in t)this.set(i,t[i],e)},t.prototype.unset=function(t,e){if(t in this.values_){var i=this.values_[t];delete this.values_[t],e||this.notify(t,i)}},t}(S),I={};function b(t){return I.hasOwnProperty(t)?I[t]:I[t]="change:"+t}var P="length",F=function(i){function t(t,e){i.call(this,t),this.element=e}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(m),M=function(o){function t(t,e){o.call(this);var i=e||{};if(this.unique_=!!i.unique,this.array_=t||[],this.unique_)for(var r=0,n=this.array_.length;r<n;++r)this.assertUnique_(this.array_[r],r);this.updateLength_()}return o&&(t.__proto__=o),((t.prototype=Object.create(o&&o.prototype)).constructor=t).prototype.clear=function(){for(;0<this.getLength();)this.pop()},t.prototype.extend=function(t){for(var e=0,i=t.length;e<i;++e)this.push(t[e]);return this},t.prototype.forEach=function(t){for(var e=this.array_,i=0,r=e.length;i<r;++i)t(e[i],i,e)},t.prototype.getArray=function(){return this.array_},t.prototype.item=function(t){return this.array_[t]},t.prototype.getLength=function(){return this.get(P)},t.prototype.insertAt=function(t,e){this.unique_&&this.assertUnique_(e),this.array_.splice(t,0,e),this.updateLength_(),this.dispatchEvent(new F(h,e))},t.prototype.pop=function(){return this.removeAt(this.getLength()-1)},t.prototype.push=function(t){this.unique_&&this.assertUnique_(t);var e=this.getLength();return this.insertAt(e,t),this.getLength()},t.prototype.remove=function(t){for(var e=this.array_,i=0,r=e.length;i<r;++i)if(e[i]===t)return this.removeAt(i)},t.prototype.removeAt=function(t){var e=this.array_[t];return this.array_.splice(t,1),this.updateLength_(),this.dispatchEvent(new F(l,e)),e},t.prototype.setAt=function(t,e){var i=this.getLength();if(t<i){this.unique_&&this.assertUnique_(e,t);var r=this.array_[t];this.array_[t]=e,this.dispatchEvent(new F(l,r)),this.dispatchEvent(new F(h,e))}else{for(var n=i;n<t;++n)this.insertAt(n,void 0);this.insertAt(t,e)}},t.prototype.updateLength_=function(){this.set(P,this.array_.length)},t.prototype.assertUnique_=function(t,e){for(var i=0,r=this.array_.length;i<r;++i)if(this.array_[i]===t&&i!==e)throw new n(58)},t}(R);function Z(t,e){if(!t)throw new n(e)}var O={BOTTOM_LEFT:"bottom-left",BOTTOM_RIGHT:"bottom-right",TOP_LEFT:"top-left",TOP_RIGHT:"top-right"},N={UNKNOWN:0,INTERSECTING:1,ABOVE:2,RIGHT:4,BELOW:8,LEFT:16};function A(t){for(var e=B(),i=0,r=t.length;i<r;++i)q(e,t[i]);return e}function G(t,e,i){return i?(i[0]=t[0]-e,i[1]=t[1]-e,i[2]=t[2]+e,i[3]=t[3]+e,i):[t[0]-e,t[1]-e,t[2]+e,t[3]+e]}function k(t,e){return e?(e[0]=t[0],e[1]=t[1],e[2]=t[2],e[3]=t[3],e):t.slice()}function D(t,e,i){var r,n;return(r=e<t[0]?t[0]-e:t[2]<e?e-t[2]:0)*r+(n=i<t[1]?t[1]-i:t[3]<i?i-t[3]:0)*n}function j(t,e){return U(t,e[0],e[1])}function Q(t,e){return t[0]<=e[0]&&e[2]<=t[2]&&t[1]<=e[1]&&e[3]<=t[3]}function U(t,e,i){return t[0]<=e&&e<=t[2]&&t[1]<=i&&i<=t[3]}function Y(t,e){var i=t[0],r=t[1],n=t[2],o=t[3],s=e[0],a=e[1],h=N.UNKNOWN;return s<i?h|=N.LEFT:n<s&&(h|=N.RIGHT),a<r?h|=N.BELOW:o<a&&(h|=N.ABOVE),h===N.UNKNOWN&&(h=N.INTERSECTING),h}function B(){return[1/0,1/0,-1/0,-1/0]}function X(t,e,i,r,n){return n?(n[0]=t,n[1]=e,n[2]=i,n[3]=r,n):[t,e,i,r]}function z(t){return X(1/0,1/0,-1/0,-1/0,t)}function V(t,e){var i=t[0],r=t[1];return X(i,r,i,r,e)}function W(t,e){return function(t,e){for(var i=0,r=e.length;i<r;++i)q(t,e[i]);return t}(z(e),t)}function K(t,e,i,r,n){return J(z(n),t,e,i,r)}function $(t,e){return t[0]==e[0]&&t[2]==e[2]&&t[1]==e[1]&&t[3]==e[3]}function H(t,e){return e[0]<t[0]&&(t[0]=e[0]),e[2]>t[2]&&(t[2]=e[2]),e[1]<t[1]&&(t[1]=e[1]),e[3]>t[3]&&(t[3]=e[3]),t}function q(t,e){e[0]<t[0]&&(t[0]=e[0]),e[0]>t[2]&&(t[2]=e[0]),e[1]<t[1]&&(t[1]=e[1]),e[1]>t[3]&&(t[3]=e[1])}function J(t,e,i,r,n){for(;i<r;i+=n)tt(t,e[i],e[i+1]);return t}function tt(t,e,i){t[0]=Math.min(t[0],e),t[1]=Math.min(t[1],i),t[2]=Math.max(t[2],e),t[3]=Math.max(t[3],i)}function et(t,e,i){var r;return(r=e.call(i,rt(t)))?r:(r=e.call(i,nt(t)))?r:(r=e.call(i,ut(t)))?r:(r=e.call(i,lt(t)))||!1}function it(t){var e=0;return pt(t)||(e=ct(t)*at(t)),e}function rt(t){return[t[0],t[1]]}function nt(t){return[t[2],t[1]]}function ot(t){return[(t[0]+t[2])/2,(t[1]+t[3])/2]}function st(t,e,i,r,n){var o=e*r[0]/2,s=e*r[1]/2,a=Math.cos(i),h=Math.sin(i),l=o*a,u=o*h,c=s*a,p=s*h,d=t[0],f=t[1],_=d-l+p,g=d-l-p,y=d+l-p,v=d+l+p,m=f-u-c,x=f-u+c,S=f+u+c,C=f+u-c;return X(Math.min(_,g,y,v),Math.min(m,x,S,C),Math.max(_,g,y,v),Math.max(m,x,S,C),n)}function at(t){return t[3]-t[1]}function ht(t,e,i){var r=i||[1/0,1/0,-1/0,-1/0];return wt(t,e)?(t[0]>e[0]?r[0]=t[0]:r[0]=e[0],t[1]>e[1]?r[1]=t[1]:r[1]=e[1],t[2]<e[2]?r[2]=t[2]:r[2]=e[2],t[3]<e[3]?r[3]=t[3]:r[3]=e[3]):z(r),r}function lt(t){return[t[0],t[3]]}function ut(t){return[t[2],t[3]]}function ct(t){return t[2]-t[0]}function wt(t,e){return t[0]<=e[2]&&t[2]>=e[0]&&t[1]<=e[3]&&t[3]>=e[1]}function pt(t){return t[2]<t[0]||t[3]<t[1]}function dt(t,e){var i=(t[2]-t[0])/2*(e-1),r=(t[3]-t[1])/2*(e-1);t[0]-=i,t[2]+=i,t[1]-=r,t[3]+=r}function ft(t,e,i){var r,n,o,s=[t[0],t[1],t[0],t[3],t[2],t[1],t[2],t[3]];return e(s,s,2),r=[s[0],s[2],s[4],s[6]],n=[s[1],s[3],s[5],s[7]],o=i,X(Math.min.apply(null,r),Math.min.apply(null,n),Math.max.apply(null,r),Math.max.apply(null,n),o)}function Rt(t,e,i,r,n,o){for(var s=o||[],a=0,h=e;h<i;h+=r){var l=t[h],u=t[h+1];s[a++]=n[0]*l+n[2]*u+n[4],s[a++]=n[1]*l+n[3]*u+n[5]}return o&&s.length!=a&&(s.length=a),s}function _t(t,e,i,r,n,o,s){for(var a=s||[],h=0,l=e;l<i;l+=r){a[h++]=t[l]+n,a[h++]=t[l+1]+o;for(var u=l+2;u<l+r;++u)a[h++]=t[u]}return s&&a.length!=h&&(a.length=h),a}function gt(t,e,i){return Math.min(Math.max(t,e),i)}var yt="cosh"in Math?Math.cosh:function(t){var e=Math.exp(t);return(e+1/e)/2};function vt(t,e,i,r,n,o){var s=n-i,a=o-r;if(0!==s||0!==a){var h=((t-i)*s+(e-r)*a)/(s*s+a*a);1<h?(i=n,r=o):0<h&&(i+=s*h,r+=a*h)}return mt(t,e,i,r)}function mt(t,e,i,r){var n=i-t,o=r-e;return n*n+o*o}function xt(t){return 180*t/Math.PI}function St(t){return t*Math.PI/180}function Ct(t,e){var i=t%e;return i*e<0?i+e:i}function It(t,e,i){return t+i*(e-t)}var Lt={POINT:"Point",LINE_STRING:"LineString",LINEAR_RING:"LinearRing",POLYGON:"Polygon",MULTI_POINT:"MultiPoint",MULTI_LINE_STRING:"MultiLineString",MULTI_POLYGON:"MultiPolygon",GEOMETRY_COLLECTION:"GeometryCollection",CIRCLE:"Circle"},bt=6371008.8;function Pt(t,e,i){var r=i||bt,n=St(t[1]),o=St(e[1]),s=(o-n)/2,a=St(e[0]-t[0])/2,h=Math.sin(s)*Math.sin(s)+Math.sin(a)*Math.sin(a)*Math.cos(n)*Math.cos(o);return 2*r*Math.atan2(Math.sqrt(h),Math.sqrt(1-h))}function Ft(t,e){for(var i=0,r=0,n=t.length;r<n-1;++r)i+=Pt(t[r],t[r+1],e);return i}function Mt(t,e){for(var i=0,r=t.length,n=t[r-1][0],o=t[r-1][1],s=0;s<r;s++){var a=t[s][0],h=t[s][1];i+=St(a-n)*(2+Math.sin(St(o))+Math.sin(St(h))),n=a,o=h}return i*e*e/2}var Ot={DEGREES:"degrees",FEET:"ft",METERS:"m",PIXELS:"pixels",TILE_PIXELS:"tile-pixels",USFEET:"us-ft"},Nt={};Nt[Ot.DEGREES]=2*Math.PI*6370997/360,Nt[Ot.FEET]=.3048,Nt[Ot.METERS]=1,Nt[Ot.USFEET]=1200/3937;var At=function(t){this.code_=t.code,this.units_=t.units,this.extent_=void 0!==t.extent?t.extent:null,this.worldExtent_=void 0!==t.worldExtent?t.worldExtent:null,this.axisOrientation_=void 0!==t.axisOrientation?t.axisOrientation:"enu",this.global_=void 0!==t.global&&t.global,this.canWrapX_=!(!this.global_||!this.extent_),this.getPointResolutionFunc_=t.getPointResolution,this.defaultTileGrid_=null,this.metersPerUnit_=t.metersPerUnit};At.prototype.canWrapX=function(){return this.canWrapX_},At.prototype.getCode=function(){return this.code_},At.prototype.getExtent=function(){return this.extent_},At.prototype.getUnits=function(){return this.units_},At.prototype.getMetersPerUnit=function(){return this.metersPerUnit_||Nt[this.units_]},At.prototype.getWorldExtent=function(){return this.worldExtent_},At.prototype.getAxisOrientation=function(){return this.axisOrientation_},At.prototype.isGlobal=function(){return this.global_},At.prototype.setGlobal=function(t){this.global_=t,this.canWrapX_=!(!t||!this.extent_)},At.prototype.getDefaultTileGrid=function(){return this.defaultTileGrid_},At.prototype.setDefaultTileGrid=function(t){this.defaultTileGrid_=t},At.prototype.setExtent=function(t){this.extent_=t,this.canWrapX_=!(!this.global_||!t)},At.prototype.setWorldExtent=function(t){this.worldExtent_=t},At.prototype.setGetPointResolution=function(t){this.getPointResolutionFunc_=t},At.prototype.getPointResolutionFunc=function(){return this.getPointResolutionFunc_};var Gt=6378137,kt=Math.PI*Gt,Dt=[-kt,-kt,kt,kt],jt=[-180,-85,180,85],Ut=function(e){function t(t){e.call(this,{code:t,units:Ot.METERS,extent:Dt,global:!0,worldExtent:jt,getPointResolution:function(t,e){return t/yt(e[1]/Gt)}})}return e&&(t.__proto__=e),(t.prototype=Object.create(e&&e.prototype)).constructor=t}(At),Yt=[new Ut("EPSG:3857"),new Ut("EPSG:102100"),new Ut("EPSG:102113"),new Ut("EPSG:900913"),new Ut("urn:ogc:def:crs:EPSG:6.18:3:3857"),new Ut("urn:ogc:def:crs:EPSG::3857"),new Ut("http://www.opengis.net/gml/srs/epsg.xml#3857")];function Bt(t,e,i){var r=t.length,n=1<i?i:2,o=e;void 0===o&&(o=2<n?t.slice():new Array(r));for(var s=kt,a=0;a<r;a+=n){o[a]=s*t[a]/180;var h=Gt*Math.log(Math.tan(Math.PI*(t[a+1]+90)/360));s<h?h=s:h<-s&&(h=-s),o[a+1]=h}return o}function Xt(t,e,i){var r=t.length,n=1<i?i:2,o=e;void 0===o&&(o=2<n?t.slice():new Array(r));for(var s=0;s<r;s+=n)o[s]=180*t[s]/kt,o[s+1]=360*Math.atan(Math.exp(t[s+1]/Gt))/Math.PI-90;return o}var zt=[-180,-90,180,90],Vt=6378137*Math.PI/180,Wt=function(i){function t(t,e){i.call(this,{code:t,units:Ot.DEGREES,extent:zt,axisOrientation:e,global:!0,metersPerUnit:Vt,worldExtent:zt})}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(At),Kt=[new Wt("CRS:84"),new Wt("EPSG:4326","neu"),new Wt("urn:ogc:def:crs:EPSG::4326","neu"),new Wt("urn:ogc:def:crs:EPSG:6.6:4326","neu"),new Wt("urn:ogc:def:crs:OGC:1.3:CRS84"),new Wt("urn:ogc:def:crs:OGC:2:84"),new Wt("http://www.opengis.net/gml/srs/epsg.xml#4326","neu"),new Wt("urn:x-ogc:def:crs:EPSG:4326","neu")],Ht={};var Zt,qt,Jt,Qt={};function $t(t,e,i){var r=t.getCode(),n=e.getCode();r in Qt||(Qt[r]={}),Qt[r][n]=i}function te(t,e){var i;return t in Qt&&e in Qt[t]&&(i=Qt[t][e]),i}function ee(t,e,i){var r;if(void 0!==e){for(var n=0,o=t.length;n<o;++n)e[n]=t[n];r=e}else r=t.slice();return r}function ie(t,e,i){if(void 0!==e&&t!==e){for(var r=0,n=t.length;r<n;++r)e[r]=t[r];t=e}return t}function re(t){var e,i;e=t.getCode(),i=t,Ht[e]=i,$t(t,t,ee)}function ne(t){var e=null;if(t instanceof At)e=t;else if("string"==typeof t){e=Ht[t]||null}return e}function oe(t,e,i,r){var n,o=(t=ne(t)).getPointResolutionFunc();if(o)n=o(e,i);else if(t.getUnits()==Ot.DEGREES&&!r||r==Ot.DEGREES)n=e;else{var s=ce(t,ne("EPSG:4326")),a=[i[0]-e/2,i[1],i[0]+e/2,i[1],i[0],i[1]-e/2,i[0],i[1]+e/2];n=(Pt((a=s(a,a,2)).slice(0,2),a.slice(2,4))+Pt(a.slice(4,6),a.slice(6,8)))/2;var h=r?Nt[r]:t.getMetersPerUnit();void 0!==h&&(n/=h)}return n}function se(t){t.forEach(re),t.forEach(function(e){t.forEach(function(t){e!==t&&$t(e,t,ee)})})}function ae(t,e){return t?"string"==typeof t?ne(t):t:ne(e)}function he(l){return function(t,e,i){for(var r=t.length,n=void 0!==i?i:2,o=void 0!==e?e:new Array(r),s=0;s<r;s+=n){var a=l([t[s],t[s+1]]);o[s]=a[0],o[s+1]=a[1];for(var h=n-1;2<=h;--h)o[s+h]=t[s+h]}return o}}function le(t,e,i,r){var n=ne(t),o=ne(e);$t(n,o,he(i)),$t(o,n,he(r))}function ue(t,e){if(t===e)return!0;var i=t.getUnits()===e.getUnits();return t.getCode()===e.getCode()?i:ce(t,e)===ee&&i}function ce(t,e){var i=te(t.getCode(),e.getCode());return i||(i=ie),i}function pe(t,e){return ce(ne(t),ne(e))}function de(t,e,i){return pe(e,i)(t,void 0,t.length)}function fe(t,e,i){return ft(t,pe(e,i))}se(Yt),se(Kt),Zt=Yt,qt=Bt,Jt=Xt,Kt.forEach(function(e){Zt.forEach(function(t){$t(e,t,qt),$t(t,e,Jt)})});var _e=new Array(6);function ge(t){return ve(t,1,0,0,1,0,0)}function ye(t,e){var i=t[0],r=t[1],n=t[2],o=t[3],s=t[4],a=t[5],h=e[0],l=e[1],u=e[2],c=e[3],p=e[4],d=e[5];return t[0]=i*h+n*l,t[1]=r*h+o*l,t[2]=i*u+n*c,t[3]=r*u+o*c,t[4]=i*p+n*d+s,t[5]=r*p+o*d+a,t}function ve(t,e,i,r,n,o,s){return t[0]=e,t[1]=i,t[2]=r,t[3]=n,t[4]=o,t[5]=s,t}function me(t,e){return t[0]=e[0],t[1]=e[1],t[2]=e[2],t[3]=e[3],t[4]=e[4],t[5]=e[5],t}function xe(t,e){var i=e[0],r=e[1];return e[0]=t[0]*i+t[2]*r+t[4],e[1]=t[1]*i+t[3]*r+t[5],e}function Se(t,e){var i=Math.cos(e),r=Math.sin(e);return ye(t,ve(_e,i,r,-r,i,0,0))}function Ce(t,e,i){return ye(t,ve(_e,e,0,0,i,0,0))}function Ee(t,e,i){return ye(t,ve(_e,1,0,0,1,e,i))}function Te(t,e,i,r,n,o,s,a){var h=Math.sin(o),l=Math.cos(o);return t[0]=r*l,t[1]=n*h,t[2]=-r*h,t[3]=n*l,t[4]=s*r*l-a*r*h+e,t[5]=s*n*h+a*n*l+i,t}function we(t){var e,i=(e=t)[0]*e[3]-e[1]*e[2];Z(0!==i,32);var r=t[0],n=t[1],o=t[2],s=t[3],a=t[4],h=t[5];return t[0]=s/i,t[1]=-n/i,t[2]=-o/i,t[3]=r/i,t[4]=(o*h-s*a)/i,t[5]=-(r*h-n*a)/i,t}var Re=[1,0,0,1,0,0],Ie=function(t){function e(){t.call(this),this.extent_=[1/0,1/0,-1/0,-1/0],this.extentRevision_=-1,this.simplifiedGeometryCache={},this.simplifiedGeometryMaxMinSquaredTolerance=0,this.simplifiedGeometryRevision=0}return t&&(e.__proto__=t),((e.prototype=Object.create(t&&t.prototype)).constructor=e).prototype.clone=function(){},e.prototype.closestPointXY=function(t,e,i,r){},e.prototype.getClosestPoint=function(t,e){var i=e||[NaN,NaN];return this.closestPointXY(t[0],t[1],i,1/0),i},e.prototype.intersectsCoordinate=function(t){return this.containsXY(t[0],t[1])},e.prototype.computeExtent=function(t){},e.prototype.getExtent=function(t){return this.extentRevision_!=this.getRevision()&&(this.extent_=this.computeExtent(this.extent_),this.extentRevision_=this.getRevision()),e=this.extent_,(i=t)?(i[0]=e[0],i[1]=e[1],i[2]=e[2],i[3]=e[3],i):e;var e,i},e.prototype.rotate=function(t,e){},e.prototype.scale=function(t,e,i){},e.prototype.translate=function(t,e){},e.prototype.simplify=function(t){return this.getSimplifiedGeometry(t*t)},e.prototype.getSimplifiedGeometry=function(t){},e.prototype.getType=function(){},e.prototype.applyTransform=function(t){},e.prototype.intersectsExtent=function(t){},e.prototype.translate=function(t,e){},e.prototype.transform=function(s,a){var t=(s=ne(s)).getUnits()==Ot.TILE_PIXELS?function(t,e,i){var r=s.getExtent(),n=s.getWorldExtent(),o=at(n)/at(r);return Te(Re,n[0],n[3],o,-o,0,0,0),Rt(t,0,t.length,i,Re,e),pe(s,a)(t,e,i)}:pe(s,a);return this.applyTransform(t),this},e}(R);Ie.prototype.containsXY=v;var Le=/^#([a-f0-9]{3}|[a-f0-9]{4}(?:[a-f0-9]{2}){0,2})$/i,be=/^([a-z]*)$/i;function Pe(t){return"string"==typeof t?t:Ge(t)}var Fe,Me,Oe=(Fe={},Me=0,function(t){var e;if(Fe.hasOwnProperty(t))e=Fe[t];else{if(1024<=Me){var i=0;for(var r in Fe)0==(3&i++)&&(delete Fe[r],--Me)}e=function(t){var e,i,r,n,o;if(be.exec(t)&&(t=function(t){var e=document.createElement("div");if(e.style.color=t,""!==e.style.color){document.body.appendChild(e);var i=getComputedStyle(e).color;return document.body.removeChild(e),i}return""}(t)),Le.exec(t)){var s,a=t.length-1;s=a<=4?1:2;var h=4===a||8===a;e=parseInt(t.substr(1+0*s,s),16),i=parseInt(t.substr(1+1*s,s),16),r=parseInt(t.substr(1+2*s,s),16),n=h?parseInt(t.substr(1+3*s,s),16):255,1==s&&(e=(e<<4)+e,i=(i<<4)+i,r=(r<<4)+r,h&&(n=(n<<4)+n)),o=[e,i,r,n/255]}else 0==t.indexOf("rgba(")?Ae(o=t.slice(5,-1).split(",").map(Number)):0==t.indexOf("rgb(")?((o=t.slice(4,-1).split(",").map(Number)).push(1),Ae(o)):Z(!1,14);return o}(t),Fe[t]=e,++Me}return e});function Ne(t){return Array.isArray(t)?t:Oe(t)}function Ae(t){return t[0]=gt(t[0]+.5|0,0,255),t[1]=gt(t[1]+.5|0,0,255),t[2]=gt(t[2]+.5|0,0,255),t[3]=gt(t[3],0,1),t}function Ge(t){var e=t[0];e!=(0|e)&&(e=e+.5|0);var i=t[1];i!=(0|i)&&(i=i+.5|0);var r=t[2];return r!=(0|r)&&(r=r+.5|0),"rgba("+e+","+i+","+r+","+(void 0===t[3]?1:t[3])+")"}function ke(t){return"string"==typeof(e=t)||e instanceof CanvasPattern||e instanceof CanvasGradient?t:Ge(t);var e}function De(t,e){var i=document.createElement("CANVAS");return t&&(i.width=t),e&&(i.height=e),i.getContext("2d")}function je(t,e){var i=e.parentNode;i&&i.replaceChild(t,e)}function Ue(t){return t&&t.parentNode?t.parentNode.removeChild(t):null}function Ye(t){for(;t.lastChild;)t.removeChild(t.lastChild)}var Be,Xe,ze=34962,Ve=5126,We=10242,Ke=10243,He=3553,Ze=33071,qe=36160,Je=["experimental-webgl","webgl","webkit-3d","moz-webgl"];function Qe(t,e){for(var i=Je.length,r=0;r<i;++r)try{var n=t.getContext(Je[r],e);if(n)return n}catch(t){}return null}if("undefined"!=typeof window&&"WebGLRenderingContext"in window)try{var $e=Qe(document.createElement("CANVAS"),{failIfMajorPerformanceCaveat:!0});$e&&(Be=$e.getParameter($e.MAX_TEXTURE_SIZE),Xe=$e.getSupportedExtensions())}catch(t){}var ti,ei,ii="undefined"!=typeof navigator?navigator.userAgent.toLowerCase():"",ri=-1!==ii.indexOf("firefox"),ni=-1!==ii.indexOf("safari")&&-1==ii.indexOf("chrom"),oi=-1!==ii.indexOf("webkit")&&-1==ii.indexOf("edge"),si=-1!==ii.indexOf("macintosh"),ai=window.devicePixelRatio||1,hi=function(){var t=!1;try{t=!!document.createElement("CANVAS").getContext("2d").setLineDash}catch(t){}return t}(),li="geolocation"in navigator,ui="ontouchstart"in window,ci="PointerEvent"in window,pi=!!navigator.msPointerEnabled,di={IDLE:0,LOADING:1,LOADED:2,ERROR:3},fi="ol-hidden",_i="ol-unselectable",gi="ol-control",yi="ol-collapsed",vi=(ei={},function(t){if(ti||(ti=document.createElement("div").style),!(t in ei)){ti.font=t;var e=ti.fontFamily;if(ti.font="",!e)return null;ei[t]=e.split(/,\s?/)}return ei[t]}),mi=function(e){function t(t){e.call(this),this.highWaterMark=void 0!==t?t:2048,this.count_=0,this.entries_={},this.oldest_=null,this.newest_=null}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.canExpireCache=function(){return this.getCount()>this.highWaterMark},t.prototype.clear=function(){this.count_=0,this.entries_={},this.oldest_=null,this.newest_=null,this.dispatchEvent(w.CLEAR)},t.prototype.containsKey=function(t){return this.entries_.hasOwnProperty(t)},t.prototype.forEach=function(t,e){for(var i=this.oldest_;i;)t.call(e,i.value_,i.key_,this),i=i.newer},t.prototype.get=function(t){var e=this.entries_[t];return Z(void 0!==e,15),e===this.newest_?e.value_:(e===this.oldest_?(this.oldest_=this.oldest_.newer,this.oldest_.older=null):(e.newer.older=e.older,e.older.newer=e.newer),e.newer=null,e.older=this.newest_,this.newest_.newer=e,(this.newest_=e).value_)},t.prototype.remove=function(t){var e=this.entries_[t];return Z(void 0!==e,15),e===this.newest_?(this.newest_=e.older,this.newest_&&(this.newest_.newer=null)):e===this.oldest_?(this.oldest_=e.newer,this.oldest_&&(this.oldest_.older=null)):(e.newer.older=e.older,e.older.newer=e.newer),delete this.entries_[t],--this.count_,e.value_},t.prototype.getCount=function(){return this.count_},t.prototype.getKeys=function(){var t,e=new Array(this.count_),i=0;for(t=this.newest_;t;t=t.older)e[i++]=t.key_;return e},t.prototype.getValues=function(){var t,e=new Array(this.count_),i=0;for(t=this.newest_;t;t=t.older)e[i++]=t.value_;return e},t.prototype.peekLast=function(){return this.oldest_.value_},t.prototype.peekLastKey=function(){return this.oldest_.key_},t.prototype.peekFirstKey=function(){return this.newest_.key_},t.prototype.pop=function(){var t=this.oldest_;return delete this.entries_[t.key_],t.newer&&(t.newer.older=null),this.oldest_=t.newer,this.oldest_||(this.newest_=null),--this.count_,t.value_},t.prototype.replace=function(t,e){this.get(t),this.entries_[t].value_=e},t.prototype.set=function(t,e){Z(!(t in this.entries_),16);var i={key_:t,newer:null,older:this.newest_,value_:e};this.newest_?this.newest_.newer=i:this.oldest_=i,this.newest_=i,this.entries_[t]=i,++this.count_},t.prototype.setSize=function(t){this.highWaterMark=t},t.prototype.prune=function(){for(;this.canExpireCache();)this.pop()},t}(i),xi="10px sans-serif",Si=[0,0,0,1],Ci="round",Ei=[],Ti="round",wi=[0,0,0,1],Ri="center",Ii=[0,0,0,0],Li=new mi,bi={},Pi=null,Fi={},Mi=function(){var o,s,a=60,h=bi,l="32px ",u=["monospace","serif"],c=u.length,p="wmytzilWMYTZIL@#/&?$%10";function d(t){for(var e=Oi(),i=!0,r=0;r<c;++r){var n=u[r];if(e.font=l+n,s=e.measureText(p).width,t!=n){e.font=l+t+","+n;var o=e.measureText(p).width;i=i&&o!=s}}return i}function f(){var t=!0;for(var e in h)h[e]<a&&(d(e)?(h[e]=a,_(Fi),Pi=null,Li.clear()):(++h[e],t=!1));t&&(clearInterval(o),o=void 0)}return function(t){var e=vi(t);if(e)for(var i=0,r=e.length;i<r;++i){var n=e[i];n in h||(h[n]=a,d(n)||void(h[n]=0)===o&&(o=setInterval(f,32)))}}}();function Oi(){return Pi||(Pi=De(1,1)),Pi}var Ni,Ai,Gi=(Ai=Fi,function(t){var e=Ai[t];return null==e&&(Ni||((Ni=document.createElement("span")).textContent="M",Ni.style.margin=Ni.style.padding="0 !important",Ni.style.position="absolute !important",Ni.style.left="-99999px !important"),Ni.style.font=t,document.body.appendChild(Ni),e=Ai[t]=Ni.offsetHeight,document.body.removeChild(Ni)),e});function ki(t,e){var i=Oi();return t!=i.font&&(i.font=t),i.measureText(e).width}function Di(t,e,i,r){0!==e&&(t.translate(i,r),t.rotate(e),t.translate(-i,-r))}var ji=[1,0,0,1,0,0];function Ui(t,e,i,r,n,o,s,a,h,l,u){var c;1!=i&&(c=t.globalAlpha,t.globalAlpha=c*i),e&&t.setTransform.apply(t,e),t.drawImage(r,n,o,s,a,h,l,s*u,a*u),c&&(t.globalAlpha=c),e&&t.setTransform.apply(t,ji)}var Yi=function(t){this.opacity_=t.opacity,this.rotateWithView_=t.rotateWithView,this.rotation_=t.rotation,this.scale_=t.scale,this.snapToPixel_=t.snapToPixel};Yi.prototype.getOpacity=function(){return this.opacity_},Yi.prototype.getRotateWithView=function(){return this.rotateWithView_},Yi.prototype.getRotation=function(){return this.rotation_},Yi.prototype.getScale=function(){return this.scale_},Yi.prototype.getSnapToPixel=function(){return this.snapToPixel_},Yi.prototype.getAnchor=function(){},Yi.prototype.getImage=function(t){},Yi.prototype.getHitDetectionImage=function(t){},Yi.prototype.getImageState=function(){},Yi.prototype.getImageSize=function(){},Yi.prototype.getHitDetectionImageSize=function(){},Yi.prototype.getOrigin=function(){},Yi.prototype.getSize=function(){},Yi.prototype.setOpacity=function(t){this.opacity_=t},Yi.prototype.setRotateWithView=function(t){this.rotateWithView_=t},Yi.prototype.setRotation=function(t){this.rotation_=t},Yi.prototype.setScale=function(t){this.scale_=t},Yi.prototype.setSnapToPixel=function(t){this.snapToPixel_=t},Yi.prototype.listenImageChange=function(t,e){},Yi.prototype.load=function(){},Yi.prototype.unlistenImageChange=function(t,e){};var Bi=function(r){function e(t){var e=void 0===t.snapToPixel||t.snapToPixel,i=void 0!==t.rotateWithView&&t.rotateWithView;r.call(this,{opacity:1,rotateWithView:i,rotation:void 0!==t.rotation?t.rotation:0,scale:1,snapToPixel:e}),this.checksums_=null,this.canvas_=null,this.hitDetectionCanvas_=null,this.fill_=void 0!==t.fill?t.fill:null,this.origin_=[0,0],this.points_=t.points,this.radius_=void 0!==t.radius?t.radius:t.radius1,this.radius2_=t.radius2,this.angle_=void 0!==t.angle?t.angle:0,this.stroke_=void 0!==t.stroke?t.stroke:null,this.anchor_=null,this.size_=null,this.imageSize_=null,this.hitDetectionImageSize_=null,this.atlasManager_=t.atlasManager,this.render_(this.atlasManager_)}return r&&(e.__proto__=r),((e.prototype=Object.create(r&&r.prototype)).constructor=e).prototype.clone=function(){var t=new e({fill:this.getFill()?this.getFill().clone():void 0,points:this.getPoints(),radius:this.getRadius(),radius2:this.getRadius2(),angle:this.getAngle(),snapToPixel:this.getSnapToPixel(),stroke:this.getStroke()?this.getStroke().clone():void 0,rotation:this.getRotation(),rotateWithView:this.getRotateWithView(),atlasManager:this.atlasManager_});return t.setOpacity(this.getOpacity()),t.setScale(this.getScale()),t},e.prototype.getAnchor=function(){return this.anchor_},e.prototype.getAngle=function(){return this.angle_},e.prototype.getFill=function(){return this.fill_},e.prototype.getHitDetectionImage=function(t){return this.hitDetectionCanvas_},e.prototype.getImage=function(t){return this.canvas_},e.prototype.getImageSize=function(){return this.imageSize_},e.prototype.getHitDetectionImageSize=function(){return this.hitDetectionImageSize_},e.prototype.getImageState=function(){return di.LOADED},e.prototype.getOrigin=function(){return this.origin_},e.prototype.getPoints=function(){return this.points_},e.prototype.getRadius=function(){return this.radius_},e.prototype.getRadius2=function(){return this.radius2_},e.prototype.getSize=function(){return this.size_},e.prototype.getStroke=function(){return this.stroke_},e.prototype.listenImageChange=function(t,e){},e.prototype.load=function(){},e.prototype.unlistenImageChange=function(t,e){},e.prototype.render_=function(t){var e,i,r="",n="",o=0,s=null,a=0,h=0;this.stroke_&&(null===(i=this.stroke_.getColor())&&(i=wi),i=ke(i),void 0===(h=this.stroke_.getWidth())&&(h=1),s=this.stroke_.getLineDash(),a=this.stroke_.getLineDashOffset(),hi||(s=null,a=0),void 0===(n=this.stroke_.getLineJoin())&&(n=Ti),void 0===(r=this.stroke_.getLineCap())&&(r=Ci),void 0===(o=this.stroke_.getMiterLimit())&&(o=10));var l=2*(this.radius_+h)+1,u={strokeStyle:i,strokeWidth:h,size:l,lineCap:r,lineDash:s,lineDashOffset:a,lineJoin:n,miterLimit:o};if(void 0===t){var c=De(l,l);this.canvas_=c.canvas,e=l=this.canvas_.width,this.draw_(u,c,0,0),this.createHitDetectionCanvas_(u)}else{l=Math.round(l);var p,d=!this.fill_;d&&(p=this.drawHitDetectionCanvas_.bind(this,u));var f=this.getChecksum(),_=t.add(f,l,l,this.draw_.bind(this,u),p);this.canvas_=_.image,this.origin_=[_.offsetX,_.offsetY],e=_.image.width,d?(this.hitDetectionCanvas_=_.hitImage,this.hitDetectionImageSize_=[_.hitImage.width,_.hitImage.height]):(this.hitDetectionCanvas_=this.canvas_,this.hitDetectionImageSize_=[e,e])}this.anchor_=[l/2,l/2],this.size_=[l,l],this.imageSize_=[e,e]},e.prototype.draw_=function(t,e,i,r){var n,o,s;e.setTransform(1,0,0,1,0,0),e.translate(i,r),e.beginPath();var a=this.points_;if(a===1/0)e.arc(t.size/2,t.size/2,this.radius_,0,2*Math.PI,!0);else{var h=void 0!==this.radius2_?this.radius2_:this.radius_;for(h!==this.radius_&&(a*=2),n=0;n<=a;n++)o=2*n*Math.PI/a-Math.PI/2+this.angle_,s=n%2==0?this.radius_:h,e.lineTo(t.size/2+s*Math.cos(o),t.size/2+s*Math.sin(o))}if(this.fill_){var l=this.fill_.getColor();null===l&&(l=Si),e.fillStyle=ke(l),e.fill()}this.stroke_&&(e.strokeStyle=t.strokeStyle,e.lineWidth=t.strokeWidth,t.lineDash&&(e.setLineDash(t.lineDash),e.lineDashOffset=t.lineDashOffset),e.lineCap=t.lineCap,e.lineJoin=t.lineJoin,e.miterLimit=t.miterLimit,e.stroke()),e.closePath()},e.prototype.createHitDetectionCanvas_=function(t){if(this.hitDetectionImageSize_=[t.size,t.size],this.fill_)this.hitDetectionCanvas_=this.canvas_;else{var e=De(t.size,t.size);this.hitDetectionCanvas_=e.canvas,this.drawHitDetectionCanvas_(t,e,0,0)}},e.prototype.drawHitDetectionCanvas_=function(t,e,i,r){e.setTransform(1,0,0,1,0,0),e.translate(i,r),e.beginPath();var n=this.points_;if(n===1/0)e.arc(t.size/2,t.size/2,this.radius_,0,2*Math.PI,!0);else{var o,s,a,h=void 0!==this.radius2_?this.radius2_:this.radius_;for(h!==this.radius_&&(n*=2),o=0;o<=n;o++)a=2*o*Math.PI/n-Math.PI/2+this.angle_,s=o%2==0?this.radius_:h,e.lineTo(t.size/2+s*Math.cos(a),t.size/2+s*Math.sin(a))}e.fillStyle=Si,e.fill(),this.stroke_&&(e.strokeStyle=t.strokeStyle,e.lineWidth=t.strokeWidth,t.lineDash&&(e.setLineDash(t.lineDash),e.lineDashOffset=t.lineDashOffset),e.stroke()),e.closePath()},e.prototype.getChecksum=function(){var t=this.stroke_?this.stroke_.getChecksum():"-",e=this.fill_?this.fill_.getChecksum():"-";if(!this.checksums_||t!=this.checksums_[1]||e!=this.checksums_[2]||this.radius_!=this.checksums_[3]||this.radius2_!=this.checksums_[4]||this.angle_!=this.checksums_[5]||this.points_!=this.checksums_[6]){var i="r"+t+e+(void 0!==this.radius_?this.radius_.toString():"-")+(void 0!==this.radius2_?this.radius2_.toString():"-")+(void 0!==this.angle_?this.angle_.toString():"-")+(void 0!==this.points_?this.points_.toString():"-");this.checksums_=[i,t,e,this.radius_,this.radius2_,this.angle_,this.points_]}return this.checksums_[0]},e}(Yi),Xi=function(i){function e(t){var e=t||{};i.call(this,{points:1/0,fill:e.fill,radius:e.radius,snapToPixel:e.snapToPixel,stroke:e.stroke,atlasManager:e.atlasManager})}return i&&(e.__proto__=i),((e.prototype=Object.create(i&&i.prototype)).constructor=e).prototype.clone=function(){var t=new e({fill:this.getFill()?this.getFill().clone():void 0,stroke:this.getStroke()?this.getStroke().clone():void 0,radius:this.getRadius(),snapToPixel:this.getSnapToPixel(),atlasManager:this.atlasManager_});return t.setOpacity(this.getOpacity()),t.setScale(this.getScale()),t},e.prototype.setRadius=function(t){this.radius_=t,this.render_(this.atlasManager_)},e}(Bi),zi=function(t){var e=t||{};this.color_=void 0!==e.color?e.color:null,this.checksum_=void 0};zi.prototype.clone=function(){var t=this.getColor();return new zi({color:t&&t.slice?t.slice():t||void 0})},zi.prototype.getColor=function(){return this.color_},zi.prototype.setColor=function(t){this.color_=t,this.checksum_=void 0},zi.prototype.getChecksum=function(){return void 0===this.checksum_&&(this.color_ instanceof CanvasPattern||this.color_ instanceof CanvasGradient?this.checksum_=Et(this.color_).toString():this.checksum_="f"+(this.color_?Pe(this.color_):"-")),this.checksum_};var Vi=function(t){var e=t||{};this.color_=void 0!==e.color?e.color:null,this.lineCap_=e.lineCap,this.lineDash_=void 0!==e.lineDash?e.lineDash:null,this.lineDashOffset_=e.lineDashOffset,this.lineJoin_=e.lineJoin,this.miterLimit_=e.miterLimit,this.width_=e.width,this.checksum_=void 0};Vi.prototype.clone=function(){var t=this.getColor();return new Vi({color:t&&t.slice?t.slice():t||void 0,lineCap:this.getLineCap(),lineDash:this.getLineDash()?this.getLineDash().slice():void 0,lineDashOffset:this.getLineDashOffset(),lineJoin:this.getLineJoin(),miterLimit:this.getMiterLimit(),width:this.getWidth()})},Vi.prototype.getColor=function(){return this.color_},Vi.prototype.getLineCap=function(){return this.lineCap_},Vi.prototype.getLineDash=function(){return this.lineDash_},Vi.prototype.getLineDashOffset=function(){return this.lineDashOffset_},Vi.prototype.getLineJoin=function(){return this.lineJoin_},Vi.prototype.getMiterLimit=function(){return this.miterLimit_},Vi.prototype.getWidth=function(){return this.width_},Vi.prototype.setColor=function(t){this.color_=t,this.checksum_=void 0},Vi.prototype.setLineCap=function(t){this.lineCap_=t,this.checksum_=void 0},Vi.prototype.setLineDash=function(t){this.lineDash_=t,this.checksum_=void 0},Vi.prototype.setLineDashOffset=function(t){this.lineDashOffset_=t,this.checksum_=void 0},Vi.prototype.setLineJoin=function(t){this.lineJoin_=t,this.checksum_=void 0},Vi.prototype.setMiterLimit=function(t){this.miterLimit_=t,this.checksum_=void 0},Vi.prototype.setWidth=function(t){this.width_=t,this.checksum_=void 0},Vi.prototype.getChecksum=function(){return void 0===this.checksum_&&(this.checksum_="s",this.color_?"string"==typeof this.color_?this.checksum_+=this.color_:this.checksum_+=Et(this.color_).toString():this.checksum_+="-",this.checksum_+=","+(void 0!==this.lineCap_?this.lineCap_.toString():"-")+","+(this.lineDash_?this.lineDash_.toString():"-")+","+(void 0!==this.lineDashOffset_?this.lineDashOffset_:"-")+","+(void 0!==this.lineJoin_?this.lineJoin_:"-")+","+(void 0!==this.miterLimit_?this.miterLimit_.toString():"-")+","+(void 0!==this.width_?this.width_.toString():"-")),this.checksum_};var Wi=function(t){var e=t||{};this.geometry_=null,this.geometryFunction_=qi,void 0!==e.geometry&&this.setGeometry(e.geometry),this.fill_=void 0!==e.fill?e.fill:null,this.image_=void 0!==e.image?e.image:null,this.renderer_=void 0!==e.renderer?e.renderer:null,this.stroke_=void 0!==e.stroke?e.stroke:null,this.text_=void 0!==e.text?e.text:null,this.zIndex_=e.zIndex};Wi.prototype.clone=function(){var t=this.getGeometry();return t&&t.clone&&(t=t.clone()),new Wi({geometry:t,fill:this.getFill()?this.getFill().clone():void 0,image:this.getImage()?this.getImage().clone():void 0,stroke:this.getStroke()?this.getStroke().clone():void 0,text:this.getText()?this.getText().clone():void 0,zIndex:this.getZIndex()})},Wi.prototype.getRenderer=function(){return this.renderer_},Wi.prototype.setRenderer=function(t){this.renderer_=t},Wi.prototype.getGeometry=function(){return this.geometry_},Wi.prototype.getGeometryFunction=function(){return this.geometryFunction_},Wi.prototype.getFill=function(){return this.fill_},Wi.prototype.setFill=function(t){this.fill_=t},Wi.prototype.getImage=function(){return this.image_},Wi.prototype.setImage=function(t){this.image_=t},Wi.prototype.getStroke=function(){return this.stroke_},Wi.prototype.setStroke=function(t){this.stroke_=t},Wi.prototype.getText=function(){return this.text_},Wi.prototype.setText=function(t){this.text_=t},Wi.prototype.getZIndex=function(){return this.zIndex_},Wi.prototype.setGeometry=function(e){"function"==typeof e?this.geometryFunction_=e:"string"==typeof e?this.geometryFunction_=function(t){return t.get(e)}:e?void 0!==e&&(this.geometryFunction_=function(){return e}):this.geometryFunction_=qi,this.geometry_=e},Wi.prototype.setZIndex=function(t){this.zIndex_=t};var Ki=null;function Hi(t,e){if(!Ki){var i=new zi({color:"rgba(255,255,255,0.4)"}),r=new Vi({color:"#3399CC",width:1.25});Ki=[new Wi({image:new Xi({fill:i,stroke:r,radius:5}),fill:i,stroke:r})]}return Ki}function Zi(){var t={},e=[255,255,255,1],i=[0,153,255,1];return t[Lt.POLYGON]=[new Wi({fill:new zi({color:[255,255,255,.5]})})],t[Lt.MULTI_POLYGON]=t[Lt.POLYGON],t[Lt.LINE_STRING]=[new Wi({stroke:new Vi({color:e,width:5})}),new Wi({stroke:new Vi({color:i,width:3})})],t[Lt.MULTI_LINE_STRING]=t[Lt.LINE_STRING],t[Lt.CIRCLE]=t[Lt.POLYGON].concat(t[Lt.LINE_STRING]),t[Lt.POINT]=[new Wi({image:new Xi({radius:6,fill:new zi({color:i}),stroke:new Vi({color:e,width:1.5})}),zIndex:1/0})],t[Lt.MULTI_POINT]=t[Lt.POINT],t[Lt.GEOMETRY_COLLECTION]=t[Lt.POLYGON].concat(t[Lt.LINE_STRING],t[Lt.POINT]),t}function qi(t){return t.getGeometry()}var Ji=function(r){function n(t){if(r.call(this),this.id_=void 0,this.geometryName_="geometry",this.style_=null,this.styleFunction_=void 0,this.geometryChangeKey_=null,E(this,b(this.geometryName_),this.handleGeometryChanged_,this),void 0!==t)if(t instanceof Ie||!t){var e=t;this.setGeometry(e)}else{var i=t;this.setProperties(i)}}return r&&(n.__proto__=r),((n.prototype=Object.create(r&&r.prototype)).constructor=n).prototype.clone=function(){var t=new n(this.getProperties());t.setGeometryName(this.getGeometryName());var e=this.getGeometry();e&&t.setGeometry(e.clone());var i=this.getStyle();return i&&t.setStyle(i),t},n.prototype.getGeometry=function(){return this.get(this.geometryName_)},n.prototype.getId=function(){return this.id_},n.prototype.getGeometryName=function(){return this.geometryName_},n.prototype.getStyle=function(){return this.style_},n.prototype.getStyleFunction=function(){return this.styleFunction_},n.prototype.handleGeometryChange_=function(){this.changed()},n.prototype.handleGeometryChanged_=function(){this.geometryChangeKey_&&(g(this.geometryChangeKey_),this.geometryChangeKey_=null);var t=this.getGeometry();t&&(this.geometryChangeKey_=E(t,w.CHANGE,this.handleGeometryChange_,this)),this.changed()},n.prototype.setGeometry=function(t){this.set(this.geometryName_,t)},n.prototype.setStyle=function(t){this.style_=t,this.styleFunction_=t?function(t){{return"function"==typeof t?t:(Array.isArray(t)?e=t:(Z(t instanceof Wi,41),e=[t]),function(){return e});var e}}(t):void 0,this.changed()},n.prototype.setId=function(t){this.id_=t,this.changed()},n.prototype.setGeometryName=function(t){d(this,b(this.geometryName_),this.handleGeometryChanged_,this),this.geometryName_=t,E(this,b(this.geometryName_),this.handleGeometryChanged_,this),this.handleGeometryChanged_()},n}(R);var Qi="accuracy",$i="accuracyGeometry",tr="altitude",er="altitudeAccuracy",ir="heading",rr="position",nr="projection",or="speed",sr="tracking",ar="trackingOptions";function hr(t,e){return e<t?1:t<e?-1:0}function lr(t,e){return 0<=t.indexOf(e)}function ur(t,e,i){var r,n=t.length;if(t[0]<=e)return 0;if(e<=t[n-1])return n-1;if(0<i){for(r=1;r<n;++r)if(t[r]<e)return r-1}else if(i<0){for(r=1;r<n;++r)if(t[r]<=e)return r}else for(r=1;r<n;++r){if(t[r]==e)return r;if(t[r]<e)return t[r-1]-e<e-t[r]?r-1:r}return n-1}function cr(t,e,i){for(;e<i;){var r=t[e];t[e]=t[i],t[i]=r,++e,--i}}function pr(t,e){for(var i=Array.isArray(e)?e:[e],r=i.length,n=0;n<r;n++)t[t.length]=i[n]}function dr(t,e){for(var i,r=t.length>>>0,n=0;n<r;n++)if(e(i=t[n],n,t))return i;return null}function fr(t,e){var i=t.length;if(i!==e.length)return!1;for(var r=0;r<i;r++)if(t[r]!==e[r])return!1;return!0}function _r(t,i){var e,r=t.length,n=Array(t.length);for(e=0;e<r;e++)n[e]={index:e,value:t[e]};for(n.sort(function(t,e){return i(t.value,e.value)||t.index-e.index}),e=0;e<t.length;e++)t[e]=n[e].value}function gr(i,r){var n;return!i.every(function(t,e){return!r(t,n=e,i)})?n:-1}var yr={XY:"XY",XYZ:"XYZ",XYM:"XYM",XYZM:"XYZM"},vr=function(t){function e(){t.call(this),this.layout=yr.XY,this.stride=2,this.flatCoordinates=null}return t&&(e.__proto__=t),((e.prototype=Object.create(t&&t.prototype)).constructor=e).prototype.computeExtent=function(t){return K(this.flatCoordinates,0,this.flatCoordinates.length,this.stride,t)},e.prototype.getCoordinates=function(){},e.prototype.getFirstCoordinate=function(){return this.flatCoordinates.slice(0,this.stride)},e.prototype.getFlatCoordinates=function(){return this.flatCoordinates},e.prototype.getLastCoordinate=function(){return this.flatCoordinates.slice(this.flatCoordinates.length-this.stride)},e.prototype.getLayout=function(){return this.layout},e.prototype.getSimplifiedGeometry=function(t){if(this.simplifiedGeometryRevision!=this.getRevision()&&(_(this.simplifiedGeometryCache),this.simplifiedGeometryMaxMinSquaredTolerance=0,this.simplifiedGeometryRevision=this.getRevision()),t<0||0!==this.simplifiedGeometryMaxMinSquaredTolerance&&t<=this.simplifiedGeometryMaxMinSquaredTolerance)return this;var e=t.toString();if(this.simplifiedGeometryCache.hasOwnProperty(e))return this.simplifiedGeometryCache[e];var i=this.getSimplifiedGeometryInternal(t);return i.getFlatCoordinates().length<this.flatCoordinates.length?this.simplifiedGeometryCache[e]=i:(this.simplifiedGeometryMaxMinSquaredTolerance=t,this)},e.prototype.getSimplifiedGeometryInternal=function(t){return this},e.prototype.getStride=function(){return this.stride},e.prototype.setFlatCoordinates=function(t,e){this.stride=mr(t),this.layout=t,this.flatCoordinates=e},e.prototype.setCoordinates=function(t,e){},e.prototype.setLayout=function(t,e,i){var r;if(t)r=mr(t);else{for(var n=0;n<i;++n){if(0===e.length)return this.layout=yr.XY,void(this.stride=2);e=e[0]}t=function(t){var e;2==t?e=yr.XY:3==t?e=yr.XYZ:4==t&&(e=yr.XYZM);return e}(r=e.length)}this.layout=t,this.stride=r},e.prototype.applyTransform=function(t){this.flatCoordinates&&(t(this.flatCoordinates,this.flatCoordinates,this.stride),this.changed())},e.prototype.rotate=function(t,e){var i=this.getFlatCoordinates();if(i){var r=this.getStride();!function(t,e,i,r,n,o,s){for(var a=s||[],h=Math.cos(n),l=Math.sin(n),u=o[0],c=o[1],p=0,d=e;d<i;d+=r){var f=t[d]-u,_=t[d+1]-c;a[p++]=u+f*h-_*l,a[p++]=c+f*l+_*h;for(var g=d+2;g<d+r;++g)a[p++]=t[g]}s&&a.length!=p&&(a.length=p)}(i,0,i.length,r,t,e,i),this.changed()}},e.prototype.scale=function(t,e,i){var r=e;void 0===r&&(r=t);var n=i;n||(n=ot(this.getExtent()));var o=this.getFlatCoordinates();if(o){var s=this.getStride();!function(t,e,i,r,n,o,s,a){for(var h=a||[],l=s[0],u=s[1],c=0,p=e;p<i;p+=r){var d=t[p]-l,f=t[p+1]-u;h[c++]=l+n*d,h[c++]=u+o*f;for(var _=p+2;_<p+r;++_)h[c++]=t[_]}a&&h.length!=c&&(h.length=c)}(o,0,o.length,s,t,r,n,o),this.changed()}},e.prototype.translate=function(t,e){var i=this.getFlatCoordinates();if(i){var r=this.getStride();_t(i,0,i.length,r,t,e,i),this.changed()}},e}(Ie);function mr(t){var e;return t==yr.XY?e=2:t==yr.XYZ||t==yr.XYM?e=3:t==yr.XYZM&&(e=4),e}function xr(t,e,i,r){for(var n=0,o=t[i-r],s=t[i-r+1];e<i;e+=r){var a=t[e],h=t[e+1];n+=s*a-o*h,o=a,s=h}return n/2}function Sr(t,e,i,r){for(var n=0,o=0,s=i.length;o<s;++o){var a=i[o];n+=xr(t,e,a,r),e=a}return n}function Cr(t,e,i,r,n,o,s){var a,h=t[e],l=t[e+1],u=t[i]-h,c=t[i+1]-l;if(0===u&&0===c)a=e;else{var p=((n-h)*u+(o-l)*c)/(u*u+c*c);if(1<p)a=i;else{if(0<p){for(var d=0;d<r;++d)s[d]=It(t[e+d],t[i+d],p);return void(s.length=r)}a=e}}for(var f=0;f<r;++f)s[f]=t[a+f];s.length=r}function Er(t,e,i,r,n){var o=t[e],s=t[e+1];for(e+=r;e<i;e+=r){var a=t[e],h=t[e+1],l=mt(o,s,a,h);n<l&&(n=l),o=a,s=h}return n}function Tr(t,e,i,r,n){for(var o=0,s=i.length;o<s;++o){var a=i[o];n=Er(t,e,a,r,n),e=a}return n}function wr(t,e,i,r,n,o,s,a,h,l,u){if(e==i)return l;var c,p;if(0===n){if((p=mt(s,a,t[e],t[e+1]))<l){for(c=0;c<r;++c)h[c]=t[e+c];return h.length=r,p}return l}for(var d=u||[NaN,NaN],f=e+r;f<i;)if(Cr(t,f-r,f,r,s,a,d),(p=mt(s,a,d[0],d[1]))<l){for(l=p,c=0;c<r;++c)h[c]=d[c];f+=h.length=r}else f+=r*Math.max((Math.sqrt(p)-Math.sqrt(l))/n|0,1);if(o&&(Cr(t,i-r,e,r,s,a,d),(p=mt(s,a,d[0],d[1]))<l)){for(l=p,c=0;c<r;++c)h[c]=d[c];h.length=r}return l}function Rr(t,e,i,r,n,o,s,a,h,l,u){for(var c=u||[NaN,NaN],p=0,d=i.length;p<d;++p){var f=i[p];l=wr(t,e,f,r,n,o,s,a,h,l,c),e=f}return l}function Ir(t,e,i,r){for(var n=0,o=i.length;n<o;++n)t[e++]=i[n];return e}function Lr(t,e,i,r){for(var n=0,o=i.length;n<o;++n)for(var s=i[n],a=0;a<r;++a)t[e++]=s[a];return e}function br(t,e,i,r,n){for(var o=n||[],s=0,a=0,h=i.length;a<h;++a){var l=Lr(t,e,i[a],r);e=o[s++]=l}return o.length=s,o}function Pr(t,e,i,r,n){for(var o=void 0!==n?n:[],s=0,a=e;a<i;a+=r)o[s++]=t.slice(a,a+r);return o.length=s,o}function Fr(t,e,i,r,n){for(var o=void 0!==n?n:[],s=0,a=0,h=i.length;a<h;++a){var l=i[a];o[s++]=Pr(t,e,l,r,o[s]),e=l}return o.length=s,o}function Mr(t,e,i,r,n){for(var o=void 0!==n?n:[],s=0,a=0,h=i.length;a<h;++a){var l=i[a];o[s++]=Fr(t,e,l,r,o[s]),e=l[l.length-1]}return o.length=s,o}function Or(t,e,i,r,n,o,s){var a=(i-e)/r;if(a<3){for(;e<i;e+=r)o[s++]=t[e],o[s++]=t[e+1];return s}var h=new Array(a);h[0]=1,h[a-1]=1;for(var l=[e,i-r],u=0;0<l.length;){for(var c=l.pop(),p=l.pop(),d=0,f=t[p],_=t[p+1],g=t[c],y=t[c+1],v=p+r;v<c;v+=r){var m=vt(t[v],t[v+1],f,_,g,y);d<m&&(u=v,d=m)}n<d&&(h[(u-e)/r]=1,p+r<u&&l.push(p,u),u+r<c&&l.push(u,c))}for(var x=0;x<a;++x)h[x]&&(o[s++]=t[e+x*r],o[s++]=t[e+x*r+1]);return s}function Nr(t,e){return e*Math.round(t/e)}function Ar(t,e,i,r,n,o,s){if(e==i)return s;var a,h,l=Nr(t[e],n),u=Nr(t[e+1],n);e+=r,o[s++]=l,o[s++]=u;do{if(a=Nr(t[e],n),h=Nr(t[e+1],n),(e+=r)==i)return o[s++]=a,o[s++]=h,s}while(a==l&&h==u);for(;e<i;){var c=Nr(t[e],n),p=Nr(t[e+1],n);if(e+=r,c!=a||p!=h){var d=a-l,f=h-u,_=c-l,g=p-u;d*g==f*_&&(d<0&&_<d||d==_||0<d&&d<_)&&(f<0&&g<f||f==g||0<f&&f<g)||(l=o[s++]=a,u=o[s++]=h),a=c,h=p}}return o[s++]=a,o[s++]=h,s}function Gr(t,e,i,r,n,o,s,a){for(var h=0,l=i.length;h<l;++h){var u=i[h];s=Ar(t,e,u,r,n,o,s),a.push(s),e=u}return s}vr.prototype.containsXY=v;var kr=function(i){function r(t,e){i.call(this),this.maxDelta_=-1,this.maxDeltaRevision_=-1,void 0===e||Array.isArray(t[0])?this.setCoordinates(t,e):this.setFlatCoordinates(e,t)}return i&&(r.__proto__=i),((r.prototype=Object.create(i&&i.prototype)).constructor=r).prototype.clone=function(){return new r(this.flatCoordinates.slice(),this.layout)},r.prototype.closestPointXY=function(t,e,i,r){return r<D(this.getExtent(),t,e)?r:(this.maxDeltaRevision_!=this.getRevision()&&(this.maxDelta_=Math.sqrt(Er(this.flatCoordinates,0,this.flatCoordinates.length,this.stride,0)),this.maxDeltaRevision_=this.getRevision()),wr(this.flatCoordinates,0,this.flatCoordinates.length,this.stride,this.maxDelta_,!0,t,e,i,r))},r.prototype.getArea=function(){return xr(this.flatCoordinates,0,this.flatCoordinates.length,this.stride)},r.prototype.getCoordinates=function(){return Pr(this.flatCoordinates,0,this.flatCoordinates.length,this.stride)},r.prototype.getSimplifiedGeometryInternal=function(t){var e=[];return e.length=Or(this.flatCoordinates,0,this.flatCoordinates.length,this.stride,t,e,0),new r(e,yr.XY)},r.prototype.getType=function(){return Lt.LINEAR_RING},r.prototype.intersectsExtent=function(t){},r.prototype.setCoordinates=function(t,e){this.setLayout(e,t,1),this.flatCoordinates||(this.flatCoordinates=[]),this.flatCoordinates.length=Lr(this.flatCoordinates,0,t,this.stride),this.changed()},r}(vr),Dr=function(i){function t(t,e){i.call(this),this.setCoordinates(t,e)}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.clone=function(){return new t(this.flatCoordinates.slice(),this.layout)},t.prototype.closestPointXY=function(t,e,i,r){var n=this.flatCoordinates,o=mt(t,e,n[0],n[1]);if(o<r){for(var s=this.stride,a=0;a<s;++a)i[a]=n[a];return i.length=s,o}return r},t.prototype.getCoordinates=function(){return this.flatCoordinates?this.flatCoordinates.slice():[]},t.prototype.computeExtent=function(t){return V(this.flatCoordinates,t)},t.prototype.getType=function(){return Lt.POINT},t.prototype.intersectsExtent=function(t){return U(t,this.flatCoordinates[0],this.flatCoordinates[1])},t.prototype.setCoordinates=function(t,e){this.setLayout(e,t,0),this.flatCoordinates||(this.flatCoordinates=[]),this.flatCoordinates.length=Ir(this.flatCoordinates,0,t,this.stride),this.changed()},t}(vr);function jr(e,i,r,n,t){return!et(t,function(t){return!Ur(e,i,r,n,t[0],t[1])})}function Ur(t,e,i,r,n,o){for(var s=0,a=t[i-r],h=t[i-r+1];e<i;e+=r){var l=t[e],u=t[e+1];h<=o?o<u&&0<(l-a)*(o-h)-(n-a)*(u-h)&&s++:u<=o&&(l-a)*(o-h)-(n-a)*(u-h)<0&&s--,a=l,h=u}return 0!==s}function Yr(t,e,i,r,n,o){if(0===i.length)return!1;if(!Ur(t,e,i[0],r,n,o))return!1;for(var s=1,a=i.length;s<a;++s)if(Ur(t,i[s-1],i[s],r,n,o))return!1;return!0}function Br(t,e,i,r,n,o,s){for(var a,h,l,u,c,p,d,f=n[o+1],_=[],g=0,y=i.length;g<y;++g){var v=i[g];for(u=t[v-r],p=t[v-r+1],a=e;a<v;a+=r)c=t[a],d=t[a+1],(f<=p&&d<=f||p<=f&&f<=d)&&(l=(f-p)/(d-p)*(c-u)+u,_.push(l)),u=c,p=d}var m=NaN,x=-1/0;for(_.sort(hr),u=_[0],a=1,h=_.length;a<h;++a){c=_[a];var S=Math.abs(c-u);x<S&&Yr(t,e,i,r,l=(u+c)/2,f)&&(m=l,x=S),u=c}return isNaN(m)&&(m=n[o]),s?(s.push(m,f,x),s):[m,f,x]}function Xr(t,e,i,r,n){for(var o=[],s=0,a=i.length;s<a;++s){var h=i[s];o=Br(t,e,h,r,n,2*s,o),e=h[h.length-1]}return o}function zr(t,e,i,r,n,o){for(var s,a=[t[e],t[e+1]],h=[];e+r<i;e+=r){if(h[0]=t[e+r],h[1]=t[e+r+1],s=n.call(o,a,h))return s;a[0]=h[0],a[1]=h[1]}return!1}function Vr(t,e,i,r,n){var o=J([1/0,1/0,-1/0,-1/0],t,e,i,r);return!!wt(n,o)&&(!!Q(n,o)||(o[0]>=n[0]&&o[2]<=n[2]||(o[1]>=n[1]&&o[3]<=n[3]||zr(t,e,i,r,function(t,e){return function(t,e,i){var r=!1,n=Y(t,e),o=Y(t,i);if(n===N.INTERSECTING||o===N.INTERSECTING)r=!0;else{var s,a,h=t[0],l=t[1],u=t[2],c=t[3],p=e[0],d=e[1],f=i[0],_=i[1],g=(_-d)/(f-p);o&N.ABOVE&&!(n&N.ABOVE)&&(r=h<=(s=f-(_-c)/g)&&s<=u),r||!(o&N.RIGHT)||n&N.RIGHT||(r=l<=(a=_-(f-u)*g)&&a<=c),r||!(o&N.BELOW)||n&N.BELOW||(r=h<=(s=f-(_-l)/g)&&s<=u),r||!(o&N.LEFT)||n&N.LEFT||(r=l<=(a=_-(f-h)*g)&&a<=c)}return r}(n,t,e)}))))}function Wr(t,e,i,r,n){if(o=t,s=e,a=i[0],!(Vr(o,s,a,h=r,l=n)||Ur(o,s,a,h,l[0],l[1])||Ur(o,s,a,h,l[0],l[3])||Ur(o,s,a,h,l[2],l[1])||Ur(o,s,a,h,l[2],l[3])))return!1;var o,s,a,h,l;if(1===i.length)return!0;for(var u=1,c=i.length;u<c;++u)if(jr(t,i[u-1],i[u],r,n))return!1;return!0}function Kr(t,e,i,r){for(;e<i-r;){for(var n=0;n<r;++n){var o=t[e+n];t[e+n]=t[i-r+n],t[i-r+n]=o}e+=r,i-=r}}function Hr(t,e,i,r){for(var n=0,o=t[i-r],s=t[i-r+1];e<i;e+=r){var a=t[e],h=t[e+1];n+=(a-o)*(h+s),o=a,s=h}return 0<n}function Zr(t,e,i,r,n){for(var o=void 0!==n&&n,s=0,a=i.length;s<a;++s){var h=i[s],l=Hr(t,e,h,r);if(0===s){if(o&&l||!o&&!l)return!1}else if(o&&!l||!o&&l)return!1;e=h}return!0}function qr(t,e,i,r,n){for(var o=void 0!==n&&n,s=0,a=i.length;s<a;++s){var h=i[s],l=Hr(t,e,h,r);(0===s?o&&l||!o&&!l:o&&!l||!o&&l)&&Kr(t,e,h,r),e=h}return e}function Jr(t,e,i,r,n){for(var o=0,s=i.length;o<s;++o)e=qr(t,e,i[o],r,n);return e}var Qr=function(r){function n(t,e,i){r.call(this),this.ends_=[],this.flatInteriorPointRevision_=-1,this.flatInteriorPoint_=null,this.maxDelta_=-1,this.maxDeltaRevision_=-1,this.orientedRevision_=-1,this.orientedFlatCoordinates_=null,void 0!==e&&i?(this.setFlatCoordinates(e,t),this.ends_=i):this.setCoordinates(t,e)}return r&&(n.__proto__=r),((n.prototype=Object.create(r&&r.prototype)).constructor=n).prototype.appendLinearRing=function(t){this.flatCoordinates?pr(this.flatCoordinates,t.getFlatCoordinates()):this.flatCoordinates=t.getFlatCoordinates().slice(),this.ends_.push(this.flatCoordinates.length),this.changed()},n.prototype.clone=function(){return new n(this.flatCoordinates.slice(),this.layout,this.ends_.slice())},n.prototype.closestPointXY=function(t,e,i,r){return r<D(this.getExtent(),t,e)?r:(this.maxDeltaRevision_!=this.getRevision()&&(this.maxDelta_=Math.sqrt(Tr(this.flatCoordinates,0,this.ends_,this.stride,0)),this.maxDeltaRevision_=this.getRevision()),Rr(this.flatCoordinates,0,this.ends_,this.stride,this.maxDelta_,!0,t,e,i,r))},n.prototype.containsXY=function(t,e){return Yr(this.getOrientedFlatCoordinates(),0,this.ends_,this.stride,t,e)},n.prototype.getArea=function(){return Sr(this.getOrientedFlatCoordinates(),0,this.ends_,this.stride)},n.prototype.getCoordinates=function(t){var e;return void 0!==t?qr(e=this.getOrientedFlatCoordinates().slice(),0,this.ends_,this.stride,t):e=this.flatCoordinates,Fr(e,0,this.ends_,this.stride)},n.prototype.getEnds=function(){return this.ends_},n.prototype.getFlatInteriorPoint=function(){if(this.flatInteriorPointRevision_!=this.getRevision()){var t=ot(this.getExtent());this.flatInteriorPoint_=Br(this.getOrientedFlatCoordinates(),0,this.ends_,this.stride,t,0),this.flatInteriorPointRevision_=this.getRevision()}return this.flatInteriorPoint_},n.prototype.getInteriorPoint=function(){return new Dr(this.getFlatInteriorPoint(),yr.XYM)},n.prototype.getLinearRingCount=function(){return this.ends_.length},n.prototype.getLinearRing=function(t){return t<0||this.ends_.length<=t?null:new kr(this.flatCoordinates.slice(0===t?0:this.ends_[t-1],this.ends_[t]),this.layout)},n.prototype.getLinearRings=function(){for(var t=this.layout,e=this.flatCoordinates,i=this.ends_,r=[],n=0,o=0,s=i.length;o<s;++o){var a=i[o],h=new kr(e.slice(n,a),t);r.push(h),n=a}return r},n.prototype.getOrientedFlatCoordinates=function(){if(this.orientedRevision_!=this.getRevision()){var t=this.flatCoordinates;Zr(t,0,this.ends_,this.stride)?this.orientedFlatCoordinates_=t:(this.orientedFlatCoordinates_=t.slice(),this.orientedFlatCoordinates_.length=qr(this.orientedFlatCoordinates_,0,this.ends_,this.stride)),this.orientedRevision_=this.getRevision()}return this.orientedFlatCoordinates_},n.prototype.getSimplifiedGeometryInternal=function(t){var e=[],i=[];return e.length=Gr(this.flatCoordinates,0,this.ends_,this.stride,Math.sqrt(t),e,0,i),new n(e,yr.XY,i)},n.prototype.getType=function(){return Lt.POLYGON},n.prototype.intersectsExtent=function(t){return Wr(this.getOrientedFlatCoordinates(),0,this.ends_,this.stride,t)},n.prototype.setCoordinates=function(t,e){this.setLayout(e,t,2),this.flatCoordinates||(this.flatCoordinates=[]);var i=br(this.flatCoordinates,0,t,this.stride,this.ends_);this.flatCoordinates.length=0===i.length?0:i[i.length-1],this.changed()},n}(vr);function $r(t,e,i,r){for(var n,o,s,a,h,l,u,c,p=i||32,d=[],f=0;f<p;++f)pr(d,(n=t,o=e,s=2*Math.PI*f/p,void 0,a=r||bt,h=St(n[1]),l=St(n[0]),u=o/a,c=Math.asin(Math.sin(h)*Math.cos(u)+Math.cos(h)*Math.sin(u)*Math.cos(s)),[xt(l+Math.atan2(Math.sin(s)*Math.sin(u)*Math.cos(h),Math.cos(u)-Math.sin(h)*Math.sin(c))),xt(c)]));return d.push(d[0],d[1]),new Qr(d,yr.XY,[d.length])}function tn(t){var e=t[0],i=t[1],r=t[2],n=t[3],o=[e,i,e,n,r,n,r,i,e,i];return new Qr(o,yr.XY,[o.length])}function en(t,e,i){for(var r=e||32,n=t.getStride(),o=t.getLayout(),s=t.getCenter(),a=n*(r+1),h=new Array(a),l=0;l<a;l+=n){h[l]=0,h[l+1]=0;for(var u=2;u<n;u++)h[l+u]=s[u]}var c=[h.length],p=new Qr(h,o,c);return rn(p,s,t.getRadius(),i),p}function rn(t,e,i,r){for(var n=t.getFlatCoordinates(),o=t.getStride(),s=n.length/o-1,a=r||0,h=0;h<=s;++h){var l=h*o,u=a+2*Ct(h,s)*Math.PI/s;n[l]=e[0]+i*Math.cos(u),n[l+1]=e[1]+i*Math.sin(u)}t.changed()}var nn=function(i){function t(t){i.call(this);var e=t||{};this.position_=null,this.transform_=ie,this.watchId_=void 0,E(this,b(nr),this.handleProjectionChanged_,this),E(this,b(sr),this.handleTrackingChanged_,this),void 0!==e.projection&&this.setProjection(e.projection),void 0!==e.trackingOptions&&this.setTrackingOptions(e.trackingOptions),this.setTracking(void 0!==e.tracking&&e.tracking)}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.disposeInternal=function(){this.setTracking(!1),i.prototype.disposeInternal.call(this)},t.prototype.handleProjectionChanged_=function(){var t=this.getProjection();t&&(this.transform_=ce(ne("EPSG:4326"),t),this.position_&&this.set(rr,this.transform_(this.position_)))},t.prototype.handleTrackingChanged_=function(){if(li){var t=this.getTracking();t&&void 0===this.watchId_?this.watchId_=navigator.geolocation.watchPosition(this.positionChange_.bind(this),this.positionError_.bind(this),this.getTrackingOptions()):t||void 0===this.watchId_||(navigator.geolocation.clearWatch(this.watchId_),this.watchId_=void 0)}},t.prototype.positionChange_=function(t){var e=t.coords;this.set(Qi,e.accuracy),this.set(tr,null===e.altitude?void 0:e.altitude),this.set(er,null===e.altitudeAccuracy?void 0:e.altitudeAccuracy),this.set(ir,null===e.heading?void 0:St(e.heading)),this.position_?(this.position_[0]=e.longitude,this.position_[1]=e.latitude):this.position_=[e.longitude,e.latitude];var i=this.transform_(this.position_);this.set(rr,i),this.set(or,null===e.speed?void 0:e.speed);var r=$r(this.position_,e.accuracy);r.applyTransform(this.transform_),this.set($i,r),this.changed()},t.prototype.positionError_=function(t){t.type=w.ERROR,this.setTracking(!1),this.dispatchEvent(t)},t.prototype.getAccuracy=function(){return this.get(Qi)},t.prototype.getAccuracyGeometry=function(){return this.get($i)||null},t.prototype.getAltitude=function(){return this.get(tr)},t.prototype.getAltitudeAccuracy=function(){return this.get(er)},t.prototype.getHeading=function(){return this.get(ir)},t.prototype.getPosition=function(){return this.get(rr)},t.prototype.getProjection=function(){return this.get(nr)},t.prototype.getSpeed=function(){return this.get(or)},t.prototype.getTracking=function(){return this.get(sr)},t.prototype.getTrackingOptions=function(){return this.get(ar)},t.prototype.setProjection=function(t){this.set(nr,ne(t))},t.prototype.setTracking=function(t){this.set(sr,t)},t.prototype.setTrackingOptions=function(t){this.set(ar,t)},t}(R);function on(t,e,i){var r=void 0!==i?t.toFixed(i):""+t,n=r.indexOf(".");return e<(n=-1===n?r.length:n)?r:new Array(1+e-n).join("0")+r}function sn(t,e){for(var i=(""+t).split("."),r=(""+e).split("."),n=0;n<Math.max(i.length,r.length);n++){var o=parseInt(i[n]||"0",10),s=parseInt(r[n]||"0",10);if(s<o)return 1;if(o<s)return-1}return 0}function an(t,e){return t[0]+=e[0],t[1]+=e[1],t}function hn(t,e){var i,r,n=t[0],o=t[1],s=e[0],a=e[1],h=s[0],l=s[1],u=a[0],c=a[1],p=u-h,d=c-l,f=0===p&&0===d?0:(p*(n-h)+d*(o-l))/(p*p+d*d||0);return f<=0?(i=h,r=l):1<=f?(i=u,r=c):(i=h+f*p,r=l+f*d),[i,r]}function ln(t,e,i){var r=Ct(e+180,360)-180,n=Math.abs(3600*r),o=i||0,s=Math.pow(10,o),a=Math.floor(n/3600),h=Math.floor((n-3600*a)/60),l=n-3600*a-60*h;return 60<=(l=Math.ceil(l*s)/s)&&(l=0,h+=1),60<=h&&(h=0,a+=1),a+"° "+on(h,2)+"′ "+on(l,2,o)+"″"+(0==r?"":" "+t.charAt(r<0?1:0))}function un(t,e,i){return t?e.replace("{x}",t[0].toFixed(i)).replace("{y}",t[1].toFixed(i)):""}function cn(t,e){for(var i=!0,r=t.length-1;0<=r;--r)if(t[r]!=e[r]){i=!1;break}return i}function pn(t,e){var i=Math.cos(e),r=Math.sin(e),n=t[0]*i-t[1]*r,o=t[1]*i+t[0]*r;return t[0]=n,t[1]=o,t}function dn(t,e){return t[0]*=e,t[1]*=e,t}function fn(t,e){var i=t[0]-e[0],r=t[1]-e[1];return i*i+r*r}function _n(t,e){return Math.sqrt(fn(t,e))}function gn(t,e){return fn(t,hn(t,e))}function yn(t,e){return un(t,"{x}, {y}",e)}function vn(t,e,i,r,n,o){var s=NaN,a=NaN,h=(i-e)/r;if(1===h)s=t[e],a=t[e+1];else if(2==h)s=(1-n)*t[e]+n*t[e+r],a=(1-n)*t[e+1]+n*t[e+r+1];else if(0!==h){for(var l=t[e],u=t[e+1],c=0,p=[0],d=e+r;d<i;d+=r){var f=t[d],_=t[d+1];c+=Math.sqrt((f-l)*(f-l)+(_-u)*(_-u)),p.push(c),l=f,u=_}var g=n*c,y=function(t,e,i){for(var r,n,o=i||hr,s=0,a=t.length,h=!1;s<a;)(n=+o(t[r=s+(a-s>>1)],e))<0?s=r+1:(a=r,h=!n);return h?s:~s}(p,g);if(y<0){var v=(g-p[-y-2])/(p[-y-1]-p[-y-2]),m=e+(-y-2)*r;s=It(t[m],t[m+r],v),a=It(t[m+1],t[m+r+1],v)}else s=t[e+y*r],a=t[e+y*r+1]}return o?(o[0]=s,o[1]=a,o):[s,a]}function mn(t,e,i,r,n,o){if(i==e)return null;var s;if(n<t[e+r-1])return o?((s=t.slice(e,e+r))[r-1]=n,s):null;if(t[i-1]<n)return o?((s=t.slice(i-r,i))[r-1]=n,s):null;if(n==t[e+r-1])return t.slice(e,e+r);for(var a=e/r,h=i/r;a<h;){var l=a+h>>1;n<t[(l+1)*r-1]?h=l:a=l+1}var u=t[a*r-1];if(n==u)return t.slice((a-1)*r,(a-1)*r+r);var c=(n-u)/(t[(a+1)*r-1]-u);s=[];for(var p=0;p<r-1;++p)s.push(It(t[(a-1)*r+p],t[a*r+p],c));return s.push(n),s}function xn(t,e,i,r){for(var n=t[e],o=t[e+1],s=0,a=e+r;a<i;a+=r){var h=t[a],l=t[a+1];s+=Math.sqrt((h-n)*(h-n)+(l-o)*(l-o)),n=h,o=l}return s}var Sn=function(i){function r(t,e){i.call(this),this.flatMidpoint_=null,this.flatMidpointRevision_=-1,this.maxDelta_=-1,this.maxDeltaRevision_=-1,void 0===e||Array.isArray(t[0])?this.setCoordinates(t,e):this.setFlatCoordinates(e,t)}return i&&(r.__proto__=i),((r.prototype=Object.create(i&&i.prototype)).constructor=r).prototype.appendCoordinate=function(t){this.flatCoordinates?pr(this.flatCoordinates,t):this.flatCoordinates=t.slice(),this.changed()},r.prototype.clone=function(){return new r(this.flatCoordinates.slice(),this.layout)},r.prototype.closestPointXY=function(t,e,i,r){return r<D(this.getExtent(),t,e)?r:(this.maxDeltaRevision_!=this.getRevision()&&(this.maxDelta_=Math.sqrt(Er(this.flatCoordinates,0,this.flatCoordinates.length,this.stride,0)),this.maxDeltaRevision_=this.getRevision()),wr(this.flatCoordinates,0,this.flatCoordinates.length,this.stride,this.maxDelta_,!1,t,e,i,r))},r.prototype.forEachSegment=function(t){return zr(this.flatCoordinates,0,this.flatCoordinates.length,this.stride,t)},r.prototype.getCoordinateAtM=function(t,e){if(this.layout!=yr.XYM&&this.layout!=yr.XYZM)return null;var i=void 0!==e&&e;return mn(this.flatCoordinates,0,this.flatCoordinates.length,this.stride,t,i)},r.prototype.getCoordinates=function(){return Pr(this.flatCoordinates,0,this.flatCoordinates.length,this.stride)},r.prototype.getCoordinateAt=function(t,e){return vn(this.flatCoordinates,0,this.flatCoordinates.length,this.stride,t,e)},r.prototype.getLength=function(){return xn(this.flatCoordinates,0,this.flatCoordinates.length,this.stride)},r.prototype.getFlatMidpoint=function(){return this.flatMidpointRevision_!=this.getRevision()&&(this.flatMidpoint_=this.getCoordinateAt(.5,this.flatMidpoint_),this.flatMidpointRevision_=this.getRevision()),this.flatMidpoint_},r.prototype.getSimplifiedGeometryInternal=function(t){var e=[];return e.length=Or(this.flatCoordinates,0,this.flatCoordinates.length,this.stride,t,e,0),new r(e,yr.XY)},r.prototype.getType=function(){return Lt.LINE_STRING},r.prototype.intersectsExtent=function(t){return Vr(this.flatCoordinates,0,this.flatCoordinates.length,this.stride,t)},r.prototype.setCoordinates=function(t,e){this.setLayout(e,t,1),this.flatCoordinates||(this.flatCoordinates=[]),this.flatCoordinates.length=Lr(this.flatCoordinates,0,t,this.stride),this.changed()},r}(vr);function Cn(t,e,i){for(var r,n,o,s,a,h,l=[],u=t(0),c=t(1),p=e(u),d=e(c),f=[c,u],_=[d,p],g=[1,0],y={},v=1e5;0<--v&&0<g.length;)o=g.pop(),u=f.pop(),p=_.pop(),(h=o.toString())in y||(l.push(p[0],p[1]),y[h]=!0),s=g.pop(),c=f.pop(),d=_.pop(),vt((n=e(r=t(a=(o+s)/2)))[0],n[1],p[0],p[1],d[0],d[1])<i?(l.push(d[0],d[1]),y[h=s.toString()]=!0):(g.push(s,a,a,o),_.push(d,n,n,p),f.push(c,r,r,u));return l}var En="postcompose",Tn="precompose",wn="render",Rn="point",In="line",Ln=function(t){var e=t||{};this.font_=e.font,this.rotation_=e.rotation,this.rotateWithView_=e.rotateWithView,this.scale_=e.scale,this.text_=e.text,this.textAlign_=e.textAlign,this.textBaseline_=e.textBaseline,this.fill_=void 0!==e.fill?e.fill:new zi({color:"#333"}),this.maxAngle_=void 0!==e.maxAngle?e.maxAngle:Math.PI/4,this.placement_=void 0!==e.placement?e.placement:Rn,this.overflow_=!!e.overflow,this.stroke_=void 0!==e.stroke?e.stroke:null,this.offsetX_=void 0!==e.offsetX?e.offsetX:0,this.offsetY_=void 0!==e.offsetY?e.offsetY:0,this.backgroundFill_=e.backgroundFill?e.backgroundFill:null,this.backgroundStroke_=e.backgroundStroke?e.backgroundStroke:null,this.padding_=void 0===e.padding?null:e.padding};Ln.prototype.clone=function(){return new Ln({font:this.getFont(),placement:this.getPlacement(),maxAngle:this.getMaxAngle(),overflow:this.getOverflow(),rotation:this.getRotation(),rotateWithView:this.getRotateWithView(),scale:this.getScale(),text:this.getText(),textAlign:this.getTextAlign(),textBaseline:this.getTextBaseline(),fill:this.getFill()?this.getFill().clone():void 0,stroke:this.getStroke()?this.getStroke().clone():void 0,offsetX:this.getOffsetX(),offsetY:this.getOffsetY(),backgroundFill:this.getBackgroundFill()?this.getBackgroundFill().clone():void 0,backgroundStroke:this.getBackgroundStroke()?this.getBackgroundStroke().clone():void 0})},Ln.prototype.getOverflow=function(){return this.overflow_},Ln.prototype.getFont=function(){return this.font_},Ln.prototype.getMaxAngle=function(){return this.maxAngle_},Ln.prototype.getPlacement=function(){return this.placement_},Ln.prototype.getOffsetX=function(){return this.offsetX_},Ln.prototype.getOffsetY=function(){return this.offsetY_},Ln.prototype.getFill=function(){return this.fill_},Ln.prototype.getRotateWithView=function(){return this.rotateWithView_},Ln.prototype.getRotation=function(){return this.rotation_},Ln.prototype.getScale=function(){return this.scale_},Ln.prototype.getStroke=function(){return this.stroke_},Ln.prototype.getText=function(){return this.text_},Ln.prototype.getTextAlign=function(){return this.textAlign_},Ln.prototype.getTextBaseline=function(){return this.textBaseline_},Ln.prototype.getBackgroundFill=function(){return this.backgroundFill_},Ln.prototype.getBackgroundStroke=function(){return this.backgroundStroke_},Ln.prototype.getPadding=function(){return this.padding_},Ln.prototype.setOverflow=function(t){this.overflow_=t},Ln.prototype.setFont=function(t){this.font_=t},Ln.prototype.setMaxAngle=function(t){this.maxAngle_=t},Ln.prototype.setOffsetX=function(t){this.offsetX_=t},Ln.prototype.setOffsetY=function(t){this.offsetY_=t},Ln.prototype.setPlacement=function(t){this.placement_=t},Ln.prototype.setFill=function(t){this.fill_=t},Ln.prototype.setRotation=function(t){this.rotation_=t},Ln.prototype.setScale=function(t){this.scale_=t},Ln.prototype.setStroke=function(t){this.stroke_=t},Ln.prototype.setText=function(t){this.text_=t},Ln.prototype.setTextAlign=function(t){this.textAlign_=t},Ln.prototype.setTextBaseline=function(t){this.textBaseline_=t},Ln.prototype.setBackgroundFill=function(t){this.backgroundFill_=t},Ln.prototype.setBackgroundStroke=function(t){this.backgroundStroke_=t},Ln.prototype.setPadding=function(t){this.padding_=t};var bn=new Vi({color:"rgba(0,0,0,0.2)"}),Pn=[90,45,30,20,10,5,2,1,.5,.2,.1,.05,.01,.005,.002,.001],Fn=function(t){var e=t||{};this.map_=null,this.postcomposeListenerKey_=null,this.projection_=null,this.maxLat_=1/0,this.maxLon_=1/0,this.minLat_=-1/0,this.minLon_=-1/0,this.maxLatP_=1/0,this.maxLonP_=1/0,this.minLatP_=-1/0,this.minLonP_=-1/0,this.targetSize_=void 0!==e.targetSize?e.targetSize:100,this.maxLines_=void 0!==e.maxLines?e.maxLines:100,this.meridians_=[],this.parallels_=[],this.strokeStyle_=void 0!==e.strokeStyle?e.strokeStyle:bn,this.fromLonLatTransform_=void 0,this.toLonLatTransform_=void 0,this.projectionCenterLonLat_=null,this.meridiansLabels_=null,this.parallelsLabels_=null,1==e.showLabels&&(this.lonLabelFormatter_=null==e.lonLabelFormatter?ln.bind(this,"EW"):e.lonLabelFormatter,this.latLabelFormatter_=null==e.latLabelFormatter?ln.bind(this,"NS"):e.latLabelFormatter,this.lonLabelPosition_=null==e.lonLabelPosition?0:e.lonLabelPosition,this.latLabelPosition_=null==e.latLabelPosition?1:e.latLabelPosition,this.lonLabelStyle_=void 0!==e.lonLabelStyle?e.lonLabelStyle:new Ln({font:"12px Calibri,sans-serif",textBaseline:"bottom",fill:new zi({color:"rgba(0,0,0,1)"}),stroke:new Vi({color:"rgba(255,255,255,1)",width:3})}),this.latLabelStyle_=void 0!==e.latLabelStyle?e.latLabelStyle:new Ln({font:"12px Calibri,sans-serif",textAlign:"end",fill:new zi({color:"rgba(0,0,0,1)"}),stroke:new Vi({color:"rgba(255,255,255,1)",width:3})}),this.meridiansLabels_=[],this.parallelsLabels_=[]),this.setMap(void 0!==e.map?e.map:null)};Fn.prototype.addMeridian_=function(t,e,i,r,n,o){var s=this.getMeridian_(t,e,i,r,o);if(wt(s.getExtent(),n)){if(this.meridiansLabels_){var a=this.getMeridianPoint_(s,n,o);this.meridiansLabels_[o]={geom:a,text:this.lonLabelFormatter_(t)}}this.meridians_[o++]=s}return o},Fn.prototype.getMeridianPoint_=function(t,e,i){var r,n=t.getFlatCoordinates(),o=Math.max(e[1],n[1]),s=Math.min(e[3],n[n.length-1]),a=gt(e[1]+Math.abs(e[1]-e[3])*this.lonLabelPosition_,o,s),h=[n[0],a];return i in this.meridiansLabels_?(r=this.meridiansLabels_[i]).setCoordinates(h):r=new Dr(h),r},Fn.prototype.addParallel_=function(t,e,i,r,n,o){var s=this.getParallel_(t,e,i,r,o);if(wt(s.getExtent(),n)){if(this.parallelsLabels_){var a=this.getParallelPoint_(s,n,o);this.parallelsLabels_[o]={geom:a,text:this.latLabelFormatter_(t)}}this.parallels_[o++]=s}return o},Fn.prototype.getParallelPoint_=function(t,e,i){var r,n=t.getFlatCoordinates(),o=Math.max(e[0],n[0]),s=Math.min(e[2],n[n.length-2]),a=[gt(e[0]+Math.abs(e[0]-e[2])*this.latLabelPosition_,o,s),n[1]];return i in this.parallelsLabels_?(r=this.parallelsLabels_[i]).setCoordinates(a):r=new Dr(a),r},Fn.prototype.createGraticule_=function(t,e,i,r){var n=this.getInterval_(i);if(-1==n)return this.meridians_.length=this.parallels_.length=0,this.meridiansLabels_&&(this.meridiansLabels_.length=0),void(this.parallelsLabels_&&(this.parallelsLabels_.length=0));var o,s,a,h,l=this.toLonLatTransform_(e),u=l[0],c=l[1],p=this.maxLines_,d=[Math.max(t[0],this.minLonP_),Math.max(t[1],this.minLatP_),Math.min(t[2],this.maxLonP_),Math.min(t[3],this.maxLatP_)],f=(d=fe(d,this.projection_,"EPSG:4326"))[3],_=d[2],g=d[1],y=d[0];for(h=gt(u=Math.floor(u/n)*n,this.minLon_,this.maxLon_),s=this.addMeridian_(h,g,f,r,t,0),o=0;h!=this.minLon_&&o++<p;)h=Math.max(h-n,this.minLon_),s=this.addMeridian_(h,g,f,r,t,s);for(h=gt(u,this.minLon_,this.maxLon_),o=0;h!=this.maxLon_&&o++<p;)h=Math.min(h+n,this.maxLon_),s=this.addMeridian_(h,g,f,r,t,s);for(this.meridians_.length=s,this.meridiansLabels_&&(this.meridiansLabels_.length=s),a=gt(c=Math.floor(c/n)*n,this.minLat_,this.maxLat_),s=this.addParallel_(a,y,_,r,t,0),o=0;a!=this.minLat_&&o++<p;)a=Math.max(a-n,this.minLat_),s=this.addParallel_(a,y,_,r,t,s);for(a=gt(c,this.minLat_,this.maxLat_),o=0;a!=this.maxLat_&&o++<p;)a=Math.min(a+n,this.maxLat_),s=this.addParallel_(a,y,_,r,t,s);this.parallels_.length=s,this.parallelsLabels_&&(this.parallelsLabels_.length=s)},Fn.prototype.getInterval_=function(t){for(var e=this.projectionCenterLonLat_[0],i=this.projectionCenterLonLat_[1],r=-1,n=Math.pow(this.targetSize_*t,2),o=[],s=[],a=0,h=Pn.length;a<h;++a){var l=Pn[a]/2;if(o[0]=e-l,o[1]=i-l,s[0]=e+l,s[1]=i+l,this.fromLonLatTransform_(o,o),this.fromLonLatTransform_(s,s),Math.pow(s[0]-o[0],2)+Math.pow(s[1]-o[1],2)<=n)break;r=Pn[a]}return r},Fn.prototype.getMap=function(){return this.map_},Fn.prototype.getMeridian_=function(t,e,i,r,n){var o,s,a,h,l,u=(o=t,s=e,a=i,h=this.projection_,l=r,Cn(function(t){return[o,s+(a-s)*t]},pe(ne("EPSG:4326"),h),l)),c=this.meridians_[n];return c?(c.setFlatCoordinates(yr.XY,u),c.changed()):c=this.meridians_[n]=new Sn(u,yr.XY),c},Fn.prototype.getMeridians=function(){return this.meridians_},Fn.prototype.getParallel_=function(t,e,i,r,n){var o,s,a,h,l,u=(o=t,s=e,a=i,h=this.projection_,l=r,Cn(function(t){return[s+(a-s)*t,o]},pe(ne("EPSG:4326"),h),l)),c=this.parallels_[n];return c?(c.setFlatCoordinates(yr.XY,u),c.changed()):c=new Sn(u,yr.XY),c},Fn.prototype.getParallels=function(){return this.parallels_},Fn.prototype.handlePostCompose_=function(t){var e,i,r,n,o=t.vectorContext,s=t.frameState,a=s.extent,h=s.viewState,l=h.center,u=h.projection,c=h.resolution,p=s.pixelRatio,d=c*c/(4*p*p);for((!this.projection_||!ue(this.projection_,u))&&this.updateProjectionInfo_(u),this.createGraticule_(a,l,c,d),o.setFillStrokeStyle(null,this.strokeStyle_),e=0,i=this.meridians_.length;e<i;++e)r=this.meridians_[e],o.drawGeometry(r);for(e=0,i=this.parallels_.length;e<i;++e)r=this.parallels_[e],o.drawGeometry(r);if(this.meridiansLabels_)for(e=0,i=this.meridiansLabels_.length;e<i;++e)n=this.meridiansLabels_[e],this.lonLabelStyle_.setText(n.text),o.setTextStyle(this.lonLabelStyle_),o.drawGeometry(n.geom);if(this.parallelsLabels_)for(e=0,i=this.parallelsLabels_.length;e<i;++e)n=this.parallelsLabels_[e],this.latLabelStyle_.setText(n.text),o.setTextStyle(this.latLabelStyle_),o.drawGeometry(n.geom)},Fn.prototype.updateProjectionInfo_=function(t){var e=ne("EPSG:4326"),i=t.getWorldExtent(),r=fe(i,e,t);this.maxLat_=i[3],this.maxLon_=i[2],this.minLat_=i[1],this.minLon_=i[0],this.maxLatP_=r[3],this.maxLonP_=r[2],this.minLatP_=r[1],this.minLonP_=r[0],this.fromLonLatTransform_=pe(e,t),this.toLonLatTransform_=pe(t,e),this.projectionCenterLonLat_=this.toLonLatTransform_(ot(t.getExtent())),this.projection_=t},Fn.prototype.setMap=function(t){this.map_&&(g(this.postcomposeListenerKey_),this.postcomposeListenerKey_=null,this.map_.render()),t&&(this.postcomposeListenerKey_=E(t,En,this.handlePostCompose_,this),t.render()),this.map_=t};var Mn=function(n){function t(t,e,i,r){n.call(this),this.extent=t,this.pixelRatio_=i,this.resolution=e,this.state=r}return n&&(t.__proto__=n),((t.prototype=Object.create(n&&n.prototype)).constructor=t).prototype.changed=function(){this.dispatchEvent(w.CHANGE)},t.prototype.getExtent=function(){return this.extent},t.prototype.getImage=function(){},t.prototype.getPixelRatio=function(){return this.pixelRatio_},t.prototype.getResolution=function(){return this.resolution},t.prototype.getState=function(){return this.state},t.prototype.load=function(){},t}(i),On=function(s){function t(t,e,i,r,n,o){s.call(this,t,e,i,di.IDLE),this.src_=r,this.image_=new Image,null!==n&&(this.image_.crossOrigin=n),this.imageListenerKeys_=null,this.state=di.IDLE,this.imageLoadFunction_=o}return s&&(t.__proto__=s),((t.prototype=Object.create(s&&s.prototype)).constructor=t).prototype.getImage=function(){return this.image_},t.prototype.handleImageError_=function(){this.state=di.ERROR,this.unlistenImage_(),this.changed()},t.prototype.handleImageLoad_=function(){void 0===this.resolution&&(this.resolution=at(this.extent)/this.image_.height),this.state=di.LOADED,this.unlistenImage_(),this.changed()},t.prototype.load=function(){this.state!=di.IDLE&&this.state!=di.ERROR||(this.state=di.LOADING,this.changed(),this.imageListenerKeys_=[p(this.image_,w.ERROR,this.handleImageError_,this),p(this.image_,w.LOAD,this.handleImageLoad_,this)],this.imageLoadFunction_(this,this.src_))},t.prototype.setImage=function(t){this.image_=t},t.prototype.unlistenImage_=function(){this.imageListenerKeys_.forEach(g),this.imageListenerKeys_=null},t}(Mn),Nn=0,An=1,Gn=2,kn=3,Dn=4,jn=5;function Un(t){return Math.pow(t,3)}function Yn(t){return 1-Un(1-t)}function Bn(t){return 3*t*t-2*t*t*t}function Xn(t){return t}var zn=function(n){function t(t,e,i){n.call(this);var r=i||{};this.tileCoord=t,this.state=e,this.interimTile=null,this.key="",this.transition_=void 0===r.transition?250:r.transition,this.transitionStarts_={}}return n&&(t.__proto__=n),((t.prototype=Object.create(n&&n.prototype)).constructor=t).prototype.changed=function(){this.dispatchEvent(w.CHANGE)},t.prototype.getKey=function(){return this.key+"/"+this.tileCoord},t.prototype.getInterimTile=function(){if(!this.interimTile)return this;var t=this.interimTile;do{if(t.getState()==Gn)return t;t=t.interimTile}while(t);return this},t.prototype.refreshInterimChain=function(){if(this.interimTile){var t=this.interimTile,e=this;do{if(t.getState()==Gn){t.interimTile=null;break}t.getState()==An?e=t:t.getState()==Nn?e.interimTile=t.interimTile:e=t,t=e.interimTile}while(t)}},t.prototype.getTileCoord=function(){return this.tileCoord},t.prototype.getState=function(){return this.state},t.prototype.setState=function(t){this.state=t,this.changed()},t.prototype.load=function(){},t.prototype.getAlpha=function(t,e){if(!this.transition_)return 1;var i=this.transitionStarts_[t];if(i){if(-1===i)return 1}else i=e,this.transitionStarts_[t]=i;var r=e-i+1e3/60;return r>=this.transition_?1:Un(r/this.transition_)},t.prototype.inTransition=function(t){return!!this.transition_&&-1!==this.transitionStarts_[t]},t.prototype.endTransition=function(t){this.transition_&&(this.transitionStarts_[t]=-1)},t}(i),Vn=function(s){function t(t,e,i,r,n,o){s.call(this,t,e,o),this.crossOrigin_=r,this.src_=i,this.image_=new Image,null!==r&&(this.image_.crossOrigin=r),this.imageListenerKeys_=null,this.tileLoadFunction_=n}return s&&(t.__proto__=s),((t.prototype=Object.create(s&&s.prototype)).constructor=t).prototype.disposeInternal=function(){this.state==An&&(this.unlistenImage_(),this.image_=Wn()),this.interimTile&&this.interimTile.dispose(),this.state=jn,this.changed(),s.prototype.disposeInternal.call(this)},t.prototype.getImage=function(){return this.image_},t.prototype.getKey=function(){return this.src_},t.prototype.handleImageError_=function(){this.state=kn,this.unlistenImage_(),this.image_=Wn(),this.changed()},t.prototype.handleImageLoad_=function(){this.image_.naturalWidth&&this.image_.naturalHeight?this.state=Gn:this.state=Dn,this.unlistenImage_(),this.changed()},t.prototype.load=function(){this.state==kn&&(this.state=Nn,this.image_=new Image,null!==this.crossOrigin_&&(this.image_.crossOrigin=this.crossOrigin_)),this.state==Nn&&(this.state=An,this.changed(),this.imageListenerKeys_=[p(this.image_,w.ERROR,this.handleImageError_,this),p(this.image_,w.LOAD,this.handleImageLoad_,this)],this.tileLoadFunction_(this,this.src_))},t.prototype.unlistenImage_=function(){this.imageListenerKeys_.forEach(g),this.imageListenerKeys_=null},t}(zn);function Wn(){var t=De(1,1);return t.fillStyle="rgba(0,0,0,0)",t.fillRect(0,0,1,1),t.canvas}var Kn=function(t,e,i){this.decay_=t,this.minVelocity_=e,this.delay_=i,this.points_=[],this.angle_=0,this.initialVelocity_=0};Kn.prototype.begin=function(){this.points_.length=0,this.angle_=0,this.initialVelocity_=0},Kn.prototype.update=function(t,e){this.points_.push(t,e,Date.now())},Kn.prototype.end=function(){if(this.points_.length<6)return!1;var t=Date.now()-this.delay_,e=this.points_.length-3;if(this.points_[e+2]<t)return!1;for(var i=e-3;0<i&&this.points_[i+2]>t;)i-=3;var r=this.points_[e+2]-this.points_[i+2];if(r<1e3/60)return!1;var n=this.points_[e]-this.points_[i],o=this.points_[e+1]-this.points_[i+1];return this.angle_=Math.atan2(o,n),this.initialVelocity_=Math.sqrt(n*n+o*o)/r,this.initialVelocity_>this.minVelocity_},Kn.prototype.getDistance=function(){return(this.minVelocity_-this.initialVelocity_)/this.decay_},Kn.prototype.getAngle=function(){return this.angle_};var Hn=function(r){function t(t,e,i){r.call(this,t),this.map=e,this.frameState=void 0!==i?i:null}return r&&(t.__proto__=r),(t.prototype=Object.create(r&&r.prototype)).constructor=t}(m),Zn=function(o){function t(t,e,i,r,n){o.call(this,t,e,n),this.originalEvent=i,this.pixel=e.getEventPixel(i),this.coordinate=e.getCoordinateFromPixel(this.pixel),this.dragging=void 0!==r&&r}return o&&(t.__proto__=o),((t.prototype=Object.create(o&&o.prototype)).constructor=t).prototype.preventDefault=function(){o.prototype.preventDefault.call(this),this.originalEvent.preventDefault()},t.prototype.stopPropagation=function(){o.prototype.stopPropagation.call(this),this.originalEvent.stopPropagation()},t}(Hn),qn={SINGLECLICK:"singleclick",CLICK:w.CLICK,DBLCLICK:w.DBLCLICK,POINTERDRAG:"pointerdrag",POINTERMOVE:"pointermove",POINTERDOWN:"pointerdown",POINTERUP:"pointerup",POINTEROVER:"pointerover",POINTEROUT:"pointerout",POINTERENTER:"pointerenter",POINTERLEAVE:"pointerleave",POINTERCANCEL:"pointercancel"},Jn=function(o){function t(t,e,i,r,n){o.call(this,t,e,i.originalEvent,r,n),this.pointerEvent=i}return o&&(t.__proto__=o),(t.prototype=Object.create(o&&o.prototype)).constructor=t}(Zn),Qn="pointermove",$n="pointerdown",to="pointerup",eo="pointerover",io="pointerout",ro="pointerenter",no="pointerleave",oo="pointercancel",so=function(t,e){this.dispatcher=t,this.mapping_=e};so.prototype.getEvents=function(){return Object.keys(this.mapping_)},so.prototype.getHandlerForEvent=function(t){return this.mapping_[t]};var ao=1,ho="mouse";function lo(t){if(!this.isEventSimulatedFromTouch_(t)){ao.toString()in this.pointerMap&&this.cancel(t);var e=go(t,this.dispatcher);this.pointerMap[ao.toString()]=t,this.dispatcher.down(e,t)}}function uo(t){if(!this.isEventSimulatedFromTouch_(t)){var e=go(t,this.dispatcher);this.dispatcher.move(e,t)}}function co(t){if(!this.isEventSimulatedFromTouch_(t)){var e=this.pointerMap[ao.toString()];if(e&&e.button===t.button){var i=go(t,this.dispatcher);this.dispatcher.up(i,t),this.cleanupMouse()}}}function po(t){if(!this.isEventSimulatedFromTouch_(t)){var e=go(t,this.dispatcher);this.dispatcher.enterOver(e,t)}}function fo(t){if(!this.isEventSimulatedFromTouch_(t)){var e=go(t,this.dispatcher);this.dispatcher.leaveOut(e,t)}}var _o=function(i){function t(t){var e={mousedown:lo,mousemove:uo,mouseup:co,mouseover:po,mouseout:fo};i.call(this,t,e),this.pointerMap=t.pointerMap,this.lastTouches=[]}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.isEventSimulatedFromTouch_=function(t){for(var e=this.lastTouches,i=t.clientX,r=t.clientY,n=0,o=e.length,s=void 0;n<o&&(s=e[n]);n++){var a=Math.abs(i-s[0]),h=Math.abs(r-s[1]);if(a<=25&&h<=25)return!0}return!1},t.prototype.cancel=function(t){var e=go(t,this.dispatcher);this.dispatcher.cancel(e,t),this.cleanupMouse()},t.prototype.cleanupMouse=function(){delete this.pointerMap[ao.toString()]},t}(so);function go(t,e){var i=e.cloneEvent(t,t),r=i.preventDefault;return i.preventDefault=function(){t.preventDefault(),r()},i.pointerId=ao,i.isPrimary=!0,i.pointerType=ho,i}var yo=["","unavailable","touch","pen","mouse"];function vo(t){this.pointerMap[t.pointerId.toString()]=t;var e=this.prepareEvent_(t);this.dispatcher.down(e,t)}function mo(t){var e=this.prepareEvent_(t);this.dispatcher.move(e,t)}function xo(t){var e=this.prepareEvent_(t);this.dispatcher.up(e,t),this.cleanup(t.pointerId)}function So(t){var e=this.prepareEvent_(t);this.dispatcher.leaveOut(e,t)}function Co(t){var e=this.prepareEvent_(t);this.dispatcher.enterOver(e,t)}function Eo(t){var e=this.prepareEvent_(t);this.dispatcher.cancel(e,t),this.cleanup(t.pointerId)}function To(t){var e=this.dispatcher.makeEvent("lostpointercapture",t,t);this.dispatcher.dispatchEvent(e)}function wo(t){var e=this.dispatcher.makeEvent("gotpointercapture",t,t);this.dispatcher.dispatchEvent(e)}var Ro=function(i){function t(t){var e={MSPointerDown:vo,MSPointerMove:mo,MSPointerUp:xo,MSPointerOut:So,MSPointerOver:Co,MSPointerCancel:Eo,MSGotPointerCapture:wo,MSLostPointerCapture:To};i.call(this,t,e),this.pointerMap=t.pointerMap}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.prepareEvent_=function(t){var e=t;return"number"==typeof t.pointerType&&((e=this.dispatcher.cloneEvent(t,t)).pointerType=yo[t.pointerType]),e},t.prototype.cleanup=function(t){delete this.pointerMap[t.toString()]},t}(so);function Io(t){this.dispatcher.fireNativeEvent(t)}function Lo(t){this.dispatcher.fireNativeEvent(t)}function bo(t){this.dispatcher.fireNativeEvent(t)}function Po(t){this.dispatcher.fireNativeEvent(t)}function Fo(t){this.dispatcher.fireNativeEvent(t)}function Mo(t){this.dispatcher.fireNativeEvent(t)}function Oo(t){this.dispatcher.fireNativeEvent(t)}function No(t){this.dispatcher.fireNativeEvent(t)}var Ao=function(i){function t(t){var e={pointerdown:Io,pointermove:Lo,pointerup:bo,pointerout:Po,pointerover:Fo,pointercancel:Mo,gotpointercapture:No,lostpointercapture:Oo};i.call(this,t,e)}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(so),Go=!1,ko=function(n){function t(t,e,i){n.call(this,t),this.originalEvent=e;var r=i||{};this.buttons=this.getButtons_(r),this.pressure=this.getPressure_(r,this.buttons),this.bubbles="bubbles"in r&&r.bubbles,this.cancelable="cancelable"in r&&r.cancelable,this.view="view"in r?r.view:null,this.detail="detail"in r?r.detail:null,this.screenX="screenX"in r?r.screenX:0,this.screenY="screenY"in r?r.screenY:0,this.clientX="clientX"in r?r.clientX:0,this.clientY="clientY"in r?r.clientY:0,this.ctrlKey="ctrlKey"in r&&r.ctrlKey,this.altKey="altKey"in r&&r.altKey,this.shiftKey="shiftKey"in r&&r.shiftKey,this.metaKey="metaKey"in r&&r.metaKey,this.button="button"in r?r.button:0,this.relatedTarget="relatedTarget"in r?r.relatedTarget:null,this.pointerId="pointerId"in r?r.pointerId:0,this.width="width"in r?r.width:0,this.height="height"in r?r.height:0,this.tiltX="tiltX"in r?r.tiltX:0,this.tiltY="tiltY"in r?r.tiltY:0,this.pointerType="pointerType"in r?r.pointerType:"",this.hwTimestamp="hwTimestamp"in r?r.hwTimestamp:0,this.isPrimary="isPrimary"in r&&r.isPrimary,e.preventDefault&&(this.preventDefault=function(){e.preventDefault()})}return n&&(t.__proto__=n),((t.prototype=Object.create(n&&n.prototype)).constructor=t).prototype.getButtons_=function(t){var e;if(t.buttons||Go)e=t.buttons;else switch(t.which){case 1:e=1;break;case 2:e=4;break;case 3:e=2;break;default:e=0}return e},t.prototype.getPressure_=function(t,e){return t.pressure?t.pressure:e?.5:0},t}(m);!function(){try{var t=new MouseEvent("click",{buttons:1});Go=1===t.buttons}catch(t){}}();function Do(t){this.vacuumTouches_(t),this.setPrimaryTouch_(t.changedTouches[0]),this.dedupSynthMouse_(t),this.clickCount_++,this.processTouches_(t,this.overDown_)}function jo(t){t.preventDefault(),this.processTouches_(t,this.moveOverOut_)}function Uo(t){this.dedupSynthMouse_(t),this.processTouches_(t,this.upOut_)}function Yo(t){this.processTouches_(t,this.cancelOut_)}var Bo=function(r){function t(t,e){var i={touchstart:Do,touchmove:jo,touchend:Uo,touchcancel:Yo};r.call(this,t,i),this.pointerMap=t.pointerMap,this.mouseSource=e,this.firstTouchId_=void 0,this.clickCount_=0,this.resetId_=void 0,this.dedupTimeout_=2500}return r&&(t.__proto__=r),((t.prototype=Object.create(r&&r.prototype)).constructor=t).prototype.isPrimaryTouch_=function(t){return this.firstTouchId_===t.identifier},t.prototype.setPrimaryTouch_=function(t){var e=Object.keys(this.pointerMap).length;(0===e||1===e&&ao.toString()in this.pointerMap)&&(this.firstTouchId_=t.identifier,this.cancelResetClickCount_())},t.prototype.removePrimaryPointer_=function(t){t.isPrimary&&(this.firstTouchId_=void 0,this.resetClickCount_())},t.prototype.resetClickCount_=function(){this.resetId_=setTimeout(this.resetClickCountHandler_.bind(this),200)},t.prototype.resetClickCountHandler_=function(){this.clickCount_=0,this.resetId_=void 0},t.prototype.cancelResetClickCount_=function(){void 0!==this.resetId_&&clearTimeout(this.resetId_)},t.prototype.touchToPointer_=function(t,e){var i=this.dispatcher.cloneEvent(t,e);return i.pointerId=e.identifier+2,i.bubbles=!0,i.cancelable=!0,i.detail=this.clickCount_,i.button=0,i.buttons=1,i.width=e.webkitRadiusX||e.radiusX||0,i.height=e.webkitRadiusY||e.radiusY||0,i.pressure=e.webkitForce||e.force||.5,i.isPrimary=this.isPrimaryTouch_(e),i.pointerType="touch",i.clientX=e.clientX,i.clientY=e.clientY,i.screenX=e.screenX,i.screenY=e.screenY,i},t.prototype.processTouches_=function(t,e){var i=Array.prototype.slice.call(t.changedTouches),r=i.length;function n(){t.preventDefault()}for(var o=0;o<r;++o){var s=this.touchToPointer_(t,i[o]);s.preventDefault=n,e.call(this,t,s)}},t.prototype.findTouch_=function(t,e){for(var i=t.length,r=0;r<i;r++){if(t[r].identifier===e)return!0}return!1},t.prototype.vacuumTouches_=function(t){var e=t.touches,i=Object.keys(this.pointerMap),r=i.length;if(r>=e.length){for(var n=[],o=0;o<r;++o){var s=i[o],a=this.pointerMap[s];s==ao||this.findTouch_(e,s-2)||n.push(a.out)}for(var h=0;h<n.length;++h)this.cancelOut_(t,n[h])}},t.prototype.overDown_=function(t,e){this.pointerMap[e.pointerId]={target:e.target,out:e,outTarget:e.target},this.dispatcher.over(e,t),this.dispatcher.enter(e,t),this.dispatcher.down(e,t)},t.prototype.moveOverOut_=function(t,e){var i=e,r=this.pointerMap[i.pointerId];if(r){var n=r.out,o=r.outTarget;this.dispatcher.move(i,t),n&&o!==i.target&&(n.relatedTarget=i.target,i.relatedTarget=o,n.target=o,i.target?(this.dispatcher.leaveOut(n,t),this.dispatcher.enterOver(i,t)):(i.target=o,i.relatedTarget=null,this.cancelOut_(t,i))),r.out=i,r.outTarget=i.target}},t.prototype.upOut_=function(t,e){this.dispatcher.up(e,t),this.dispatcher.out(e,t),this.dispatcher.leave(e,t),this.cleanUpPointer_(e)},t.prototype.cancelOut_=function(t,e){this.dispatcher.cancel(e,t),this.dispatcher.out(e,t),this.dispatcher.leave(e,t),this.cleanUpPointer_(e)},t.prototype.cleanUpPointer_=function(t){delete this.pointerMap[t.pointerId],this.removePrimaryPointer_(t)},t.prototype.dedupSynthMouse_=function(t){var r=this.mouseSource.lastTouches,e=t.changedTouches[0];if(this.isPrimaryTouch_(e)){var n=[e.clientX,e.clientY];r.push(n),setTimeout(function(){var t,e,i;e=n,i=(t=r).indexOf(e),-1<i&&t.splice(i,1)},this.dedupTimeout_)}},t}(so),Xo=[["bubbles",!1],["cancelable",!1],["view",null],["detail",null],["screenX",0],["screenY",0],["clientX",0],["clientY",0],["ctrlKey",!1],["altKey",!1],["shiftKey",!1],["metaKey",!1],["button",0],["relatedTarget",null],["buttons",0],["pointerId",0],["width",0],["height",0],["pressure",0],["tiltX",0],["tiltY",0],["pointerType",""],["hwTimestamp",0],["isPrimary",!1],["type",""],["target",null],["currentTarget",null],["which",0]],zo=function(e){function t(t){e.call(this),this.element_=t,this.pointerMap={},this.eventMap_={},this.eventSourceList_=[],this.registerSources()}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.registerSources=function(){if(ci)this.registerSource("native",new Ao(this));else if(pi)this.registerSource("ms",new Ro(this));else{var t=new _o(this);this.registerSource("mouse",t),ui&&this.registerSource("touch",new Bo(this,t))}this.register_()},t.prototype.registerSource=function(t,e){var i=e,r=i.getEvents();r&&(r.forEach(function(t){var e=i.getHandlerForEvent(t);e&&(this.eventMap_[t]=e.bind(i))}.bind(this)),this.eventSourceList_.push(i))},t.prototype.register_=function(){for(var t=this.eventSourceList_.length,e=0;e<t;e++){var i=this.eventSourceList_[e];this.addEvents_(i.getEvents())}},t.prototype.unregister_=function(){for(var t=this.eventSourceList_.length,e=0;e<t;e++){var i=this.eventSourceList_[e];this.removeEvents_(i.getEvents())}},t.prototype.eventHandler_=function(t){var e=t.type,i=this.eventMap_[e];i&&i(t)},t.prototype.addEvents_=function(t){t.forEach(function(t){E(this.element_,t,this.eventHandler_,this)}.bind(this))},t.prototype.removeEvents_=function(t){t.forEach(function(t){d(this.element_,t,this.eventHandler_,this)}.bind(this))},t.prototype.cloneEvent=function(t,e){for(var i={},r=0,n=Xo.length;r<n;r++){var o=Xo[r][0];i[o]=t[o]||e[o]||Xo[r][1]}return i},t.prototype.down=function(t,e){this.fireEvent($n,t,e)},t.prototype.move=function(t,e){this.fireEvent(Qn,t,e)},t.prototype.up=function(t,e){this.fireEvent(to,t,e)},t.prototype.enter=function(t,e){t.bubbles=!1,this.fireEvent(ro,t,e)},t.prototype.leave=function(t,e){t.bubbles=!1,this.fireEvent(no,t,e)},t.prototype.over=function(t,e){t.bubbles=!0,this.fireEvent(eo,t,e)},t.prototype.out=function(t,e){t.bubbles=!0,this.fireEvent(io,t,e)},t.prototype.cancel=function(t,e){this.fireEvent(oo,t,e)},t.prototype.leaveOut=function(t,e){this.out(t,e),this.contains_(t.target,t.relatedTarget)||this.leave(t,e)},t.prototype.enterOver=function(t,e){this.over(t,e),this.contains_(t.target,t.relatedTarget)||this.enter(t,e)},t.prototype.contains_=function(t,e){return!(!t||!e)&&t.contains(e)},t.prototype.makeEvent=function(t,e,i){return new ko(t,i,e)},t.prototype.fireEvent=function(t,e,i){var r=this.makeEvent(t,e,i);this.dispatchEvent(r)},t.prototype.fireNativeEvent=function(t){var e=this.makeEvent(t.type,t,t);this.dispatchEvent(e)},t.prototype.wrapMouseEvent=function(t,e){return this.makeEvent(t,_o.prepareEvent(e,this),e)},t.prototype.disposeInternal=function(){this.unregister_(),e.prototype.disposeInternal.call(this)},t}(i),Vo=function(r){function t(t,e){r.call(this),this.map_=t,this.clickTimeoutId_=0,this.dragging_=!1,this.dragListenerKeys_=[],this.moveTolerance_=e?e*ai:ai,this.down_=null;var i=this.map_.getViewport();this.activePointers_=0,this.trackedTouches_={},this.pointerEventHandler_=new zo(i),this.documentPointerEventHandler_=null,this.pointerdownListenerKey_=E(this.pointerEventHandler_,$n,this.handlePointerDown_,this),this.relayedListenerKey_=E(this.pointerEventHandler_,Qn,this.relayEvent_,this)}return r&&(t.__proto__=r),((t.prototype=Object.create(r&&r.prototype)).constructor=t).prototype.emulateClick_=function(e){var t=new Jn(qn.CLICK,this.map_,e);this.dispatchEvent(t),0!==this.clickTimeoutId_?(clearTimeout(this.clickTimeoutId_),this.clickTimeoutId_=0,t=new Jn(qn.DBLCLICK,this.map_,e),this.dispatchEvent(t)):this.clickTimeoutId_=setTimeout(function(){this.clickTimeoutId_=0;var t=new Jn(qn.SINGLECLICK,this.map_,e);this.dispatchEvent(t)}.bind(this),250)},t.prototype.updateActivePointers_=function(t){var e=t;e.type==qn.POINTERUP||e.type==qn.POINTERCANCEL?delete this.trackedTouches_[e.pointerId]:e.type==qn.POINTERDOWN&&(this.trackedTouches_[e.pointerId]=!0),this.activePointers_=Object.keys(this.trackedTouches_).length},t.prototype.handlePointerUp_=function(t){this.updateActivePointers_(t);var e=new Jn(qn.POINTERUP,this.map_,t);this.dispatchEvent(e),e.propagationStopped||this.dragging_||!this.isMouseActionButton_(t)||this.emulateClick_(this.down_),0===this.activePointers_&&(this.dragListenerKeys_.forEach(g),this.dragListenerKeys_.length=0,this.dragging_=!1,this.down_=null,this.documentPointerEventHandler_.dispose(),this.documentPointerEventHandler_=null)},t.prototype.isMouseActionButton_=function(t){return 0===t.button},t.prototype.handlePointerDown_=function(t){this.updateActivePointers_(t);var e=new Jn(qn.POINTERDOWN,this.map_,t);this.dispatchEvent(e),this.down_=t,0===this.dragListenerKeys_.length&&(this.documentPointerEventHandler_=new zo(document),this.dragListenerKeys_.push(E(this.documentPointerEventHandler_,qn.POINTERMOVE,this.handlePointerMove_,this),E(this.documentPointerEventHandler_,qn.POINTERUP,this.handlePointerUp_,this),E(this.pointerEventHandler_,qn.POINTERCANCEL,this.handlePointerUp_,this)))},t.prototype.handlePointerMove_=function(t){if(this.isMoving_(t)){this.dragging_=!0;var e=new Jn(qn.POINTERDRAG,this.map_,t,this.dragging_);this.dispatchEvent(e)}t.preventDefault()},t.prototype.relayEvent_=function(t){var e=!(!this.down_||!this.isMoving_(t));this.dispatchEvent(new Jn(t.type,this.map_,t,e))},t.prototype.isMoving_=function(t){return this.dragging_||Math.abs(t.clientX-this.down_.clientX)>this.moveTolerance_||Math.abs(t.clientY-this.down_.clientY)>this.moveTolerance_},t.prototype.disposeInternal=function(){this.relayedListenerKey_&&(g(this.relayedListenerKey_),this.relayedListenerKey_=null),this.pointerdownListenerKey_&&(g(this.pointerdownListenerKey_),this.pointerdownListenerKey_=null),this.dragListenerKeys_.forEach(g),this.dragListenerKeys_.length=0,this.documentPointerEventHandler_&&(this.documentPointerEventHandler_.dispose(),this.documentPointerEventHandler_=null),this.pointerEventHandler_&&(this.pointerEventHandler_.dispose(),this.pointerEventHandler_=null),r.prototype.disposeInternal.call(this)},t}(i),Wo="postrender",Ko="movestart",Ho="moveend",Zo={LAYERGROUP:"layergroup",SIZE:"size",TARGET:"target",VIEW:"view"},qo=function(t,e){this.priorityFunction_=t,this.keyFunction_=e,this.elements_=[],this.priorities_=[],this.queuedElements_={}};qo.prototype.clear=function(){this.elements_.length=0,this.priorities_.length=0,_(this.queuedElements_)},qo.prototype.dequeue=function(){var t=this.elements_,e=this.priorities_,i=t[0];1==t.length?(t.length=0,e.length=0):(t[0]=t.pop(),e[0]=e.pop(),this.siftUp_(0));var r=this.keyFunction_(i);return delete this.queuedElements_[r],i},qo.prototype.enqueue=function(t){Z(!(this.keyFunction_(t)in this.queuedElements_),31);var e=this.priorityFunction_(t);return e!=1/0&&(this.elements_.push(t),this.priorities_.push(e),this.queuedElements_[this.keyFunction_(t)]=!0,this.siftDown_(0,this.elements_.length-1),!0)},qo.prototype.getCount=function(){return this.elements_.length},qo.prototype.getLeftChildIndex_=function(t){return 2*t+1},qo.prototype.getRightChildIndex_=function(t){return 2*t+2},qo.prototype.getParentIndex_=function(t){return t-1>>1},qo.prototype.heapify_=function(){var t;for(t=(this.elements_.length>>1)-1;0<=t;t--)this.siftUp_(t)},qo.prototype.isEmpty=function(){return 0===this.elements_.length},qo.prototype.isKeyQueued=function(t){return t in this.queuedElements_},qo.prototype.isQueued=function(t){return this.isKeyQueued(this.keyFunction_(t))},qo.prototype.siftUp_=function(t){for(var e=this.elements_,i=this.priorities_,r=e.length,n=e[t],o=i[t],s=t;t<r>>1;){var a=this.getLeftChildIndex_(t),h=this.getRightChildIndex_(t),l=h<r&&i[h]<i[a]?h:a;e[t]=e[l],i[t]=i[l],t=l}e[t]=n,i[t]=o,this.siftDown_(s,t)},qo.prototype.siftDown_=function(t,e){for(var i=this.elements_,r=this.priorities_,n=i[e],o=r[e];t<e;){var s=this.getParentIndex_(e);if(!(r[s]>o))break;i[e]=i[s],r[e]=r[s],e=s}i[e]=n,r[e]=o},qo.prototype.reprioritize=function(){var t,e,i,r=this.priorityFunction_,n=this.elements_,o=this.priorities_,s=0,a=n.length;for(e=0;e<a;++e)(i=r(t=n[e]))==1/0?delete this.queuedElements_[this.keyFunction_(t)]:(o[s]=i,n[s++]=t);n.length=s,o.length=s,this.heapify_()};var Jo=function(i){function t(e,t){i.call(this,function(t){return e.apply(null,t)},function(t){return t[0].getKey()}),this.tileChangeCallback_=t,this.tilesLoading_=0,this.tilesLoadingKeys_={}}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.enqueue=function(t){var e=i.prototype.enqueue.call(this,t);e&&E(t[0],w.CHANGE,this.handleTileChange,this);return e},t.prototype.getTilesLoading=function(){return this.tilesLoading_},t.prototype.handleTileChange=function(t){var e=t.target,i=e.getState();if(i===Gn||i===kn||i===Dn||i===jn){d(e,w.CHANGE,this.handleTileChange,this);var r=e.getKey();r in this.tilesLoadingKeys_&&(delete this.tilesLoadingKeys_[r],--this.tilesLoading_),this.tileChangeCallback_()}},t.prototype.loadMoreTiles=function(t,e){for(var i,r,n,o=0,s=!1;this.tilesLoading_<t&&o<e&&0<this.getCount();)n=(r=this.dequeue()[0]).getKey(),(i=r.getState())===jn?s=!0:i!==Nn||n in this.tilesLoadingKeys_||(this.tilesLoadingKeys_[n]=!0,++this.tilesLoading_,++o,r.load());0===o&&s&&this.tileChangeCallback_()},t}(qo),Qo=42,$o=256;function ts(t){return t}function es(t,e){return void 0!==t?0:void 0}function is(t,e){return void 0!==t?t+e:void 0}var rs={ANIMATING:0,INTERACTING:1},ns="center",os="resolution",ss="rotation",as=function(i){function t(t){i.call(this);var e=C({},t);this.hints_=[0,0],this.animations_=[],this.updateAnimationKey_,this.updateAnimations_=this.updateAnimations_.bind(this),this.projection_=ae(e.projection,"EPSG:3857"),this.applyOptions_(e)}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.applyOptions_=function(t){var e={};e[ns]=void 0!==t.center?t.center:null;var i=function(t){var e,i,r,n=void 0!==t.minZoom?t.minZoom:0,o=void 0!==t.maxZoom?t.maxZoom:28,s=void 0!==t.zoomFactor?t.zoomFactor:2;if(void 0!==t.resolutions){var a=t.resolutions;i=a[n],r=void 0!==a[o]?a[o]:a[a.length-1],g=a,e=function(t,e,i){if(void 0!==t){var r=ur(g,t,i);r=gt(r+e,0,g.length-1);var n=Math.floor(r);if(r!=n&&n<g.length-1){var o=g[n]/g[n+1];return g[n]/Math.pow(o,r-n)}return g[n]}}}else{var h=ae(t.projection,"EPSG:3857"),l=h.getExtent(),u=l?Math.max(ct(l),at(l)):360*Nt[Ot.DEGREES]/h.getMetersPerUnit(),c=u/$o/Math.pow(2,0),p=c/Math.pow(2,28);void 0!==(i=t.maxResolution)?n=0:i=c/Math.pow(s,n),void 0===(r=t.minResolution)&&(r=void 0!==t.maxZoom?void 0!==t.maxResolution?i/Math.pow(s,o):c/Math.pow(s,o):p),o=n+Math.floor(Math.log(i/r)/Math.log(s)),r=i/Math.pow(s,o-n),d=s,f=i,_=o-n,e=function(t,e,i){if(void 0!==t){var r=-i/2+.5,n=Math.floor(Math.log(f/t)/Math.log(d)+r),o=Math.max(n+e,0);return void 0!==_&&(o=Math.min(o,_)),f/Math.pow(d,o)}}}var d,f,_;var g;return{constraint:e,maxResolution:i,minResolution:r,minZoom:n,zoomFactor:s}}(t);this.maxResolution_=i.maxResolution,this.minResolution_=i.minResolution,this.zoomFactor_=i.zoomFactor,this.resolutions_=t.resolutions,this.minZoom_=i.minZoom;var r,n,o=void 0!==(r=t).extent?(n=r.extent,function(t){return t?[gt(t[0],n[0],n[2]),gt(t[1],n[1],n[3])]:void 0}):ts,s=i.constraint,a=function(t){{if(void 0===t.enableRotation||t.enableRotation){var e=t.constrainRotation;return void 0===e||!0===e?(o=n||St(5),function(t,e){return void 0!==t?Math.abs(t+e)<=o?0:t+e:void 0}):!1===e?is:"number"==typeof e?(i=e,r=2*Math.PI/i,function(t,e){return void 0!==t?t=Math.floor((t+e)/r+.5)*r:void 0}):is}return es}var i,r;var n,o}(t);this.constraints_={center:o,resolution:s,rotation:a},void 0!==t.resolution?e[os]=t.resolution:void 0!==t.zoom&&(e[os]=this.constrainResolution(this.maxResolution_,t.zoom-this.minZoom_),this.resolutions_&&(e[os]=gt(Number(this.getResolution()||e[os]),this.minResolution_,this.maxResolution_))),e[ss]=void 0!==t.rotation?t.rotation:0,this.setProperties(e),this.options_=t},t.prototype.getUpdatedOptions_=function(t){var e=C({},this.options_);return void 0!==e.resolution?e.resolution=this.getResolution():e.zoom=this.getZoom(),e.center=this.getCenter(),e.rotation=this.getRotation(),C({},e,t)},t.prototype.animate=function(t){var e,i=arguments,r=arguments.length;if(1<r&&"function"==typeof arguments[r-1]&&(e=arguments[r-1],--r),!this.isDef()){var n=arguments[r-1];return n.center&&this.setCenter(n.center),void 0!==n.zoom&&this.setZoom(n.zoom),void 0!==n.rotation&&this.setRotation(n.rotation),void(e&&setTimeout(function(){e(!0)},0))}for(var o=Date.now(),s=this.getCenter().slice(),a=this.getResolution(),h=this.getRotation(),l=[],u=0;u<r;++u){var c=i[u],p={start:o,complete:!1,anchor:c.anchor,duration:void 0!==c.duration?c.duration:1e3,easing:c.easing||Bn};if(c.center&&(p.sourceCenter=s,p.targetCenter=c.center,s=p.targetCenter),void 0!==c.zoom?(p.sourceResolution=a,p.targetResolution=this.constrainResolution(this.maxResolution_,c.zoom-this.minZoom_,0),a=p.targetResolution):c.resolution&&(p.sourceResolution=a,p.targetResolution=c.resolution,a=p.targetResolution),void 0!==c.rotation){p.sourceRotation=h;var d=Ct(c.rotation-h+Math.PI,2*Math.PI)-Math.PI;p.targetRotation=h+d,h=p.targetRotation}p.callback=e,hs(p)?p.complete=!0:o+=p.duration,l.push(p)}this.animations_.push(l),this.setHint(rs.ANIMATING,1),this.updateAnimations_()},t.prototype.getAnimating=function(){return 0<this.hints_[rs.ANIMATING]},t.prototype.getInteracting=function(){return 0<this.hints_[rs.INTERACTING]},t.prototype.cancelAnimations=function(){this.setHint(rs.ANIMATING,-this.hints_[rs.ANIMATING]);for(var t=0,e=this.animations_.length;t<e;++t){var i=this.animations_[t];i[0].callback&&i[0].callback(!1)}this.animations_.length=0},t.prototype.updateAnimations_=function(){var t=this;if(void 0!==this.updateAnimationKey_&&(cancelAnimationFrame(this.updateAnimationKey_),this.updateAnimationKey_=void 0),this.getAnimating()){for(var e=Date.now(),i=!1,r=this.animations_.length-1;0<=r;--r){for(var n=t.animations_[r],o=!0,s=0,a=n.length;s<a;++s){var h=n[s];if(!h.complete){var l=e-h.start,u=0<h.duration?l/h.duration:1;1<=u?(h.complete=!0,u=1):o=!1;var c=h.easing(u);if(h.sourceCenter){var p=h.sourceCenter[0],d=h.sourceCenter[1],f=p+c*(h.targetCenter[0]-p),_=d+c*(h.targetCenter[1]-d);t.set(ns,[f,_])}if(h.sourceResolution&&h.targetResolution){var g=1===c?h.targetResolution:h.sourceResolution+c*(h.targetResolution-h.sourceResolution);h.anchor&&t.set(ns,t.calculateCenterZoom(g,h.anchor)),t.set(os,g)}if(void 0!==h.sourceRotation&&void 0!==h.targetRotation){var y=1===c?Ct(h.targetRotation+Math.PI,2*Math.PI)-Math.PI:h.sourceRotation+c*(h.targetRotation-h.sourceRotation);h.anchor&&t.set(ns,t.calculateCenterRotate(y,h.anchor)),t.set(ss,y)}if(i=!0,!h.complete)break}}if(o){t.animations_[r]=null,t.setHint(rs.ANIMATING,-1);var v=n[0].callback;v&&setTimeout(function(){v(!0)},0)}}this.animations_=this.animations_.filter(Boolean),i&&void 0===this.updateAnimationKey_&&(this.updateAnimationKey_=requestAnimationFrame(this.updateAnimations_))}},t.prototype.calculateCenterRotate=function(t,e){var i,r=this.getCenter();return void 0!==r&&(pn(i=[r[0]-e[0],r[1]-e[1]],t-this.getRotation()),an(i,e)),i},t.prototype.calculateCenterZoom=function(t,e){var i,r=this.getCenter(),n=this.getResolution();void 0!==r&&void 0!==n&&(i=[e[0]-t*(e[0]-r[0])/n,e[1]-t*(e[1]-r[1])/n]);return i},t.prototype.getSizeFromViewport_=function(){var t=[100,100],e='.ol-viewport[data-view="'+Et(this)+'"]',i=document.querySelector(e);if(i){var r=getComputedStyle(i);t[0]=parseInt(r.width,10),t[1]=parseInt(r.height,10)}return t},t.prototype.constrainCenter=function(t){return this.constraints_.center(t)},t.prototype.constrainResolution=function(t,e,i){var r=e||0,n=i||0;return this.constraints_.resolution(t,r,n)},t.prototype.constrainRotation=function(t,e){var i=e||0;return this.constraints_.rotation(t,i)},t.prototype.getCenter=function(){return this.get(ns)},t.prototype.getConstraints=function(){return this.constraints_},t.prototype.getHints=function(t){return void 0!==t?(t[0]=this.hints_[0],t[1]=this.hints_[1],t):this.hints_.slice()},t.prototype.calculateExtent=function(t){var e=t||this.getSizeFromViewport_(),i=this.getCenter();Z(i,1);var r=this.getResolution();Z(void 0!==r,2);var n=this.getRotation();return Z(void 0!==n,3),st(i,r,n,e)},t.prototype.getMaxResolution=function(){return this.maxResolution_},t.prototype.getMinResolution=function(){return this.minResolution_},t.prototype.getMaxZoom=function(){return this.getZoomForResolution(this.minResolution_)},t.prototype.setMaxZoom=function(t){this.applyOptions_(this.getUpdatedOptions_({maxZoom:t}))},t.prototype.getMinZoom=function(){return this.getZoomForResolution(this.maxResolution_)},t.prototype.setMinZoom=function(t){this.applyOptions_(this.getUpdatedOptions_({minZoom:t}))},t.prototype.getProjection=function(){return this.projection_},t.prototype.getResolution=function(){return this.get(os)},t.prototype.getResolutions=function(){return this.resolutions_},t.prototype.getResolutionForExtent=function(t,e){var i=e||this.getSizeFromViewport_(),r=ct(t)/i[0],n=at(t)/i[1];return Math.max(r,n)},t.prototype.getResolutionForValueFunction=function(t){var e=t||2,i=this.maxResolution_,r=this.minResolution_,n=Math.log(i/r)/Math.log(e);return function(t){return i/Math.pow(e,t*n)}},t.prototype.getRotation=function(){return this.get(ss)},t.prototype.getValueForResolutionFunction=function(t){var e=t||2,i=this.maxResolution_,r=this.minResolution_,n=Math.log(i/r)/Math.log(e);return function(t){return Math.log(i/t)/Math.log(e)/n}},t.prototype.getState=function(){var t=this.getCenter(),e=this.getProjection(),i=this.getResolution(),r=this.getRotation();return{center:t.slice(),projection:void 0!==e?e:null,resolution:i,rotation:r,zoom:this.getZoom()}},t.prototype.getZoom=function(){var t,e=this.getResolution();return void 0!==e&&(t=this.getZoomForResolution(e)),t},t.prototype.getZoomForResolution=function(t){var e,i,r=this.minZoom_||0;if(this.resolutions_){var n=ur(this.resolutions_,t,1);r=n,e=this.resolutions_[n],i=n==this.resolutions_.length-1?2:e/this.resolutions_[n+1]}else e=this.maxResolution_,i=this.zoomFactor_;return r+Math.log(e/t)/Math.log(i)},t.prototype.getResolutionForZoom=function(t){return this.constrainResolution(this.maxResolution_,t-this.minZoom_,0)},t.prototype.fit=function(t,e){var i,r=e||{},n=r.size;n||(n=this.getSizeFromViewport_()),t instanceof vr?t.getType()===Lt.CIRCLE?(i=tn(t=t.getExtent())).rotate(this.getRotation(),ot(t)):i=t:(Z(Array.isArray(t),24),Z(!pt(t),25),i=tn(t));var o,s=void 0!==r.padding?r.padding:[0,0,0,0],a=void 0===r.constrainResolution||r.constrainResolution,h=void 0!==r.nearest&&r.nearest;o=void 0!==r.minResolution?r.minResolution:void 0!==r.maxZoom?this.constrainResolution(this.maxResolution_,r.maxZoom-this.minZoom_,0):0;for(var l=i.getFlatCoordinates(),u=this.getRotation(),c=Math.cos(-u),p=Math.sin(-u),d=1/0,f=1/0,_=-1/0,g=-1/0,y=i.getStride(),v=0,m=l.length;v<m;v+=y){var x=l[v]*c-l[v+1]*p,S=l[v]*p+l[v+1]*c;d=Math.min(d,x),f=Math.min(f,S),_=Math.max(_,x),g=Math.max(g,S)}var C=this.getResolutionForExtent([d,f,_,g],[n[0]-s[1]-s[3],n[1]-s[0]-s[2]]);if(C=isNaN(C)?o:Math.max(C,o),a){var E=this.constrainResolution(C,0,0);!h&&E<C&&(E=this.constrainResolution(E,-1,0)),C=E}p=-p;var T=(d+_)/2,w=(f+g)/2,R=[(T+=(s[1]-s[3])/2*C)*c-(w+=(s[0]-s[2])/2*C)*p,w*c+T*p],I=r.callback?r.callback:L;void 0!==r.duration?this.animate({resolution:C,center:R,duration:r.duration,easing:r.easing},I):(this.setResolution(C),this.setCenter(R),setTimeout(I.bind(void 0,!0),0))},t.prototype.centerOn=function(t,e,i){var r=this.getRotation(),n=Math.cos(-r),o=Math.sin(-r),s=t[0]*n-t[1]*o,a=t[1]*n+t[0]*o,h=this.getResolution(),l=(s+=(e[0]/2-i[0])*h)*n-(a+=(i[1]-e[1]/2)*h)*(o=-o),u=a*n+s*o;this.setCenter([l,u])},t.prototype.isDef=function(){return!!this.getCenter()&&void 0!==this.getResolution()},t.prototype.rotate=function(t,e){if(void 0!==e){var i=this.calculateCenterRotate(t,e);this.setCenter(i)}this.setRotation(t)},t.prototype.setCenter=function(t){this.set(ns,t),this.getAnimating()&&this.cancelAnimations()},t.prototype.setHint=function(t,e){return this.hints_[t]+=e,this.changed(),this.hints_[t]},t.prototype.setResolution=function(t){this.set(os,t),this.getAnimating()&&this.cancelAnimations()},t.prototype.setRotation=function(t){this.set(ss,t),this.getAnimating()&&this.cancelAnimations()},t.prototype.setZoom=function(t){this.setResolution(this.getResolutionForZoom(t))},t}(R);function hs(t){return!(t.sourceCenter&&t.targetCenter&&!cn(t.sourceCenter,t.targetCenter))&&(t.sourceResolution===t.targetResolution&&t.sourceRotation===t.targetRotation)}var ls="opacity",us="visible",cs="extent",ps="zIndex",ds="maxResolution",fs="minResolution",_s="source",gs=function(i){function t(t){i.call(this);var e=C({},t);e[ls]=void 0!==t.opacity?t.opacity:1,e[us]=void 0===t.visible||t.visible,e[ps]=void 0!==t.zIndex?t.zIndex:0,e[ds]=void 0!==t.maxResolution?t.maxResolution:1/0,e[fs]=void 0!==t.minResolution?t.minResolution:0,this.setProperties(e),this.state_={layer:this,managed:!0},this.type}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.getType=function(){return this.type},t.prototype.getLayerState=function(){return this.state_.opacity=gt(this.getOpacity(),0,1),this.state_.sourceState=this.getSourceState(),this.state_.visible=this.getVisible(),this.state_.extent=this.getExtent(),this.state_.zIndex=this.getZIndex(),this.state_.maxResolution=this.getMaxResolution(),this.state_.minResolution=Math.max(this.getMinResolution(),0),this.state_},t.prototype.getLayersArray=function(t){},t.prototype.getLayerStatesArray=function(t){},t.prototype.getExtent=function(){return this.get(cs)},t.prototype.getMaxResolution=function(){return this.get(ds)},t.prototype.getMinResolution=function(){return this.get(fs)},t.prototype.getOpacity=function(){return this.get(ls)},t.prototype.getSourceState=function(){},t.prototype.getVisible=function(){return this.get(us)},t.prototype.getZIndex=function(){return this.get(ps)},t.prototype.setExtent=function(t){this.set(cs,t)},t.prototype.setMaxResolution=function(t){this.set(ds,t)},t.prototype.setMinResolution=function(t){this.set(fs,t)},t.prototype.setOpacity=function(t){this.set(ls,t)},t.prototype.setVisible=function(t){this.set(us,t)},t.prototype.setZIndex=function(t){this.set(ps,t)},t}(R),ys="undefined",vs="loading",ms="ready",xs="error",Ss="layers",Cs=function(n){function t(t){var e=t||{},i=C({},e);delete i.layers;var r=e.layers;n.call(this,i),this.layersListenerKeys_=[],this.listenerKeys_={},E(this,b(Ss),this.handleLayersChanged_,this),r?Array.isArray(r)?r=new M(r.slice(),{unique:!0}):(Z(r instanceof M,43),r=r):r=new M(void 0,{unique:!0}),this.setLayers(r)}return n&&(t.__proto__=n),((t.prototype=Object.create(n&&n.prototype)).constructor=t).prototype.handleLayerChange_=function(){this.changed()},t.prototype.handleLayersChanged_=function(){this.layersListenerKeys_.forEach(g),this.layersListenerKeys_.length=0;var t=this.getLayers();for(var e in this.layersListenerKeys_.push(E(t,h,this.handleLayersAdd_,this),E(t,l,this.handleLayersRemove_,this)),this.listenerKeys_)this.listenerKeys_[e].forEach(g);_(this.listenerKeys_);for(var i=t.getArray(),r=0,n=i.length;r<n;r++){var o=i[r];this.listenerKeys_[Et(o).toString()]=[E(o,a,this.handleLayerChange_,this),E(o,w.CHANGE,this.handleLayerChange_,this)]}this.changed()},t.prototype.handleLayersAdd_=function(t){var e=t.element,i=Et(e).toString();this.listenerKeys_[i]=[E(e,a,this.handleLayerChange_,this),E(e,w.CHANGE,this.handleLayerChange_,this)],this.changed()},t.prototype.handleLayersRemove_=function(t){var e=Et(t.element).toString();this.listenerKeys_[e].forEach(g),delete this.listenerKeys_[e],this.changed()},t.prototype.getLayers=function(){return this.get(Ss)},t.prototype.setLayers=function(t){this.set(Ss,t)},t.prototype.getLayersArray=function(t){var e=void 0!==t?t:[];return this.getLayers().forEach(function(t){t.getLayersArray(e)}),e},t.prototype.getLayerStatesArray=function(t){var e=void 0!==t?t:[],i=e.length;this.getLayers().forEach(function(t){t.getLayerStatesArray(e)});for(var r=this.getLayerState(),n=i,o=e.length;n<o;n++){var s=e[n];s.opacity*=r.opacity,s.visible=s.visible&&r.visible,s.maxResolution=Math.min(s.maxResolution,r.maxResolution),s.minResolution=Math.max(s.minResolution,r.minResolution),void 0!==r.extent&&(void 0!==s.extent?s.extent=ht(s.extent,r.extent):s.extent=r.extent)}return e},t.prototype.getSourceState=function(){return ms},t}(gs);function Es(t,e,i){return void 0===i&&(i=[0,0]),i[0]=t[0]+2*e,i[1]=t[1]+2*e,i}function Ts(t,e,i){return void 0===i&&(i=[0,0]),i[0]=t[0]*e+.5|0,i[1]=t[1]*e+.5|0,i}function ws(t,e){return Array.isArray(t)?t:(void 0===e?e=[t,t]:e[0]=e[1]=t,e)}var Rs=function(s){function t(t){s.call(this);var e=function(t){var e=null;void 0!==t.keyboardEventTarget&&(e="string"==typeof t.keyboardEventTarget?document.getElementById(t.keyboardEventTarget):t.keyboardEventTarget);var i,r,n,o={},s=t.layers instanceof Cs?t.layers:new Cs({layers:t.layers});o[Zo.LAYERGROUP]=s,o[Zo.TARGET]=t.target,o[Zo.VIEW]=void 0!==t.view?t.view:new as,void 0!==t.controls&&(Array.isArray(t.controls)?i=new M(t.controls.slice()):(Z(t.controls instanceof M,47),i=t.controls));void 0!==t.interactions&&(Array.isArray(t.interactions)?r=new M(t.interactions.slice()):(Z(t.interactions instanceof M,48),r=t.interactions));void 0!==t.overlays?Array.isArray(t.overlays)?n=new M(t.overlays.slice()):(Z(t.overlays instanceof M,49),n=t.overlays):n=new M;return{controls:i,interactions:r,keyboardEventTarget:e,overlays:n,values:o}}(t);this.maxTilesLoading_=void 0!==t.maxTilesLoading?t.maxTilesLoading:16,this.loadTilesWhileAnimating_=void 0!==t.loadTilesWhileAnimating&&t.loadTilesWhileAnimating,this.loadTilesWhileInteracting_=void 0!==t.loadTilesWhileInteracting&&t.loadTilesWhileInteracting,this.pixelRatio_=void 0!==t.pixelRatio?t.pixelRatio:ai,this.animationDelayKey_,this.animationDelay_=function(){this.animationDelayKey_=void 0,this.renderFrame_.call(this,Date.now())}.bind(this),this.coordinateToPixelTransform_=[1,0,0,1,0,0],this.pixelToCoordinateTransform_=[1,0,0,1,0,0],this.frameIndex_=0,this.frameState_=null,this.previousExtent_=null,this.viewPropertyListenerKey_=null,this.viewChangeListenerKey_=null,this.layerGroupPropertyListenerKeys_=null,this.viewport_=document.createElement("DIV"),this.viewport_.className="ol-viewport"+(ui?" ol-touch":""),this.viewport_.style.position="relative",this.viewport_.style.overflow="hidden",this.viewport_.style.width="100%",this.viewport_.style.height="100%",this.viewport_.style.msTouchAction="none",this.viewport_.style.touchAction="none",this.overlayContainer_=document.createElement("DIV"),this.overlayContainer_.className="ol-overlaycontainer",this.viewport_.appendChild(this.overlayContainer_),this.overlayContainerStopEvent_=document.createElement("DIV"),this.overlayContainerStopEvent_.className="ol-overlaycontainer-stopevent";for(var i=[w.CLICK,w.DBLCLICK,w.MOUSEDOWN,w.TOUCHSTART,w.MSPOINTERDOWN,qn.POINTERDOWN,w.MOUSEWHEEL,w.WHEEL],r=0,n=i.length;r<n;++r)E(this.overlayContainerStopEvent_,i[r],x);for(var o in this.viewport_.appendChild(this.overlayContainerStopEvent_),this.mapBrowserEventHandler_=new Vo(this,t.moveTolerance),qn)E(this.mapBrowserEventHandler_,qn[o],this.handleMapBrowserEvent,this);this.keyboardEventTarget_=e.keyboardEventTarget,this.keyHandlerKeys_=null,E(this.viewport_,w.CONTEXTMENU,this.handleBrowserEvent,this),E(this.viewport_,w.WHEEL,this.handleBrowserEvent,this),E(this.viewport_,w.MOUSEWHEEL,this.handleBrowserEvent,this),this.controls=e.controls||new M,this.interactions=e.interactions||new M,this.overlays_=e.overlays,this.overlayIdIndex_={},this.renderer_=this.createRenderer(),this.handleResize_,this.focus_=null,this.postRenderFunctions_=[],this.tileQueue_=new Jo(this.getTilePriority.bind(this),this.handleTileChange_.bind(this)),this.skippedFeatureUids_={},E(this,b(Zo.LAYERGROUP),this.handleLayerGroupChanged_,this),E(this,b(Zo.VIEW),this.handleViewChanged_,this),E(this,b(Zo.SIZE),this.handleSizeChanged_,this),E(this,b(Zo.TARGET),this.handleTargetChanged_,this),this.setProperties(e.values),this.controls.forEach(function(t){t.setMap(this)}.bind(this)),E(this.controls,h,function(t){t.element.setMap(this)},this),E(this.controls,l,function(t){t.element.setMap(null)},this),this.interactions.forEach(function(t){t.setMap(this)}.bind(this)),E(this.interactions,h,function(t){t.element.setMap(this)},this),E(this.interactions,l,function(t){t.element.setMap(null)},this),this.overlays_.forEach(this.addOverlayInternal_.bind(this)),E(this.overlays_,h,function(t){this.addOverlayInternal_(t.element)},this),E(this.overlays_,l,function(t){var e=t.element.getId();void 0!==e&&delete this.overlayIdIndex_[e.toString()],t.element.setMap(null)},this)}return s&&(t.__proto__=s),((t.prototype=Object.create(s&&s.prototype)).constructor=t).prototype.createRenderer=function(){throw new Error("Use a map type that has a createRenderer method")},t.prototype.addControl=function(t){this.getControls().push(t)},t.prototype.addInteraction=function(t){this.getInteractions().push(t)},t.prototype.addLayer=function(t){this.getLayerGroup().getLayers().push(t)},t.prototype.addOverlay=function(t){this.getOverlays().push(t)},t.prototype.addOverlayInternal_=function(t){var e=t.getId();void 0!==e&&(this.overlayIdIndex_[e.toString()]=t),t.setMap(this)},t.prototype.disposeInternal=function(){this.mapBrowserEventHandler_.dispose(),d(this.viewport_,w.CONTEXTMENU,this.handleBrowserEvent,this),d(this.viewport_,w.WHEEL,this.handleBrowserEvent,this),d(this.viewport_,w.MOUSEWHEEL,this.handleBrowserEvent,this),void 0!==this.handleResize_&&(removeEventListener(w.RESIZE,this.handleResize_,!1),this.handleResize_=void 0),this.animationDelayKey_&&(cancelAnimationFrame(this.animationDelayKey_),this.animationDelayKey_=void 0),this.setTarget(null),s.prototype.disposeInternal.call(this)},t.prototype.forEachFeatureAtPixel=function(t,e,i){if(this.frameState_){var r=this.getCoordinateFromPixel(t),n=void 0!==(i=void 0!==i?i:{}).hitTolerance?i.hitTolerance*this.frameState_.pixelRatio:0,o=void 0!==i.layerFilter?i.layerFilter:y;return this.renderer_.forEachFeatureAtCoordinate(r,this.frameState_,n,e,null,o,null)}},t.prototype.getFeaturesAtPixel=function(t,e){var i=null;return this.forEachFeatureAtPixel(t,function(t){i||(i=[]),i.push(t)},e),i},t.prototype.forEachLayerAtPixel=function(t,e,i){if(this.frameState_){var r=i||{},n=void 0!==r.hitTolerance?i.hitTolerance*this.frameState_.pixelRatio:0,o=r.layerFilter||y;return this.renderer_.forEachLayerAtPixel(t,this.frameState_,n,e,null,o,null)}},t.prototype.hasFeatureAtPixel=function(t,e){if(!this.frameState_)return!1;var i=this.getCoordinateFromPixel(t),r=void 0!==(e=void 0!==e?e:{}).layerFilter?e.layerFilter:y,n=void 0!==e.hitTolerance?e.hitTolerance*this.frameState_.pixelRatio:0;return this.renderer_.hasFeatureAtCoordinate(i,this.frameState_,n,r,null)},t.prototype.getEventCoordinate=function(t){return this.getCoordinateFromPixel(this.getEventPixel(t))},t.prototype.getEventPixel=function(t){var e=this.viewport_.getBoundingClientRect(),i=t.changedTouches?t.changedTouches[0]:t;return[i.clientX-e.left,i.clientY-e.top]},t.prototype.getTarget=function(){return this.get(Zo.TARGET)},t.prototype.getTargetElement=function(){var t=this.getTarget();return void 0!==t?"string"==typeof t?document.getElementById(t):t:null},t.prototype.getCoordinateFromPixel=function(t){var e=this.frameState_;return e?xe(e.pixelToCoordinateTransform,t.slice()):null},t.prototype.getControls=function(){return this.controls},t.prototype.getOverlays=function(){return this.overlays_},t.prototype.getOverlayById=function(t){var e=this.overlayIdIndex_[t.toString()];return void 0!==e?e:null},t.prototype.getInteractions=function(){return this.interactions},t.prototype.getLayerGroup=function(){return this.get(Zo.LAYERGROUP)},t.prototype.getLayers=function(){return this.getLayerGroup().getLayers()},t.prototype.getPixelFromCoordinate=function(t){var e=this.frameState_;return e?xe(e.coordinateToPixelTransform,t.slice(0,2)):null},t.prototype.getRenderer=function(){return this.renderer_},t.prototype.getSize=function(){return this.get(Zo.SIZE)},t.prototype.getView=function(){return this.get(Zo.VIEW)},t.prototype.getViewport=function(){return this.viewport_},t.prototype.getOverlayContainer=function(){return this.overlayContainer_},t.prototype.getOverlayContainerStopEvent=function(){return this.overlayContainerStopEvent_},t.prototype.getTilePriority=function(t,e,i,r){var n=this.frameState_;if(!(n&&e in n.wantedTiles))return 1/0;if(!n.wantedTiles[e][t.getKey()])return 1/0;var o=i[0]-n.focus[0],s=i[1]-n.focus[1];return 65536*Math.log(r)+Math.sqrt(o*o+s*s)/r},t.prototype.handleBrowserEvent=function(t,e){var i=e||t.type,r=new Zn(i,this,t);this.handleMapBrowserEvent(r)},t.prototype.handleMapBrowserEvent=function(t){if(this.frameState_){this.focus_=t.coordinate,t.frameState=this.frameState_;var e=this.getInteractions().getArray();if(!1!==this.dispatchEvent(t))for(var i=e.length-1;0<=i;i--){var r=e[i];if(r.getActive())if(!r.handleEvent(t))break}}},t.prototype.handlePostRender=function(){var t=this.frameState_,e=this.tileQueue_;if(!e.isEmpty()){var i=this.maxTilesLoading_,r=i;if(t){var n=t.viewHints;n[rs.ANIMATING]&&(i=this.loadTilesWhileAnimating_?8:0,r=2),n[rs.INTERACTING]&&(i=this.loadTilesWhileInteracting_?8:0,r=2)}e.getTilesLoading()<i&&(e.reprioritize(),e.loadMoreTiles(i,r))}for(var o=this.postRenderFunctions_,s=0,a=o.length;s<a;++s)o[s](this,t);o.length=0},t.prototype.handleSizeChanged_=function(){this.render()},t.prototype.handleTargetChanged_=function(){var t;if(this.getTarget()&&(t=this.getTargetElement()),this.keyHandlerKeys_){for(var e=0,i=this.keyHandlerKeys_.length;e<i;++e)g(this.keyHandlerKeys_[e]);this.keyHandlerKeys_=null}if(t){t.appendChild(this.viewport_);var r=this.keyboardEventTarget_?this.keyboardEventTarget_:t;this.keyHandlerKeys_=[E(r,w.KEYDOWN,this.handleBrowserEvent,this),E(r,w.KEYPRESS,this.handleBrowserEvent,this)],this.handleResize_||(this.handleResize_=this.updateSize.bind(this),addEventListener(w.RESIZE,this.handleResize_,!1))}else this.renderer_.removeLayerRenderers(),Ue(this.viewport_),void 0!==this.handleResize_&&(removeEventListener(w.RESIZE,this.handleResize_,!1),this.handleResize_=void 0);this.updateSize()},t.prototype.handleTileChange_=function(){this.render()},t.prototype.handleViewPropertyChanged_=function(){this.render()},t.prototype.handleViewChanged_=function(){this.viewPropertyListenerKey_&&(g(this.viewPropertyListenerKey_),this.viewPropertyListenerKey_=null),this.viewChangeListenerKey_&&(g(this.viewChangeListenerKey_),this.viewChangeListenerKey_=null);var t=this.getView();t&&(this.viewport_.setAttribute("data-view",Et(t)),this.viewPropertyListenerKey_=E(t,a,this.handleViewPropertyChanged_,this),this.viewChangeListenerKey_=E(t,w.CHANGE,this.handleViewPropertyChanged_,this)),this.render()},t.prototype.handleLayerGroupChanged_=function(){this.layerGroupPropertyListenerKeys_&&(this.layerGroupPropertyListenerKeys_.forEach(g),this.layerGroupPropertyListenerKeys_=null);var t=this.getLayerGroup();t&&(this.layerGroupPropertyListenerKeys_=[E(t,a,this.render,this),E(t,w.CHANGE,this.render,this)]),this.render()},t.prototype.isRendered=function(){return!!this.frameState_},t.prototype.renderSync=function(){this.animationDelayKey_&&cancelAnimationFrame(this.animationDelayKey_),this.animationDelay_()},t.prototype.render=function(){void 0===this.animationDelayKey_&&(this.animationDelayKey_=requestAnimationFrame(this.animationDelay_))},t.prototype.removeControl=function(t){return this.getControls().remove(t)},t.prototype.removeInteraction=function(t){return this.getInteractions().remove(t)},t.prototype.removeLayer=function(t){return this.getLayerGroup().getLayers().remove(t)},t.prototype.removeOverlay=function(t){return this.getOverlays().remove(t)},t.prototype.renderFrame_=function(t){var e,i,r=this.getSize(),n=this.getView(),o=[1/0,1/0,-1/0,-1/0],s=this.frameState_,a=null;if(void 0!==r&&(0<(i=r)[0]&&0<i[1])&&n&&n.isDef()){for(var h=n.getHints(this.frameState_?this.frameState_.viewHints:void 0),l=this.getLayerGroup().getLayerStatesArray(),u={},c=0,p=l.length;c<p;++c)u[Et(l[c].layer)]=l[c];e=n.getState();var d=this.focus_;if(!d){d=e.center;var f=e.resolution/this.pixelRatio_;d[0]=Math.round(d[0]/f)*f,d[1]=Math.round(d[1]/f)*f}a={animate:!1,coordinateToPixelTransform:this.coordinateToPixelTransform_,extent:o,focus:d,index:this.frameIndex_++,layerStates:u,layerStatesArray:l,pixelRatio:this.pixelRatio_,pixelToCoordinateTransform:this.pixelToCoordinateTransform_,postRenderFunctions:[],size:r,skippedFeatureUids:this.skippedFeatureUids_,tileQueue:this.tileQueue_,time:t,usedTiles:{},viewState:e,viewHints:h,wantedTiles:{}}}if(a&&(a.extent=st(e.center,e.resolution,e.rotation,a.size,o)),this.frameState_=a,this.renderer_.renderFrame(a),a){if(a.animate&&this.render(),Array.prototype.push.apply(this.postRenderFunctions_,a.postRenderFunctions),s)(!this.previousExtent_||!pt(this.previousExtent_)&&!$(a.extent,this.previousExtent_))&&(this.dispatchEvent(new Hn(Ko,this,s)),this.previousExtent_=z(this.previousExtent_));this.previousExtent_&&!a.viewHints[rs.ANIMATING]&&!a.viewHints[rs.INTERACTING]&&!$(a.extent,this.previousExtent_)&&(this.dispatchEvent(new Hn(Ho,this,a)),k(a.extent,this.previousExtent_))}this.dispatchEvent(new Hn(Wo,this,a)),setTimeout(this.handlePostRender.bind(this),0)},t.prototype.setLayerGroup=function(t){this.set(Zo.LAYERGROUP,t)},t.prototype.setSize=function(t){this.set(Zo.SIZE,t)},t.prototype.setTarget=function(t){this.set(Zo.TARGET,t)},t.prototype.setView=function(t){this.set(Zo.VIEW,t)},t.prototype.skipFeature=function(t){var e=Et(t).toString();this.skippedFeatureUids_[e]=!0,this.render()},t.prototype.updateSize=function(){var t=this.getTargetElement();if(t){var e=getComputedStyle(t);this.setSize([t.offsetWidth-parseFloat(e.borderLeftWidth)-parseFloat(e.paddingLeft)-parseFloat(e.paddingRight)-parseFloat(e.borderRightWidth),t.offsetHeight-parseFloat(e.borderTopWidth)-parseFloat(e.paddingTop)-parseFloat(e.paddingBottom)-parseFloat(e.borderBottomWidth)])}else this.setSize(void 0)},t.prototype.unskipFeature=function(t){var e=Et(t).toString();delete this.skippedFeatureUids_[e],this.render()},t}(R);var Is=function(e){function t(t){e.call(this),this.element=t.element?t.element:null,this.target_=null,this.map_=null,this.listenerKeys=[],this.render=t.render?t.render:L,t.target&&this.setTarget(t.target)}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.disposeInternal=function(){Ue(this.element),e.prototype.disposeInternal.call(this)},t.prototype.getMap=function(){return this.map_},t.prototype.setMap=function(t){this.map_&&Ue(this.element);for(var e=0,i=this.listenerKeys.length;e<i;++e)g(this.listenerKeys[e]);(this.listenerKeys.length=0,this.map_=t,this.map_)&&((this.target_?this.target_:t.getOverlayContainerStopEvent()).appendChild(this.element),this.render!==L&&this.listenerKeys.push(E(t,Wo,this.render,this)),t.render())},t.prototype.setTarget=function(t){this.target_="string"==typeof t?document.getElementById(t):t},t}(R),Ls=function(r){function t(t){var e=C({},t);delete e.source,r.call(this,e),this.mapPrecomposeKey_=null,this.mapRenderKey_=null,this.sourceChangeKey_=null,t.map&&this.setMap(t.map),E(this,b(_s),this.handleSourcePropertyChange_,this);var i=t.source?t.source:null;this.setSource(i)}return r&&(t.__proto__=r),((t.prototype=Object.create(r&&r.prototype)).constructor=t).prototype.getLayersArray=function(t){var e=t||[];return e.push(this),e},t.prototype.getLayerStatesArray=function(t){var e=t||[];return e.push(this.getLayerState()),e},t.prototype.getSource=function(){return this.get(_s)||null},t.prototype.getSourceState=function(){var t=this.getSource();return t?t.getState():ys},t.prototype.handleSourceChange_=function(){this.changed()},t.prototype.handleSourcePropertyChange_=function(){this.sourceChangeKey_&&(g(this.sourceChangeKey_),this.sourceChangeKey_=null);var t=this.getSource();t&&(this.sourceChangeKey_=E(t,w.CHANGE,this.handleSourceChange_,this)),this.changed()},t.prototype.setMap=function(t){this.mapPrecomposeKey_&&(g(this.mapPrecomposeKey_),this.mapPrecomposeKey_=null),t||this.changed(),this.mapRenderKey_&&(g(this.mapRenderKey_),this.mapRenderKey_=null),t&&(this.mapPrecomposeKey_=E(t,Tn,function(t){var e=this.getLayerState();e.managed=!1,e.zIndex=1/0,t.frameState.layerStatesArray.push(e),t.frameState.layerStates[Et(this)]=e},this),this.mapRenderKey_=E(this,w.CHANGE,t.render,t),this.changed())},t.prototype.setSource=function(t){this.set(_s,t)},t}(gs);function bs(t,e){return t.visible&&e>=t.minResolution&&e<t.maxResolution}var Ps=function(u){function t(t){var e=t||{};u.call(this,{element:document.createElement("div"),render:e.render||Fs,target:e.target}),this.ulElement_=document.createElement("UL"),this.collapsed_=void 0===e.collapsed||e.collapsed,this.collapsible_=void 0===e.collapsible||e.collapsible,this.collapsible_||(this.collapsed_=!1);var i=void 0!==e.className?e.className:"ol-attribution",r=void 0!==e.tipLabel?e.tipLabel:"Attributions",n=void 0!==e.collapseLabel?e.collapseLabel:"»";"string"==typeof n?(this.collapseLabel_=document.createElement("span"),this.collapseLabel_.textContent=n):this.collapseLabel_=n;var o=void 0!==e.label?e.label:"i";"string"==typeof o?(this.label_=document.createElement("span"),this.label_.textContent=o):this.label_=o;var s=this.collapsible_&&!this.collapsed_?this.collapseLabel_:this.label_,a=document.createElement("button");a.setAttribute("type","button"),a.title=r,a.appendChild(s),E(a,w.CLICK,this.handleClick_,this);var h=i+" "+_i+" "+gi+(this.collapsed_&&this.collapsible_?" "+yi:"")+(this.collapsible_?"":" ol-uncollapsible"),l=this.element;l.className=h,l.appendChild(this.ulElement_),l.appendChild(a),this.renderedAttributions_=[],this.renderedVisible_=!0}return u&&(t.__proto__=u),((t.prototype=Object.create(u&&u.prototype)).constructor=t).prototype.getSourceAttributions_=function(t){for(var e={},i=[],r=t.layerStatesArray,n=t.viewState.resolution,o=0,s=r.length;o<s;++o){var a=r[o];if(bs(a,n)){var h=a.layer.getSource();if(h){var l=h.getAttributions();if(l){var u=l(t);if(u)if(Array.isArray(u))for(var c=0,p=u.length;c<p;++c)u[c]in e||(i.push(u[c]),e[u[c]]=!0);else u in e||(i.push(u),e[u]=!0)}}}}return i},t.prototype.updateElement_=function(t){if(t){var e=this.getSourceAttributions_(t),i=0<e.length;if(this.renderedVisible_!=i&&(this.element.style.display=i?"":"none",this.renderedVisible_=i),!fr(e,this.renderedAttributions_)){Ye(this.ulElement_);for(var r=0,n=e.length;r<n;++r){var o=document.createElement("LI");o.innerHTML=e[r],this.ulElement_.appendChild(o)}this.renderedAttributions_=e}}else this.renderedVisible_&&(this.element.style.display="none",this.renderedVisible_=!1)},t.prototype.handleClick_=function(t){t.preventDefault(),this.handleToggle_()},t.prototype.handleToggle_=function(){this.element.classList.toggle(yi),this.collapsed_?je(this.collapseLabel_,this.label_):je(this.label_,this.collapseLabel_),this.collapsed_=!this.collapsed_},t.prototype.getCollapsible=function(){return this.collapsible_},t.prototype.setCollapsible=function(t){this.collapsible_!==t&&(this.collapsible_=t,this.element.classList.toggle("ol-uncollapsible"),!t&&this.collapsed_&&this.handleToggle_())},t.prototype.setCollapsed=function(t){this.collapsible_&&this.collapsed_!==t&&this.handleToggle_()},t.prototype.getCollapsed=function(){return this.collapsed_},t}(Is);function Fs(t){this.updateElement_(t.frameState)}var Ms=function(h){function t(t){var e=t||{};h.call(this,{element:document.createElement("div"),render:e.render||Os,target:e.target});var i=void 0!==e.className?e.className:"ol-rotate",r=void 0!==e.label?e.label:"⇧";this.label_=null,"string"==typeof r?(this.label_=document.createElement("span"),this.label_.className="ol-compass",this.label_.textContent=r):(this.label_=r,this.label_.classList.add("ol-compass"));var n=e.tipLabel?e.tipLabel:"Reset rotation",o=document.createElement("button");o.className=i+"-reset",o.setAttribute("type","button"),o.title=n,o.appendChild(this.label_),E(o,w.CLICK,this.handleClick_,this);var s=i+" "+_i+" "+gi,a=this.element;a.className=s,a.appendChild(o),this.callResetNorth_=e.resetNorth?e.resetNorth:void 0,this.duration_=void 0!==e.duration?e.duration:250,this.autoHide_=void 0===e.autoHide||e.autoHide,this.rotation_=void 0,this.autoHide_&&this.element.classList.add(fi)}return h&&(t.__proto__=h),((t.prototype=Object.create(h&&h.prototype)).constructor=t).prototype.handleClick_=function(t){t.preventDefault(),void 0!==this.callResetNorth_?this.callResetNorth_():this.resetNorth_()},t.prototype.resetNorth_=function(){var t=this.getMap().getView();t&&void 0!==t.getRotation()&&(0<this.duration_?t.animate({rotation:0,duration:this.duration_,easing:Yn}):t.setRotation(0))},t}(Is);function Os(t){var e=t.frameState;if(e){var i=e.viewState.rotation;if(i!=this.rotation_){var r="rotate("+i+"rad)";if(this.autoHide_){var n=this.element.classList.contains(fi);n||0!==i?n&&0!==i&&this.element.classList.remove(fi):this.element.classList.add(fi)}this.label_.style.msTransform=r,this.label_.style.webkitTransform=r,this.label_.style.transform=r}this.rotation_=i}}var Ns=function(p){function t(t){var e=t||{};p.call(this,{element:document.createElement("div"),target:e.target});var i=void 0!==e.className?e.className:"ol-zoom",r=void 0!==e.delta?e.delta:1,n=void 0!==e.zoomInLabel?e.zoomInLabel:"+",o=void 0!==e.zoomOutLabel?e.zoomOutLabel:"−",s=void 0!==e.zoomInTipLabel?e.zoomInTipLabel:"Zoom in",a=void 0!==e.zoomOutTipLabel?e.zoomOutTipLabel:"Zoom out",h=document.createElement("button");h.className=i+"-in",h.setAttribute("type","button"),h.title=s,h.appendChild("string"==typeof n?document.createTextNode(n):n),E(h,w.CLICK,this.handleClick_.bind(this,r));var l=document.createElement("button");l.className=i+"-out",l.setAttribute("type","button"),l.title=a,l.appendChild("string"==typeof o?document.createTextNode(o):o),E(l,w.CLICK,this.handleClick_.bind(this,-r));var u=i+" "+_i+" "+gi,c=this.element;c.className=u,c.appendChild(h),c.appendChild(l),this.duration_=void 0!==e.duration?e.duration:250}return p&&(t.__proto__=p),((t.prototype=Object.create(p&&p.prototype)).constructor=t).prototype.handleClick_=function(t,e){e.preventDefault(),this.zoomByDelta_(t)},t.prototype.zoomByDelta_=function(t){var e=this.getMap().getView();if(e){var i=e.getResolution();if(i){var r=e.constrainResolution(i,t);0<this.duration_?(e.getAnimating()&&e.cancelAnimations(),e.animate({resolution:r,duration:this.duration_,easing:Yn})):e.setResolution(r)}}},t}(Is);function As(t){var e=t||{},i=new M;return(void 0===e.zoom||e.zoom)&&i.push(new Ns(e.zoomOptions)),(void 0===e.rotate||e.rotate)&&i.push(new Ms(e.rotateOptions)),(void 0===e.attribution||e.attribution)&&i.push(new Ps(e.attributionOptions)),i}var Gs="active",ks=function(e){function t(t){e.call(this),this.map_=null,this.setActive(!0),this.handleEvent=t.handleEvent}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.getActive=function(){return this.get(Gs)},t.prototype.getMap=function(){return this.map_},t.prototype.setActive=function(t){this.set(Gs,t)},t.prototype.setMap=function(t){this.map_=t},t}(R);function Ds(t,e,i,r){js(t,e=t.constrainRotation(e,0),i,r)}function js(t,e,i,r){if(void 0!==e){var n=t.getRotation(),o=t.getCenter();void 0!==n&&o&&0<r?t.animate({rotation:e,anchor:i,duration:r,easing:Yn}):t.rotate(e,i)}}function Us(t,e,i,r,n){Bs(t,e=t.constrainResolution(e,0,n),i,r)}function Ys(t,e,i,r){var n=t.getResolution(),o=t.constrainResolution(n,e,0);if(void 0!==o){var s=t.getResolutions();o=gt(o,t.getMinResolution()||s[s.length-1],t.getMaxResolution()||s[0])}if(i&&void 0!==o&&o!==n){var a=t.getCenter(),h=t.calculateCenterZoom(o,i);h=t.constrainCenter(h),i=[(o*a[0]-n*h[0])/(o-n),(o*a[1]-n*h[1])/(o-n)]}Bs(t,o,i,r)}function Bs(t,e,i,r){if(e){var n=t.getResolution(),o=t.getCenter();if(void 0!==n&&o&&e!==n&&r)t.animate({resolution:e,anchor:i,duration:r,easing:Yn});else{if(i){var s=t.calculateCenterZoom(e,i);t.setCenter(s)}t.setResolution(e)}}}var Xs=function(i){function t(t){i.call(this,{handleEvent:zs});var e=t||{};this.delta_=e.delta?e.delta:1,this.duration_=void 0!==e.duration?e.duration:250}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(ks);function zs(t){var e=!1,i=t.originalEvent;if(t.type==qn.DBLCLICK){var r=t.map,n=t.coordinate,o=i.shiftKey?-this.delta_:this.delta_;Ys(r.getView(),o,n,this.duration_),t.preventDefault(),e=!0}return!e}var Vs=function(t){var e=t.originalEvent;return e.altKey&&!(e.metaKey||e.ctrlKey)&&!e.shiftKey},Ws=function(t){var e=t.originalEvent;return e.altKey&&!(e.metaKey||e.ctrlKey)&&e.shiftKey},Ks=y,Hs=function(t){var e=t.originalEvent;return 0==e.button&&!(oi&&si&&e.ctrlKey)},Zs=v,qs=function(t){return"pointermove"==t.type},Js=function(t){return t.type==qn.SINGLECLICK},Qs=function(t){var e=t.originalEvent;return!e.altKey&&!(e.metaKey||e.ctrlKey)&&!e.shiftKey},$s=function(t){var e=t.originalEvent;return!e.altKey&&!(e.metaKey||e.ctrlKey)&&e.shiftKey},ta=function(t){var e=t.originalEvent.target.tagName;return"INPUT"!==e&&"SELECT"!==e&&"TEXTAREA"!==e},ea=function(t){return Z(t.pointerEvent,56),"mouse"==t.pointerEvent.pointerType},ia=function(t){var e=t.pointerEvent;return e.isPrimary&&0===e.button},ra=L,na=v,oa=v,sa=L,aa=function(i){function t(t){var e=t||{};i.call(this,{handleEvent:e.handleEvent||la}),this.handleDownEvent_=e.handleDownEvent?e.handleDownEvent:oa,this.handleDragEvent_=e.handleDragEvent?e.handleDragEvent:ra,this.handleMoveEvent_=e.handleMoveEvent?e.handleMoveEvent:sa,this.handleUpEvent_=e.handleUpEvent?e.handleUpEvent:na,this.handlingDownUpSequence=!1,this.stopDown=e.stopDown?e.stopDown:ua,this.trackedPointers_={},this.targetPointers=[]}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.updateTrackedPointers_=function(t){if((r=t.type)===qn.POINTERDOWN||r===qn.POINTERDRAG||r===qn.POINTERUP){var e=t.pointerEvent,i=e.pointerId.toString();t.type==qn.POINTERUP?delete this.trackedPointers_[i]:t.type==qn.POINTERDOWN?this.trackedPointers_[i]=e:i in this.trackedPointers_&&(this.trackedPointers_[i]=e),this.targetPointers=o(this.trackedPointers_)}var r},t}(ks);function ha(t){for(var e=t.length,i=0,r=0,n=0;n<e;n++)i+=t[n].clientX,r+=t[n].clientY;return[i/e,r/e]}function la(t){if(!(t instanceof Jn))return!0;var e=!1;if(this.updateTrackedPointers_(t),this.handlingDownUpSequence){if(t.type==qn.POINTERDRAG)this.handleDragEvent_(t);else if(t.type==qn.POINTERUP){var i=this.handleUpEvent_(t);this.handlingDownUpSequence=i&&0<this.targetPointers.length}}else if(t.type==qn.POINTERDOWN){var r=this.handleDownEvent_(t);this.handlingDownUpSequence=r,e=this.stopDown(r)}else t.type==qn.POINTERMOVE&&this.handleMoveEvent_(t);return!e}function ua(t){return t}var ca=function(i){function t(t){i.call(this,{handleDownEvent:fa,handleDragEvent:pa,handleUpEvent:da,stopDown:v});var e=t||{};this.kinetic_=e.kinetic,this.lastCentroid=null,this.lastPointersCount_,this.condition_=e.condition?e.condition:Qs,this.noKinetic_=!1}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(aa);function pa(t){var e=this.targetPointers,i=ha(e);if(e.length==this.lastPointersCount_){if(this.kinetic_&&this.kinetic_.update(i[0],i[1]),this.lastCentroid){var r=this.lastCentroid[0]-i[0],n=i[1]-this.lastCentroid[1],o=t.map.getView(),s=[r,n];dn(s,o.getResolution()),pn(s,o.getRotation()),an(s,o.getCenter()),s=o.constrainCenter(s),o.setCenter(s)}}else this.kinetic_&&this.kinetic_.begin();this.lastCentroid=i,this.lastPointersCount_=e.length}function da(t){var e=t.map,i=e.getView();if(0===this.targetPointers.length){if(!this.noKinetic_&&this.kinetic_&&this.kinetic_.end()){var r=this.kinetic_.getDistance(),n=this.kinetic_.getAngle(),o=i.getCenter(),s=e.getPixelFromCoordinate(o),a=e.getCoordinateFromPixel([s[0]-r*Math.cos(n),s[1]-r*Math.sin(n)]);i.animate({center:i.constrainCenter(a),duration:500,easing:Yn})}return i.setHint(rs.INTERACTING,-1),!1}return this.kinetic_&&this.kinetic_.begin(),!(this.lastCentroid=null)}function fa(t){if(0<this.targetPointers.length&&this.condition_(t)){var e=t.map.getView();return this.lastCentroid=null,this.handlingDownUpSequence||e.setHint(rs.INTERACTING,1),e.getAnimating()&&e.setCenter(t.frameState.viewState.center),this.kinetic_&&this.kinetic_.begin(),this.noKinetic_=1<this.targetPointers.length,!0}return!1}var _a=function(i){function t(t){var e=t||{};i.call(this,{handleDownEvent:va,handleDragEvent:ga,handleUpEvent:ya,stopDown:v}),this.condition_=e.condition?e.condition:Ws,this.lastAngle_=void 0,this.duration_=void 0!==e.duration?e.duration:250}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(aa);function ga(t){if(ea(t)){var e=t.map,i=e.getView();if(i.getConstraints().rotation!==es){var r=e.getSize(),n=t.pixel,o=Math.atan2(r[1]/2-n[1],n[0]-r[0]/2);if(void 0!==this.lastAngle_){var s=o-this.lastAngle_;js(i,i.getRotation()-s)}this.lastAngle_=o}}}function ya(t){if(!ea(t))return!0;var e=t.map.getView();return e.setHint(rs.INTERACTING,-1),Ds(e,e.getRotation(),void 0,this.duration_),!1}function va(t){return!!ea(t)&&(!(!Hs(t)||!this.condition_(t))&&(t.map.getView().setHint(rs.INTERACTING,1),!(this.lastAngle_=void 0)))}var ma=function(e){function t(t){e.call(this),this.geometry_=null,this.element_=document.createElement("div"),this.element_.style.position="absolute",this.element_.className="ol-box "+t,this.map_=null,this.startPixel_=null,this.endPixel_=null}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.disposeInternal=function(){this.setMap(null)},t.prototype.render_=function(){var t=this.startPixel_,e=this.endPixel_,i=this.element_.style;i.left=Math.min(t[0],e[0])+"px",i.top=Math.min(t[1],e[1])+"px",i.width=Math.abs(e[0]-t[0])+"px",i.height=Math.abs(e[1]-t[1])+"px"},t.prototype.setMap=function(t){if(this.map_){this.map_.getOverlayContainer().removeChild(this.element_);var e=this.element_.style;e.left=e.top=e.width=e.height="inherit"}this.map_=t,this.map_&&this.map_.getOverlayContainer().appendChild(this.element_)},t.prototype.setPixels=function(t,e){this.startPixel_=t,this.endPixel_=e,this.createOrUpdateGeometry(),this.render_()},t.prototype.createOrUpdateGeometry=function(){var t=this.startPixel_,e=this.endPixel_,i=[t,[t[0],e[1]],e,[e[0],t[1]]].map(this.map_.getCoordinateFromPixel,this.map_);i[4]=i[0].slice(),this.geometry_?this.geometry_.setCoordinates([i]):this.geometry_=new Qr([i])},t.prototype.getGeometry=function(){return this.geometry_},t}(t),xa={BOXSTART:"boxstart",BOXDRAG:"boxdrag",BOXEND:"boxend"},Sa=function(r){function t(t,e,i){r.call(this,t),this.coordinate=e,this.mapBrowserEvent=i}return r&&(t.__proto__=r),(t.prototype=Object.create(r&&r.prototype)).constructor=t}(m),Ca=function(i){function t(t){i.call(this,{handleDownEvent:Ra,handleDragEvent:Ta,handleUpEvent:wa});var e=t||{};this.box_=new ma(e.className||"ol-dragbox"),this.minArea_=void 0!==e.minArea?e.minArea:64,this.onBoxEnd_=e.onBoxEnd?e.onBoxEnd:L,this.startPixel_=null,this.condition_=e.condition?e.condition:Ks,this.boxEndCondition_=e.boxEndCondition?e.boxEndCondition:Ea}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.getGeometry=function(){return this.box_.getGeometry()},t}(aa);function Ea(t,e,i){var r=i[0]-e[0],n=i[1]-e[1];return r*r+n*n>=this.minArea_}function Ta(t){ea(t)&&(this.box_.setPixels(this.startPixel_,t.pixel),this.dispatchEvent(new Sa(xa.BOXDRAG,t.coordinate,t)))}function wa(t){return!ea(t)||(this.box_.setMap(null),this.boxEndCondition_(t,this.startPixel_,t.pixel)&&(this.onBoxEnd_(t),this.dispatchEvent(new Sa(xa.BOXEND,t.coordinate,t))),!1)}function Ra(t){return!!ea(t)&&(!(!Hs(t)||!this.condition_(t))&&(this.startPixel_=t.pixel,this.box_.setMap(t.map),this.box_.setPixels(this.startPixel_,this.startPixel_),this.dispatchEvent(new Sa(xa.BOXSTART,t.coordinate,t)),!0))}var Ia=function(r){function t(t){var e=t||{},i=e.condition?e.condition:$s;r.call(this,{condition:i,className:e.className||"ol-dragzoom",onBoxEnd:La}),this.duration_=void 0!==e.duration?e.duration:200,this.out_=void 0!==e.out&&e.out}return r&&(t.__proto__=r),(t.prototype=Object.create(r&&r.prototype)).constructor=t}(Ca);function La(){var t=this.getMap(),e=t.getView(),i=t.getSize(),r=this.getGeometry().getExtent();if(this.out_){var n=e.calculateExtent(i),o=W([t.getPixelFromCoordinate(rt(r)),t.getPixelFromCoordinate(ut(r))]);dt(n,1/e.getResolutionForExtent(o,i)),r=n}var s=e.constrainResolution(e.getResolutionForExtent(r,i)),a=ot(r);a=e.constrainCenter(a),e.animate({resolution:s,center:a,duration:this.duration_,easing:Yn})}var ba={LEFT:37,UP:38,RIGHT:39,DOWN:40},Pa=function(i){function t(t){i.call(this,{handleEvent:Fa});var e=t||{};this.defaultCondition_=function(t){return Qs(t)&&ta(t)},this.condition_=void 0!==e.condition?e.condition:this.defaultCondition_,this.duration_=void 0!==e.duration?e.duration:100,this.pixelDelta_=void 0!==e.pixelDelta?e.pixelDelta:128}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(ks);function Fa(t){var e=!1;if(t.type==w.KEYDOWN){var i=t.originalEvent.keyCode;if(this.condition_(t)&&(i==ba.DOWN||i==ba.LEFT||i==ba.RIGHT||i==ba.UP)){var r=t.map.getView(),n=r.getResolution()*this.pixelDelta_,o=0,s=0;i==ba.DOWN?s=-n:i==ba.LEFT?o=-n:i==ba.RIGHT?o=n:s=n;var a=[o,s];pn(a,r.getRotation()),function(t,e,i){var r=t.getCenter();if(r){var n=t.constrainCenter([r[0]+e[0],r[1]+e[1]]);i?t.animate({duration:i,easing:Xn,center:n}):t.setCenter(n)}}(r,a,this.duration_),t.preventDefault(),e=!0}}return!e}var Ma=function(i){function t(t){i.call(this,{handleEvent:Oa});var e=t||{};this.condition_=e.condition?e.condition:ta,this.delta_=e.delta?e.delta:1,this.duration_=void 0!==e.duration?e.duration:100}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(ks);function Oa(t){var e=!1;if(t.type==w.KEYDOWN||t.type==w.KEYPRESS){var i=t.originalEvent.charCode;if(this.condition_(t)&&(i=="+".charCodeAt(0)||i=="-".charCodeAt(0))){var r=t.map,n=i=="+".charCodeAt(0)?this.delta_:-this.delta_;Ys(r.getView(),n,void 0,this.duration_),t.preventDefault(),e=!0}}return!e}var Na={TRACKPAD:"trackpad",WHEEL:"wheel"},Aa=function(i){function t(t){i.call(this,{handleEvent:Ga});var e=t||{};this.delta_=0,this.duration_=void 0!==e.duration?e.duration:250,this.timeout_=void 0!==e.timeout?e.timeout:80,this.useAnchor_=void 0===e.useAnchor||e.useAnchor,this.constrainResolution_=e.constrainResolution||!1,this.condition_=e.condition?e.condition:Ks,this.lastAnchor_=null,this.startTime_=void 0,this.timeoutId_=void 0,this.mode_=void 0,this.trackpadEventGap_=400,this.trackpadTimeoutId_=void 0,this.trackpadDeltaPerZoom_=300,this.trackpadZoomBuffer_=1.5}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.decrementInteractingHint_=function(){this.trackpadTimeoutId_=void 0,this.getMap().getView().setHint(rs.INTERACTING,-1)},t.prototype.handleWheelZoom_=function(t){var e=t.getView();e.getAnimating()&&e.cancelAnimations();Ys(e,-gt(this.delta_,-1,1),this.lastAnchor_,this.duration_),this.mode_=void 0,this.delta_=0,this.lastAnchor_=null,this.startTime_=void 0,this.timeoutId_=void 0},t.prototype.setMouseAnchor=function(t){(this.useAnchor_=t)||(this.lastAnchor_=null)},t}(ks);function Ga(t){if(!this.condition_(t))return!0;var e=t.type;if(e!==w.WHEEL&&e!==w.MOUSEWHEEL)return!0;t.preventDefault();var i,r=t.map,n=t.originalEvent;if(this.useAnchor_&&(this.lastAnchor_=t.coordinate),t.type==w.WHEEL?(i=n.deltaY,ri&&n.deltaMode===WheelEvent.DOM_DELTA_PIXEL&&(i/=ai),n.deltaMode===WheelEvent.DOM_DELTA_LINE&&(i*=40)):t.type==w.MOUSEWHEEL&&(i=-n.wheelDeltaY,ni&&(i/=3)),0===i)return!1;var o=Date.now();if(void 0===this.startTime_&&(this.startTime_=o),(!this.mode_||o-this.startTime_>this.trackpadEventGap_)&&(this.mode_=Math.abs(i)<4?Na.TRACKPAD:Na.WHEEL),this.mode_===Na.TRACKPAD){var s=r.getView();this.trackpadTimeoutId_?clearTimeout(this.trackpadTimeoutId_):s.setHint(rs.INTERACTING,1),this.trackpadTimeoutId_=setTimeout(this.decrementInteractingHint_.bind(this),this.trackpadEventGap_);var a=s.getResolution()*Math.pow(2,i/this.trackpadDeltaPerZoom_),h=s.getMinResolution(),l=s.getMaxResolution(),u=0;if(a<h?(a=Math.max(a,h/this.trackpadZoomBuffer_),u=1):l<a&&(a=Math.min(a,l*this.trackpadZoomBuffer_),u=-1),this.lastAnchor_){var c=s.calculateCenterZoom(a,this.lastAnchor_);s.setCenter(s.constrainCenter(c))}return s.setResolution(a),0===u&&this.constrainResolution_&&s.animate({resolution:s.constrainResolution(a,0<i?-1:1),easing:Yn,anchor:this.lastAnchor_,duration:this.duration_}),0<u?s.animate({resolution:h,easing:Yn,anchor:this.lastAnchor_,duration:500}):u<0&&s.animate({resolution:l,easing:Yn,anchor:this.lastAnchor_,duration:500}),this.startTime_=o,!1}this.delta_+=i;var p=Math.max(this.timeout_-(o-this.startTime_),0);return clearTimeout(this.timeoutId_),this.timeoutId_=setTimeout(this.handleWheelZoom_.bind(this,r),p),!1}var ka=function(i){function t(t){i.call(this,{handleDownEvent:Ua,handleDragEvent:Da,handleUpEvent:ja,stopDown:v});var e=t||{};this.anchor_=null,this.lastAngle_=void 0,this.rotating_=!1,this.rotationDelta_=0,this.threshold_=void 0!==e.threshold?e.threshold:.3,this.duration_=void 0!==e.duration?e.duration:250}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(aa);function Da(t){var e=0,i=this.targetPointers[0],r=this.targetPointers[1],n=Math.atan2(r.clientY-i.clientY,r.clientX-i.clientX);if(void 0!==this.lastAngle_){var o=n-this.lastAngle_;this.rotationDelta_+=o,!this.rotating_&&Math.abs(this.rotationDelta_)>this.threshold_&&(this.rotating_=!0),e=o}this.lastAngle_=n;var s=t.map,a=s.getView();if(a.getConstraints().rotation!==es){var h=s.getViewport().getBoundingClientRect(),l=ha(this.targetPointers);if(l[0]-=h.left,l[1]-=h.top,this.anchor_=s.getCoordinateFromPixel(l),this.rotating_){var u=a.getRotation();s.render(),js(a,u+e,this.anchor_)}}}function ja(t){if(this.targetPointers.length<2){var e=t.map.getView();if(e.setHint(rs.INTERACTING,-1),this.rotating_)Ds(e,e.getRotation(),this.anchor_,this.duration_);return!1}return!0}function Ua(t){if(2<=this.targetPointers.length){var e=t.map;return this.anchor_=null,this.lastAngle_=void 0,this.rotating_=!1,this.rotationDelta_=0,this.handlingDownUpSequence||e.getView().setHint(rs.INTERACTING,1),!0}return!1}var Ya=function(i){function t(t){i.call(this,{handleDownEvent:za,handleDragEvent:Ba,handleUpEvent:Xa,stopDown:v});var e=t||{};this.constrainResolution_=e.constrainResolution||!1,this.anchor_=null,this.duration_=void 0!==e.duration?e.duration:400,this.lastDistance_=void 0,this.lastScaleDelta_=1}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(aa);function Ba(t){var e=1,i=this.targetPointers[0],r=this.targetPointers[1],n=i.clientX-r.clientX,o=i.clientY-r.clientY,s=Math.sqrt(n*n+o*o);void 0!==this.lastDistance_&&(e=this.lastDistance_/s),this.lastDistance_=s;var a=t.map,h=a.getView(),l=h.getResolution(),u=h.getMaxResolution(),c=h.getMinResolution(),p=l*e;u<p?(e=u/l,p=u):p<c&&(e=c/l,p=c),1!=e&&(this.lastScaleDelta_=e);var d=a.getViewport().getBoundingClientRect(),f=ha(this.targetPointers);f[0]-=d.left,f[1]-=d.top,this.anchor_=a.getCoordinateFromPixel(f),a.render(),Bs(h,p,this.anchor_)}function Xa(t){if(this.targetPointers.length<2){var e=t.map.getView();e.setHint(rs.INTERACTING,-1);var i=e.getResolution();if(this.constrainResolution_||i<e.getMinResolution()||i>e.getMaxResolution()){var r=this.lastScaleDelta_-1;Us(e,i,this.anchor_,this.duration_,r)}return!1}return!0}function za(t){if(2<=this.targetPointers.length){var e=t.map;return this.anchor_=null,this.lastDistance_=void 0,this.lastScaleDelta_=1,this.handlingDownUpSequence||e.getView().setHint(rs.INTERACTING,1),!0}return!1}var Va="addfeatures",Wa=function(n){function t(t,e,i,r){n.call(this,t),this.features=i,this.file=e,this.projection=r}return n&&(t.__proto__=n),(t.prototype=Object.create(n&&n.prototype)).constructor=t}(m),Ka=function(i){function t(t){var e=t||{};i.call(this,{handleEvent:y}),this.formatConstructors_=e.formatConstructors?e.formatConstructors:[],this.projection_=e.projection?ne(e.projection):null,this.dropListenKeys_=null,this.source_=e.source||null,this.target=e.target?e.target:null}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.handleResult_=function(t,e){var i=e.target.result,r=this.getMap(),n=this.projection_;n||(n=r.getView().getProjection());for(var o=this.formatConstructors_,s=[],a=0,h=o.length;a<h;++a){var l=new o[a];if((s=this.tryReadFeatures_(l,i,{featureProjection:n}))&&0<s.length)break}this.source_&&(this.source_.clear(),this.source_.addFeatures(s)),this.dispatchEvent(new Wa(Va,t,s,n))},t.prototype.registerListeners_=function(){var t=this.getMap();if(t){var e=this.target?this.target:t.getViewport();this.dropListenKeys_=[E(e,w.DROP,Ha,this),E(e,w.DRAGENTER,Za,this),E(e,w.DRAGOVER,Za,this),E(e,w.DROP,Za,this)]}},t.prototype.setActive=function(t){i.prototype.setActive.call(this,t),t?this.registerListeners_():this.unregisterListeners_()},t.prototype.setMap=function(t){this.unregisterListeners_(),i.prototype.setMap.call(this,t),this.getActive()&&this.registerListeners_()},t.prototype.tryReadFeatures_=function(t,e,i){try{return t.readFeatures(e,i)}catch(t){return null}},t.prototype.unregisterListeners_=function(){this.dropListenKeys_&&(this.dropListenKeys_.forEach(g),this.dropListenKeys_=null)},t}(ks);function Ha(t){for(var e=t.dataTransfer.files,i=0,r=e.length;i<r;++i){var n=e.item(i),o=new FileReader;o.addEventListener(w.LOAD,this.handleResult_.bind(this,n)),o.readAsText(n)}}function Za(t){t.stopPropagation(),t.preventDefault(),t.dataTransfer.dropEffect="copy"}var qa=function(i){function t(t){var e=t||{};i.call(this,{handleDownEvent:$a,handleDragEvent:Ja,handleUpEvent:Qa}),this.condition_=e.condition?e.condition:$s,this.lastAngle_=void 0,this.lastMagnitude_=void 0,this.lastScaleDelta_=0,this.duration_=void 0!==e.duration?e.duration:400}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(aa);function Ja(t){if(ea(t)){var e=t.map,i=e.getSize(),r=t.pixel,n=r[0]-i[0]/2,o=i[1]/2-r[1],s=Math.atan2(o,n),a=Math.sqrt(n*n+o*o),h=e.getView();if(h.getConstraints().rotation!==es&&void 0!==this.lastAngle_){var l=s-this.lastAngle_;js(h,h.getRotation()-l)}if(this.lastAngle_=s,void 0!==this.lastMagnitude_)Bs(h,this.lastMagnitude_*(h.getResolution()/a));void 0!==this.lastMagnitude_&&(this.lastScaleDelta_=this.lastMagnitude_/a),this.lastMagnitude_=a}}function Qa(t){if(!ea(t))return!0;var e=t.map.getView();e.setHint(rs.INTERACTING,-1);var i=this.lastScaleDelta_-1;return Ds(e,e.getRotation()),Us(e,e.getResolution(),void 0,this.duration_,i),this.lastScaleDelta_=0,!1}function $a(t){return!!ea(t)&&(!!this.condition_(t)&&(t.map.getView().setHint(rs.INTERACTING,1),this.lastAngle_=void 0,!(this.lastMagnitude_=void 0)))}var th=function(n){function t(t,e,i){if(n.call(this),void 0!==i&&void 0===e)this.setFlatCoordinates(i,t);else{var r=e||0;this.setCenterAndRadius(t,r,i)}}return n&&(t.__proto__=n),((t.prototype=Object.create(n&&n.prototype)).constructor=t).prototype.clone=function(){return new t(this.flatCoordinates.slice(),void 0,this.layout)},t.prototype.closestPointXY=function(t,e,i,r){var n=this.flatCoordinates,o=t-n[0],s=e-n[1],a=o*o+s*s;if(a<r){if(0===a)for(var h=0;h<this.stride;++h)i[h]=n[h];else{var l=this.getRadius()/Math.sqrt(a);i[0]=n[0]+l*o,i[1]=n[1]+l*s;for(var u=2;u<this.stride;++u)i[u]=n[u]}return i.length=this.stride,a}return r},t.prototype.containsXY=function(t,e){var i=this.flatCoordinates,r=t-i[0],n=e-i[1];return r*r+n*n<=this.getRadiusSquared_()},t.prototype.getCenter=function(){return this.flatCoordinates.slice(0,this.stride)},t.prototype.computeExtent=function(t){var e=this.flatCoordinates,i=e[this.stride]-e[0];return X(e[0]-i,e[1]-i,e[0]+i,e[1]+i,t)},t.prototype.getRadius=function(){return Math.sqrt(this.getRadiusSquared_())},t.prototype.getRadiusSquared_=function(){var t=this.flatCoordinates[this.stride]-this.flatCoordinates[0],e=this.flatCoordinates[this.stride+1]-this.flatCoordinates[1];return t*t+e*e},t.prototype.getType=function(){return Lt.CIRCLE},t.prototype.intersectsExtent=function(t){if(wt(t,this.getExtent())){var e=this.getCenter();return t[0]<=e[0]&&t[2]>=e[0]||(t[1]<=e[1]&&t[3]>=e[1]||et(t,this.intersectsCoordinate,this))}return!1},t.prototype.setCenter=function(t){var e=this.stride,i=this.flatCoordinates[e]-this.flatCoordinates[0],r=t.slice();r[e]=r[0]+i;for(var n=1;n<e;++n)r[e+n]=t[n];this.setFlatCoordinates(this.layout,r),this.changed()},t.prototype.setCenterAndRadius=function(t,e,i){this.setLayout(i,t,0),this.flatCoordinates||(this.flatCoordinates=[]);var r=this.flatCoordinates,n=Ir(r,0,t,this.stride);r[n++]=r[0]+e;for(var o=1,s=this.stride;o<s;++o)r[n++]=r[o];r.length=n,this.changed()},t.prototype.getCoordinates=function(){},t.prototype.setCoordinates=function(t,e){},t.prototype.setRadius=function(t){this.flatCoordinates[this.stride]=this.flatCoordinates[0]+t,this.changed()},t}(vr);th.prototype.transform;var eh=function(l){function r(t,e,i){if(l.call(this),this.ends_=[],this.maxDelta_=-1,this.maxDeltaRevision_=-1,Array.isArray(t[0]))this.setCoordinates(t,e);else if(void 0!==e&&i)this.setFlatCoordinates(e,t),this.ends_=i;else{for(var r=this.getLayout(),n=[],o=[],s=0,a=t.length;s<a;++s){var h=t[s];0===s&&(r=h.getLayout()),pr(n,h.getFlatCoordinates()),o.push(n.length)}this.setFlatCoordinates(r,n),this.ends_=o}}return l&&(r.__proto__=l),((r.prototype=Object.create(l&&l.prototype)).constructor=r).prototype.appendLineString=function(t){this.flatCoordinates?pr(this.flatCoordinates,t.getFlatCoordinates().slice()):this.flatCoordinates=t.getFlatCoordinates().slice(),this.ends_.push(this.flatCoordinates.length),this.changed()},r.prototype.clone=function(){return new r(this.flatCoordinates.slice(),this.layout,this.ends_.slice())},r.prototype.closestPointXY=function(t,e,i,r){return r<D(this.getExtent(),t,e)?r:(this.maxDeltaRevision_!=this.getRevision()&&(this.maxDelta_=Math.sqrt(Tr(this.flatCoordinates,0,this.ends_,this.stride,0)),this.maxDeltaRevision_=this.getRevision()),Rr(this.flatCoordinates,0,this.ends_,this.stride,this.maxDelta_,!1,t,e,i,r))},r.prototype.getCoordinateAtM=function(t,e,i){if(this.layout!=yr.XYM&&this.layout!=yr.XYZM||0===this.flatCoordinates.length)return null;var r=void 0!==e&&e,n=void 0!==i&&i;return function(t,e,i,r,n,o,s){if(s)return mn(t,e,i[i.length-1],r,n,o);var a;if(n<t[r-1])return o?((a=t.slice(0,r))[r-1]=n,a):null;if(t[t.length-1]<n)return o?((a=t.slice(t.length-r))[r-1]=n,a):null;for(var h=0,l=i.length;h<l;++h){var u=i[h];if(e!=u){if(n<t[e+r-1])return null;if(n<=t[u-1])return mn(t,e,u,r,n,!1);e=u}}return null}(this.flatCoordinates,0,this.ends_,this.stride,t,r,n)},r.prototype.getCoordinates=function(){return Fr(this.flatCoordinates,0,this.ends_,this.stride)},r.prototype.getEnds=function(){return this.ends_},r.prototype.getLineString=function(t){return t<0||this.ends_.length<=t?null:new Sn(this.flatCoordinates.slice(0===t?0:this.ends_[t-1],this.ends_[t]),this.layout)},r.prototype.getLineStrings=function(){for(var t=this.flatCoordinates,e=this.ends_,i=this.layout,r=[],n=0,o=0,s=e.length;o<s;++o){var a=e[o],h=new Sn(t.slice(n,a),i);r.push(h),n=a}return r},r.prototype.getFlatMidpoints=function(){for(var t=[],e=this.flatCoordinates,i=0,r=this.ends_,n=this.stride,o=0,s=r.length;o<s;++o){var a=r[o];pr(t,vn(e,i,a,n,.5)),i=a}return t},r.prototype.getSimplifiedGeometryInternal=function(t){var e=[],i=[];return e.length=function(t,e,i,r,n,o,s,a){for(var h=0,l=i.length;h<l;++h){var u=i[h];s=Or(t,e,u,r,n,o,s),a.push(s),e=u}return s}(this.flatCoordinates,0,this.ends_,this.stride,t,e,0,i),new r(e,yr.XY,i)},r.prototype.getType=function(){return Lt.MULTI_LINE_STRING},r.prototype.intersectsExtent=function(t){return function(t,e,i,r,n){for(var o=0,s=i.length;o<s;++o){if(Vr(t,e,i[o],r,n))return!0;e=i[o]}return!1}(this.flatCoordinates,0,this.ends_,this.stride,t)},r.prototype.setCoordinates=function(t,e){this.setLayout(e,t,2),this.flatCoordinates||(this.flatCoordinates=[]);var i=br(this.flatCoordinates,0,t,this.stride,this.ends_);this.flatCoordinates.length=0===i.length?0:i[i.length-1],this.changed()},r}(vr),ih=function(i){function t(t,e){i.call(this),e&&!Array.isArray(t[0])?this.setFlatCoordinates(e,t):this.setCoordinates(t,e)}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.appendPoint=function(t){this.flatCoordinates?pr(this.flatCoordinates,t.getFlatCoordinates()):this.flatCoordinates=t.getFlatCoordinates().slice(),this.changed()},t.prototype.clone=function(){return new t(this.flatCoordinates.slice(),this.layout)},t.prototype.closestPointXY=function(t,e,i,r){if(r<D(this.getExtent(),t,e))return r;for(var n=this.flatCoordinates,o=this.stride,s=0,a=n.length;s<a;s+=o){var h=mt(t,e,n[s],n[s+1]);if(h<r){r=h;for(var l=0;l<o;++l)i[l]=n[s+l];i.length=o}}return r},t.prototype.getCoordinates=function(){return Pr(this.flatCoordinates,0,this.flatCoordinates.length,this.stride)},t.prototype.getPoint=function(t){var e=this.flatCoordinates?this.flatCoordinates.length/this.stride:0;return t<0||e<=t?null:new Dr(this.flatCoordinates.slice(t*this.stride,(t+1)*this.stride),this.layout)},t.prototype.getPoints=function(){for(var t=this.flatCoordinates,e=this.layout,i=this.stride,r=[],n=0,o=t.length;n<o;n+=i){var s=new Dr(t.slice(n,n+i),e);r.push(s)}return r},t.prototype.getType=function(){return Lt.MULTI_POINT},t.prototype.intersectsExtent=function(t){for(var e=this.flatCoordinates,i=this.stride,r=0,n=e.length;r<n;r+=i){if(U(t,e[r],e[r+1]))return!0}return!1},t.prototype.setCoordinates=function(t,e){this.setLayout(e,t,1),this.flatCoordinates||(this.flatCoordinates=[]),this.flatCoordinates.length=Lr(this.flatCoordinates,0,t,this.stride),this.changed()},t}(vr);function rh(t,e,i,r){for(var n=[],o=[1/0,1/0,-1/0,-1/0],s=0,a=i.length;s<a;++s){var h=i[s];o=K(t,e,h[0],r),n.push((o[0]+o[2])/2,(o[1]+o[3])/2),e=h[h.length-1]}return n}var nh=function(d){function r(t,e,i){if(d.call(this),this.endss_=[],this.flatInteriorPointsRevision_=-1,this.flatInteriorPoints_=null,this.maxDelta_=-1,this.maxDeltaRevision_=-1,this.orientedRevision_=-1,this.orientedFlatCoordinates_=null,!i&&!Array.isArray(t[0])){for(var r=this.getLayout(),n=[],o=[],s=0,a=t.length;s<a;++s){var h=t[s];0===s&&(r=h.getLayout());for(var l=n.length,u=h.getEnds(),c=0,p=u.length;c<p;++c)u[c]+=l;pr(n,h.getFlatCoordinates()),o.push(u)}e=r,t=n,i=o}void 0!==e&&i?(this.setFlatCoordinates(e,t),this.endss_=i):this.setCoordinates(t,e)}return d&&(r.__proto__=d),((r.prototype=Object.create(d&&d.prototype)).constructor=r).prototype.appendPolygon=function(t){var e;if(this.flatCoordinates){var i=this.flatCoordinates.length;pr(this.flatCoordinates,t.getFlatCoordinates());for(var r=0,n=(e=t.getEnds().slice()).length;r<n;++r)e[r]+=i}else this.flatCoordinates=t.getFlatCoordinates().slice(),e=t.getEnds().slice(),this.endss_.push();this.endss_.push(e),this.changed()},r.prototype.clone=function(){for(var t=this.endss_.length,e=new Array(t),i=0;i<t;++i)e[i]=this.endss_[i].slice();return new r(this.flatCoordinates.slice(),this.layout,e)},r.prototype.closestPointXY=function(t,e,i,r){return r<D(this.getExtent(),t,e)?r:(this.maxDeltaRevision_!=this.getRevision()&&(this.maxDelta_=Math.sqrt(function(t,e,i,r,n){for(var o=0,s=i.length;o<s;++o){var a=i[o];n=Tr(t,e,a,r,n),e=a[a.length-1]}return n}(this.flatCoordinates,0,this.endss_,this.stride,0)),this.maxDeltaRevision_=this.getRevision()),function(t,e,i,r,n,o,s,a,h,l,u){for(var c=u||[NaN,NaN],p=0,d=i.length;p<d;++p){var f=i[p];l=Rr(t,e,f,r,n,o,s,a,h,l,c),e=f[f.length-1]}return l}(this.getOrientedFlatCoordinates(),0,this.endss_,this.stride,this.maxDelta_,!0,t,e,i,r))},r.prototype.containsXY=function(t,e){return function(t,e,i,r,n,o){if(0===i.length)return!1;for(var s=0,a=i.length;s<a;++s){var h=i[s];if(Yr(t,e,h,r,n,o))return!0;e=h[h.length-1]}return!1}(this.getOrientedFlatCoordinates(),0,this.endss_,this.stride,t,e)},r.prototype.getArea=function(){return function(t,e,i,r){for(var n=0,o=0,s=i.length;o<s;++o){var a=i[o];n+=Sr(t,e,a,r),e=a[a.length-1]}return n}(this.getOrientedFlatCoordinates(),0,this.endss_,this.stride)},r.prototype.getCoordinates=function(t){var e;return void 0!==t?Jr(e=this.getOrientedFlatCoordinates().slice(),0,this.endss_,this.stride,t):e=this.flatCoordinates,Mr(e,0,this.endss_,this.stride)},r.prototype.getEndss=function(){return this.endss_},r.prototype.getFlatInteriorPoints=function(){if(this.flatInteriorPointsRevision_!=this.getRevision()){var t=rh(this.flatCoordinates,0,this.endss_,this.stride);this.flatInteriorPoints_=Xr(this.getOrientedFlatCoordinates(),0,this.endss_,this.stride,t),this.flatInteriorPointsRevision_=this.getRevision()}return this.flatInteriorPoints_},r.prototype.getInteriorPoints=function(){return new ih(this.getFlatInteriorPoints().slice(),yr.XYM)},r.prototype.getOrientedFlatCoordinates=function(){if(this.orientedRevision_!=this.getRevision()){var t=this.flatCoordinates;!function(t,e,i,r,n){for(var o=0,s=i.length;o<s;++o)if(!Zr(t,e,i[o],r,n))return!1;return!0}(t,0,this.endss_,this.stride)?(this.orientedFlatCoordinates_=t.slice(),this.orientedFlatCoordinates_.length=Jr(this.orientedFlatCoordinates_,0,this.endss_,this.stride)):this.orientedFlatCoordinates_=t,this.orientedRevision_=this.getRevision()}return this.orientedFlatCoordinates_},r.prototype.getSimplifiedGeometryInternal=function(t){var e=[],i=[];return e.length=function(t,e,i,r,n,o,s,a){for(var h=0,l=i.length;h<l;++h){var u=i[h],c=[];s=Gr(t,e,u,r,n,o,s,c),a.push(c),e=u[u.length-1]}return s}(this.flatCoordinates,0,this.endss_,this.stride,Math.sqrt(t),e,0,i),new r(e,yr.XY,i)},r.prototype.getPolygon=function(t){if(t<0||this.endss_.length<=t)return null;var e;if(0===t)e=0;else{var i=this.endss_[t-1];e=i[i.length-1]}var r=this.endss_[t].slice(),n=r[r.length-1];if(0!==e)for(var o=0,s=r.length;o<s;++o)r[o]-=e;return new Qr(this.flatCoordinates.slice(e,n),this.layout,r)},r.prototype.getPolygons=function(){for(var t=this.layout,e=this.flatCoordinates,i=this.endss_,r=[],n=0,o=0,s=i.length;o<s;++o){var a=i[o].slice(),h=a[a.length-1];if(0!==n)for(var l=0,u=a.length;l<u;++l)a[l]-=n;var c=new Qr(e.slice(n,h),t,a);r.push(c),n=h}return r},r.prototype.getType=function(){return Lt.MULTI_POLYGON},r.prototype.intersectsExtent=function(t){return function(t,e,i,r,n){for(var o=0,s=i.length;o<s;++o){var a=i[o];if(Wr(t,e,a,r,n))return!0;e=a[a.length-1]}return!1}(this.getOrientedFlatCoordinates(),0,this.endss_,this.stride,t)},r.prototype.setCoordinates=function(t,e){this.setLayout(e,t,3),this.flatCoordinates||(this.flatCoordinates=[]);var i=function(t,e,i,r,n){for(var o=n||[],s=0,a=0,h=i.length;a<h;++a){var l=br(t,e,i[a],r,o[s]);e=(o[s++]=l)[l.length-1]}return o.length=s,o}(this.flatCoordinates,0,t,this.stride,this.endss_);if(0===i.length)this.flatCoordinates.length=0;else{var r=i[i.length-1];this.flatCoordinates.length=0===r.length?0:r[r.length-1]}this.changed()},r}(vr),oh={IMAGE:"IMAGE",TILE:"TILE",VECTOR_TILE:"VECTOR_TILE",VECTOR:"VECTOR"},sh="image",ah="vector",hh="renderOrder",lh=function(r){function t(t){var e=t||{},i=C({},e);delete i.style,delete i.renderBuffer,delete i.updateWhileAnimating,delete i.updateWhileInteracting,r.call(this,i),this.declutter_=void 0!==e.declutter&&e.declutter,this.renderBuffer_=void 0!==e.renderBuffer?e.renderBuffer:100,this.style_=null,this.styleFunction_=void 0,this.setStyle(e.style),this.updateWhileAnimating_=void 0!==e.updateWhileAnimating&&e.updateWhileAnimating,this.updateWhileInteracting_=void 0!==e.updateWhileInteracting&&e.updateWhileInteracting,this.renderMode_=e.renderMode||ah,this.type=oh.VECTOR}return r&&(t.__proto__=r),((t.prototype=Object.create(r&&r.prototype)).constructor=t).prototype.getDeclutter=function(){return this.declutter_},t.prototype.setDeclutter=function(t){this.declutter_=t},t.prototype.getRenderBuffer=function(){return this.renderBuffer_},t.prototype.getRenderOrder=function(){return this.get(hh)},t.prototype.getStyle=function(){return this.style_},t.prototype.getStyleFunction=function(){return this.styleFunction_},t.prototype.getUpdateWhileAnimating=function(){return this.updateWhileAnimating_},t.prototype.getUpdateWhileInteracting=function(){return this.updateWhileInteracting_},t.prototype.setRenderOrder=function(t){this.set(hh,t)},t.prototype.setStyle=function(t){var e,i,r;this.style_=void 0!==t?t:Hi,this.styleFunction_=null===t?void 0:("function"==typeof(e=this.style_)?i=e:(Array.isArray(e)?r=e:(Z(e instanceof Wi,41),r=[e]),i=function(){return r}),i),this.changed()},t.prototype.getRenderMode=function(){return this.renderMode_},t}(Ls);lh.prototype.getSource;var uh={ARRAY_BUFFER:"arraybuffer",JSON:"json",TEXT:"text",XML:"xml"};function ch(i,o,s,a){return function(t,e,r){var n=new XMLHttpRequest;n.open("GET","function"==typeof i?i(t,e,r):i,!0),o.getType()==uh.ARRAY_BUFFER&&(n.responseType="arraybuffer"),n.onload=function(t){if(!n.status||200<=n.status&&n.status<300){var e,i=o.getType();i==uh.JSON||i==uh.TEXT?e=n.responseText:i==uh.XML?(e=n.responseXML)||(e=(new DOMParser).parseFromString(n.responseText,"application/xml")):i==uh.ARRAY_BUFFER&&(e=n.response),e?s.call(this,o.readFeatures(e,{featureProjection:r}),o.readProjection(e),o.getLastExtent()):a.call(this)}else a.call(this)}.bind(this),n.onerror=function(){a.call(this)}.bind(this),n.send()}}function ph(t,e){return ch(t,e,function(t,e){this.addFeatures(t)},L)}function dh(t,e){return[[-1/0,-1/0,1/0,1/0]]}var fh=function(e){function t(t){e.call(this),this.projection_=ne(t.projection),this.attributions_=this.adaptAttributions_(t.attributions),this.state_=void 0!==t.state?t.state:ms,this.wrapX_=void 0!==t.wrapX&&t.wrapX}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.adaptAttributions_=function(e){return e?Array.isArray(e)?function(t){return e}:"function"==typeof e?e:function(t){return[e]}:null},t.prototype.getAttributions=function(){return this.attributions_},t.prototype.getProjection=function(){return this.projection_},t.prototype.getResolutions=function(){},t.prototype.getState=function(){return this.state_},t.prototype.getWrapX=function(){return this.wrapX_},t.prototype.refresh=function(){this.changed()},t.prototype.setAttributions=function(t){this.attributions_=this.adaptAttributions_(t),this.changed()},t.prototype.setState=function(t){this.state_=t,this.changed()},t}(R);fh.prototype.forEachFeatureAtCoordinate=L;var _h="addfeature",gh="changefeature",yh="clear",vh="removefeature";"undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof self&&self;var mh,xh=(function(t,e){t.exports=function(){function g(t,e,i){var r=t[e];t[e]=t[i],t[i]=r}function o(t,e){return t<e?-1:e<t?1:0}return function(t,e,i,r,n){!function t(e,i,r,n,o){for(;r<n;){if(600<n-r){var s=n-r+1,a=i-r+1,h=Math.log(s),l=.5*Math.exp(2*h/3),u=.5*Math.sqrt(h*l*(s-l)/s)*(a-s/2<0?-1:1),c=Math.max(r,Math.floor(i-a*l/s+u)),p=Math.min(n,Math.floor(i+(s-a)*l/s+u));t(e,i,c,p,o)}var d=e[i],f=r,_=n;for(g(e,r,i),0<o(e[n],d)&&g(e,r,n);f<_;){for(g(e,f,_),f++,_--;o(e[f],d)<0;)f++;for(;0<o(e[_],d);)_--}0===o(e[r],d)?g(e,r,_):g(e,++_,n),_<=i&&(r=_+1),i<=_&&(n=_-1)}}(t,e,i||0,r||t.length-1,n||o)}}()}(mh={exports:{}},mh.exports),mh.exports),Sh=Eh,Ch=Eh;function Eh(t,e){if(!(this instanceof Eh))return new Eh(t,e);this._maxEntries=Math.max(4,t||9),this._minEntries=Math.max(2,Math.ceil(.4*this._maxEntries)),e&&this._initFormat(e),this.clear()}function Th(t,e,i){if(!i)return e.indexOf(t);for(var r=0;r<e.length;r++)if(i(t,e[r]))return r;return-1}function wh(t,e){Rh(t,0,t.children.length,e,t)}function Rh(t,e,i,r,n){n||(n=Nh(null)),n.minX=1/0,n.minY=1/0,n.maxX=-1/0,n.maxY=-1/0;for(var o,s=e;s<i;s++)o=t.children[s],Ih(n,t.leaf?r(o):o);return n}function Ih(t,e){return t.minX=Math.min(t.minX,e.minX),t.minY=Math.min(t.minY,e.minY),t.maxX=Math.max(t.maxX,e.maxX),t.maxY=Math.max(t.maxY,e.maxY),t}function Lh(t,e){return t.minX-e.minX}function bh(t,e){return t.minY-e.minY}function Ph(t){return(t.maxX-t.minX)*(t.maxY-t.minY)}function Fh(t){return t.maxX-t.minX+(t.maxY-t.minY)}function Mh(t,e){return t.minX<=e.minX&&t.minY<=e.minY&&e.maxX<=t.maxX&&e.maxY<=t.maxY}function Oh(t,e){return e.minX<=t.maxX&&e.minY<=t.maxY&&e.maxX>=t.minX&&e.maxY>=t.minY}function Nh(t){return{children:t,height:1,leaf:!0,minX:1/0,minY:1/0,maxX:-1/0,maxY:-1/0}}function Ah(t,e,i,r,n){for(var o,s=[e,i];s.length;)(i=s.pop())-(e=s.pop())<=r||(o=e+Math.ceil((i-e)/r/2)*r,xh(t,o,e,i,n),s.push(e,o,o,i))}Eh.prototype={all:function(){return this._all(this.data,[])},search:function(t){var e=this.data,i=[],r=this.toBBox;if(!Oh(t,e))return i;for(var n,o,s,a,h=[];e;){for(n=0,o=e.children.length;n<o;n++)s=e.children[n],Oh(t,a=e.leaf?r(s):s)&&(e.leaf?i.push(s):Mh(t,a)?this._all(s,i):h.push(s));e=h.pop()}return i},collides:function(t){var e=this.data,i=this.toBBox;if(!Oh(t,e))return!1;for(var r,n,o,s,a=[];e;){for(r=0,n=e.children.length;r<n;r++)if(o=e.children[r],Oh(t,s=e.leaf?i(o):o)){if(e.leaf||Mh(t,s))return!0;a.push(o)}e=a.pop()}return!1},load:function(t){if(!t||!t.length)return this;if(t.length<this._minEntries){for(var e=0,i=t.length;e<i;e++)this.insert(t[e]);return this}var r=this._build(t.slice(),0,t.length-1,0);if(this.data.children.length)if(this.data.height===r.height)this._splitRoot(this.data,r);else{if(this.data.height<r.height){var n=this.data;this.data=r,r=n}this._insert(r,this.data.height-r.height-1,!0)}else this.data=r;return this},insert:function(t){return t&&this._insert(t,this.data.height-1),this},clear:function(){return this.data=Nh([]),this},remove:function(t,e){if(!t)return this;for(var i,r,n,o,s=this.data,a=this.toBBox(t),h=[],l=[];s||h.length;){if(s||(s=h.pop(),r=h[h.length-1],i=l.pop(),o=!0),s.leaf&&-1!==(n=Th(t,s.children,e)))return s.children.splice(n,1),h.push(s),this._condense(h),this;o||s.leaf||!Mh(s,a)?r?(i++,s=r.children[i],o=!1):s=null:(h.push(s),l.push(i),i=0,s=(r=s).children[0])}return this},toBBox:function(t){return t},compareMinX:Lh,compareMinY:bh,toJSON:function(){return this.data},fromJSON:function(t){return this.data=t,this},_all:function(t,e){for(var i=[];t;)t.leaf?e.push.apply(e,t.children):i.push.apply(i,t.children),t=i.pop();return e},_build:function(t,e,i,r){var n,o=i-e+1,s=this._maxEntries;if(o<=s)return wh(n=Nh(t.slice(e,i+1)),this.toBBox),n;r||(r=Math.ceil(Math.log(o)/Math.log(s)),s=Math.ceil(o/Math.pow(s,r-1))),(n=Nh([])).leaf=!1,n.height=r;var a,h,l,u,c=Math.ceil(o/s),p=c*Math.ceil(Math.sqrt(s));for(Ah(t,e,i,p,this.compareMinX),a=e;a<=i;a+=p)for(Ah(t,a,l=Math.min(a+p-1,i),c,this.compareMinY),h=a;h<=l;h+=c)u=Math.min(h+c-1,l),n.children.push(this._build(t,h,u,r-1));return wh(n,this.toBBox),n},_chooseSubtree:function(t,e,i,r){for(var n,o,s,a,h,l,u,c,p,d;r.push(e),!e.leaf&&r.length-1!==i;){for(u=c=1/0,n=0,o=e.children.length;n<o;n++)h=Ph(s=e.children[n]),p=t,d=s,(l=(Math.max(d.maxX,p.maxX)-Math.min(d.minX,p.minX))*(Math.max(d.maxY,p.maxY)-Math.min(d.minY,p.minY))-h)<c?(c=l,u=h<u?h:u,a=s):l===c&&h<u&&(u=h,a=s);e=a||e.children[0]}return e},_insert:function(t,e,i){var r=this.toBBox,n=i?t:r(t),o=[],s=this._chooseSubtree(n,this.data,e,o);for(s.children.push(t),Ih(s,n);0<=e&&o[e].children.length>this._maxEntries;)this._split(o,e),e--;this._adjustParentBBoxes(n,o,e)},_split:function(t,e){var i=t[e],r=i.children.length,n=this._minEntries;this._chooseSplitAxis(i,n,r);var o=this._chooseSplitIndex(i,n,r),s=Nh(i.children.splice(o,i.children.length-o));s.height=i.height,s.leaf=i.leaf,wh(i,this.toBBox),wh(s,this.toBBox),e?t[e-1].children.push(s):this._splitRoot(i,s)},_splitRoot:function(t,e){this.data=Nh([t,e]),this.data.height=t.height+1,this.data.leaf=!1,wh(this.data,this.toBBox)},_chooseSplitIndex:function(t,e,i){var r,n,o,s,a,h,l,u,c,p,d,f,_,g;for(h=l=1/0,r=e;r<=i-e;r++)n=Rh(t,0,r,this.toBBox),o=Rh(t,r,i,this.toBBox),c=n,p=o,void 0,d=Math.max(c.minX,p.minX),f=Math.max(c.minY,p.minY),_=Math.min(c.maxX,p.maxX),g=Math.min(c.maxY,p.maxY),s=Math.max(0,_-d)*Math.max(0,g-f),a=Ph(n)+Ph(o),s<h?(h=s,u=r,l=a<l?a:l):s===h&&a<l&&(l=a,u=r);return u},_chooseSplitAxis:function(t,e,i){var r=t.leaf?this.compareMinX:Lh,n=t.leaf?this.compareMinY:bh;this._allDistMargin(t,e,i,r)<this._allDistMargin(t,e,i,n)&&t.children.sort(r)},_allDistMargin:function(t,e,i,r){t.children.sort(r);var n,o,s=this.toBBox,a=Rh(t,0,e,s),h=Rh(t,i-e,i,s),l=Fh(a)+Fh(h);for(n=e;n<i-e;n++)o=t.children[n],Ih(a,t.leaf?s(o):o),l+=Fh(a);for(n=i-e-1;e<=n;n--)o=t.children[n],Ih(h,t.leaf?s(o):o),l+=Fh(h);return l},_adjustParentBBoxes:function(t,e,i){for(var r=i;0<=r;r--)Ih(e[r],t)},_condense:function(t){for(var e,i=t.length-1;0<=i;i--)0===t[i].children.length?0<i?(e=t[i-1].children).splice(e.indexOf(t[i]),1):this.clear():wh(t[i],this.toBBox)},_initFormat:function(t){var e=["return a"," - b",";"];this.compareMinX=new Function("a","b",e.join(t[0])),this.compareMinY=new Function("a","b",e.join(t[1])),this.toBBox=new Function("a","return {minX: a"+t[0]+", minY: a"+t[1]+", maxX: a"+t[2]+", maxY: a"+t[3]+"};")}},Sh.default=Ch;var Gh=function(t){this.rbush_=Sh(t,void 0),this.items_={}};Gh.prototype.insert=function(t,e){var i={minX:t[0],minY:t[1],maxX:t[2],maxY:t[3],value:e};this.rbush_.insert(i),this.items_[Et(e)]=i},Gh.prototype.load=function(t,e){for(var i=new Array(e.length),r=0,n=e.length;r<n;r++){var o=t[r],s=e[r],a={minX:o[0],minY:o[1],maxX:o[2],maxY:o[3],value:s};i[r]=a,this.items_[Et(s)]=a}this.rbush_.load(i)},Gh.prototype.remove=function(t){var e=Et(t),i=this.items_[e];return delete this.items_[e],null!==this.rbush_.remove(i)},Gh.prototype.update=function(t,e){var i=this.items_[Et(e)];$([i.minX,i.minY,i.maxX,i.maxY],t)||(this.remove(e),this.insert(t,e))},Gh.prototype.getAll=function(){return this.rbush_.all().map(function(t){return t.value})},Gh.prototype.getInExtent=function(t){var e={minX:t[0],minY:t[1],maxX:t[2],maxY:t[3]};return this.rbush_.search(e).map(function(t){return t.value})},Gh.prototype.forEach=function(t,e){return this.forEach_(this.getAll(),t,e)},Gh.prototype.forEachInExtent=function(t,e,i){return this.forEach_(this.getInExtent(t),e,i)},Gh.prototype.forEach_=function(t,e,i){for(var r,n=0,o=t.length;n<o;n++)if(r=e.call(i,t[n]))return r;return r},Gh.prototype.isEmpty=function(){return Tt(this.items_)},Gh.prototype.clear=function(){this.rbush_.clear(),this.items_={}},Gh.prototype.getExtent=function(t){var e=this.rbush_.data;return X(e.minX,e.minY,e.maxX,e.maxY,t)},Gh.prototype.concat=function(t){for(var e in this.rbush_.load(t.rbush_.all()),t.items_)this.items_[0|e]=t.items_[0|e]};var kh=function(i){function t(t,e){i.call(this,t),this.feature=e}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(m),Dh=function(o){function t(t){var e=t||{};o.call(this,{attributions:e.attributions,projection:void 0,state:ms,wrapX:void 0===e.wrapX||e.wrapX}),this.loader_=L,this.format_=e.format,this.overlaps_=null==e.overlaps||e.overlaps,this.url_=e.url,void 0!==e.loader?this.loader_=e.loader:void 0!==this.url_&&(Z(this.format_,7),this.loader_=ph(this.url_,this.format_)),this.strategy_=void 0!==e.strategy?e.strategy:dh;var i,r,n=void 0===e.useSpatialIndex||e.useSpatialIndex;this.featuresRtree_=n?new Gh:null,this.loadedExtentsRtree_=new Gh,this.nullGeometryFeatures_={},this.idIndex_={},this.undefIdIndex_={},this.featureChangeKeys_={},this.featuresCollection_=null,e.features instanceof M?r=(i=e.features).getArray():Array.isArray(e.features)&&(r=e.features),n||void 0!==i||(i=new M(r)),void 0!==r&&this.addFeaturesInternal(r),void 0!==i&&this.bindFeaturesCollection_(i)}return o&&(t.__proto__=o),(t.prototype=Object.create(o&&o.prototype)).constructor=t}(fh);Dh.prototype.addFeature=function(t){this.addFeatureInternal(t),this.changed()},Dh.prototype.addFeatureInternal=function(t){var e=Et(t).toString();if(this.addToIndex_(e,t)){this.setupChangeEvents_(e,t);var i=t.getGeometry();if(i){var r=i.getExtent();this.featuresRtree_&&this.featuresRtree_.insert(r,t)}else this.nullGeometryFeatures_[e]=t;this.dispatchEvent(new kh(_h,t))}},Dh.prototype.setupChangeEvents_=function(t,e){this.featureChangeKeys_[t]=[E(e,w.CHANGE,this.handleFeatureChange_,this),E(e,a,this.handleFeatureChange_,this)]},Dh.prototype.addToIndex_=function(t,e){var i=!0,r=e.getId();return void 0!==r?r.toString()in this.idIndex_?i=!1:this.idIndex_[r.toString()]=e:(Z(!(t in this.undefIdIndex_),30),this.undefIdIndex_[t]=e),i},Dh.prototype.addFeatures=function(t){this.addFeaturesInternal(t),this.changed()},Dh.prototype.addFeaturesInternal=function(t){for(var e=[],i=[],r=[],n=0,o=t.length;n<o;n++){var s=t[n],a=Et(s).toString();this.addToIndex_(a,s)&&i.push(s)}for(var h=0,l=i.length;h<l;h++){var u=i[h],c=Et(u).toString();this.setupChangeEvents_(c,u);var p=u.getGeometry();if(p){var d=p.getExtent();e.push(d),r.push(u)}else this.nullGeometryFeatures_[c]=u}this.featuresRtree_&&this.featuresRtree_.load(e,r);for(var f=0,_=i.length;f<_;f++)this.dispatchEvent(new kh(_h,i[f]))},Dh.prototype.bindFeaturesCollection_=function(e){var i=!1;E(this,_h,function(t){i||(i=!0,e.push(t.feature),i=!1)}),E(this,vh,function(t){i||(i=!0,e.remove(t.feature),i=!1)}),E(e,h,function(t){i||(i=!0,this.addFeature(t.element),i=!1)},this),E(e,l,function(t){i||(i=!0,this.removeFeature(t.element),i=!1)},this),this.featuresCollection_=e},Dh.prototype.clear=function(t){if(t){for(var e in this.featureChangeKeys_){this.featureChangeKeys_[e].forEach(g)}this.featuresCollection_||(this.featureChangeKeys_={},this.idIndex_={},this.undefIdIndex_={})}else if(this.featuresRtree_)for(var i in this.featuresRtree_.forEach(this.removeFeatureInternal,this),this.nullGeometryFeatures_)this.removeFeatureInternal(this.nullGeometryFeatures_[i]);this.featuresCollection_&&this.featuresCollection_.clear(),this.featuresRtree_&&this.featuresRtree_.clear(),this.loadedExtentsRtree_.clear(),this.nullGeometryFeatures_={};var r=new kh(yh);this.dispatchEvent(r),this.changed()},Dh.prototype.forEachFeature=function(t){return this.featuresRtree_?this.featuresRtree_.forEach(t):this.featuresCollection_?this.featuresCollection_.forEach(t):void 0},Dh.prototype.forEachFeatureAtCoordinateDirect=function(e,i){var t=[e[0],e[1],e[0],e[1]];return this.forEachFeatureInExtent(t,function(t){return t.getGeometry().intersectsCoordinate(e)?i(t):void 0})},Dh.prototype.forEachFeatureInExtent=function(t,e){return this.featuresRtree_?this.featuresRtree_.forEachInExtent(t,e):this.featuresCollection_?this.featuresCollection_.forEach(e):void 0},Dh.prototype.forEachFeatureIntersectingExtent=function(i,r){return this.forEachFeatureInExtent(i,function(t){if(t.getGeometry().intersectsExtent(i)){var e=r(t);if(e)return e}})},Dh.prototype.getFeaturesCollection=function(){return this.featuresCollection_},Dh.prototype.getFeatures=function(){var t;return this.featuresCollection_?t=this.featuresCollection_.getArray():this.featuresRtree_&&(t=this.featuresRtree_.getAll(),Tt(this.nullGeometryFeatures_)||pr(t,o(this.nullGeometryFeatures_))),t},Dh.prototype.getFeaturesAtCoordinate=function(t){var e=[];return this.forEachFeatureAtCoordinateDirect(t,function(t){e.push(t)}),e},Dh.prototype.getFeaturesInExtent=function(t){return this.featuresRtree_.getInExtent(t)},Dh.prototype.getClosestFeatureToCoordinate=function(t,e){var n=t[0],o=t[1],s=null,a=[NaN,NaN],h=1/0,l=[-1/0,-1/0,1/0,1/0],u=e||y;return this.featuresRtree_.forEachInExtent(l,function(t){if(u(t)){var e=t.getGeometry(),i=h;if((h=e.closestPointXY(n,o,a,h))<i){s=t;var r=Math.sqrt(h);l[0]=n-r,l[1]=o-r,l[2]=n+r,l[3]=o+r}}}),s},Dh.prototype.getExtent=function(t){return this.featuresRtree_.getExtent(t)},Dh.prototype.getFeatureById=function(t){var e=this.idIndex_[t.toString()];return void 0!==e?e:null},Dh.prototype.getFormat=function(){return this.format_},Dh.prototype.getOverlaps=function(){return this.overlaps_},Dh.prototype.getResolutions=function(){},Dh.prototype.getUrl=function(){return this.url_},Dh.prototype.handleFeatureChange_=function(t){var e=t.target,i=Et(e).toString(),r=e.getGeometry();if(r){var n=r.getExtent();i in this.nullGeometryFeatures_?(delete this.nullGeometryFeatures_[i],this.featuresRtree_&&this.featuresRtree_.insert(n,e)):this.featuresRtree_&&this.featuresRtree_.update(n,e)}else i in this.nullGeometryFeatures_||(this.featuresRtree_&&this.featuresRtree_.remove(e),this.nullGeometryFeatures_[i]=e);var o=e.getId();if(void 0!==o){var s=o.toString();i in this.undefIdIndex_?(delete this.undefIdIndex_[i],this.idIndex_[s]=e):this.idIndex_[s]!==e&&(this.removeFromIdIndex_(e),this.idIndex_[s]=e)}else i in this.undefIdIndex_||(this.removeFromIdIndex_(e),this.undefIdIndex_[i]=e);this.changed(),this.dispatchEvent(new kh(gh,e))},Dh.prototype.hasFeature=function(t){var e=t.getId();return void 0!==e?e in this.idIndex_:Et(t).toString()in this.undefIdIndex_},Dh.prototype.isEmpty=function(){return this.featuresRtree_.isEmpty()&&Tt(this.nullGeometryFeatures_)},Dh.prototype.loadFeatures=function(t,r,n){for(var o=this,s=this.loadedExtentsRtree_,a=this.strategy_(t,r),e=function(t,e){var i=a[t];s.forEachInExtent(i,function(t){return Q(t.extent,i)})||(o.loader_.call(o,i,r,n),s.insert(i,{extent:i.slice()}))},i=0,h=a.length;i<h;++i)e(i)},Dh.prototype.removeLoadedExtent=function(e){var i,t=this.loadedExtentsRtree_;t.forEachInExtent(e,function(t){if($(t.extent,e))return i=t,!0}),i&&t.remove(i)},Dh.prototype.removeFeature=function(t){var e=Et(t).toString();e in this.nullGeometryFeatures_?delete this.nullGeometryFeatures_[e]:this.featuresRtree_&&this.featuresRtree_.remove(t),this.removeFeatureInternal(t),this.changed()},Dh.prototype.removeFeatureInternal=function(t){var e=Et(t).toString();this.featureChangeKeys_[e].forEach(g),delete this.featureChangeKeys_[e];var i=t.getId();void 0!==i?delete this.idIndex_[i.toString()]:delete this.undefIdIndex_[e],this.dispatchEvent(new kh(vh,t))},Dh.prototype.removeFromIdIndex_=function(t){var e=!1;for(var i in this.idIndex_)if(this.idIndex_[i]===t){delete this.idIndex_[i],e=!0;break}return e},Dh.prototype.setLoader=function(t){this.loader_=t};var jh={POINT:"Point",LINE_STRING:"LineString",POLYGON:"Polygon",CIRCLE:"Circle"},Uh="drawstart",Yh="drawend",Bh=function(i){function t(t,e){i.call(this,t),this.feature=e}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(m),Xh=function(o){function t(t){o.call(this,{handleDownEvent:Vh,handleEvent:zh,handleUpEvent:Wh,stopDown:v}),this.shouldHandle_=!1,this.downPx_=null,this.downTimeout_,this.lastDragTime_,this.freehand_=!1,this.source_=t.source?t.source:null,this.features_=t.features?t.features:null,this.snapTolerance_=t.snapTolerance?t.snapTolerance:12,this.type_=t.type,this.mode_=function(t){var e;t===Lt.POINT||t===Lt.MULTI_POINT?e=jh.POINT:t===Lt.LINE_STRING||t===Lt.MULTI_LINE_STRING?e=jh.LINE_STRING:t===Lt.POLYGON||t===Lt.MULTI_POLYGON?e=jh.POLYGON:t===Lt.CIRCLE&&(e=jh.CIRCLE);return e}(this.type_),this.stopClick_=!!t.stopClick,this.minPoints_=t.minPoints?t.minPoints:this.mode_===jh.POLYGON?3:2,this.maxPoints_=t.maxPoints?t.maxPoints:1/0,this.finishCondition_=t.finishCondition?t.finishCondition:y;var i,e=t.geometryFunction;if(!e)if(this.type_===Lt.CIRCLE)e=function(t,e){var i=e||new th([NaN,NaN]),r=fn(t[0],t[1]);return i.setCenterAndRadius(t[0],Math.sqrt(r)),i};else{var r,n=this.mode_;n===jh.POINT?r=Dr:n===jh.LINE_STRING?r=Sn:n===jh.POLYGON&&(r=Qr),e=function(t,e){var i=e;return i?n===jh.POLYGON?t[0].length?i.setCoordinates([t[0].concat([t[0][0]])]):i.setCoordinates([]):i.setCoordinates(t):i=new r(t),i}}this.geometryFunction_=e,this.dragVertexDelay_=void 0!==t.dragVertexDelay?t.dragVertexDelay:500,this.finishCoordinate_=null,this.sketchFeature_=null,this.sketchPoint_=null,this.sketchCoords_=null,this.sketchLine_=null,this.sketchLineCoords_=null,this.squaredClickTolerance_=t.clickTolerance?t.clickTolerance*t.clickTolerance:36,this.overlay_=new lh({source:new Dh({useSpatialIndex:!1,wrapX:!!t.wrapX&&t.wrapX}),style:t.style?t.style:(i=Zi(),function(t,e){return i[t.getGeometry().getType()]}),updateWhileInteracting:!0}),this.geometryName_=t.geometryName,this.condition_=t.condition?t.condition:Qs,this.freehandCondition_,t.freehand?this.freehandCondition_=Ks:this.freehandCondition_=t.freehandCondition?t.freehandCondition:$s,E(this,b(Gs),this.updateState_,this)}return o&&(t.__proto__=o),((t.prototype=Object.create(o&&o.prototype)).constructor=t).prototype.setMap=function(t){o.prototype.setMap.call(this,t),this.updateState_()},t.prototype.handlePointerMove_=function(t){if(this.downPx_&&(!this.freehand_&&this.shouldHandle_||this.freehand_&&!this.shouldHandle_)){var e=this.downPx_,i=t.pixel,r=e[0]-i[0],n=e[1]-i[1],o=r*r+n*n;if(this.shouldHandle_=this.freehand_?o>this.squaredClickTolerance_:o<=this.squaredClickTolerance_,!this.shouldHandle_)return!0}return this.finishCoordinate_?this.modifyDrawing_(t):this.createOrUpdateSketchPoint_(t),!0},t.prototype.atFinish_=function(t){var e=!1;if(this.sketchFeature_){var i=!1,r=[this.finishCoordinate_];if(this.mode_===jh.LINE_STRING?i=this.sketchCoords_.length>this.minPoints_:this.mode_===jh.POLYGON&&(i=this.sketchCoords_[0].length>this.minPoints_,r=[this.sketchCoords_[0][0],this.sketchCoords_[0][this.sketchCoords_[0].length-2]]),i)for(var n=t.map,o=0,s=r.length;o<s;o++){var a=r[o],h=n.getPixelFromCoordinate(a),l=t.pixel,u=l[0]-h[0],c=l[1]-h[1],p=this.freehand_?1:this.snapTolerance_;if(e=Math.sqrt(u*u+c*c)<=p){this.finishCoordinate_=a;break}}}return e},t.prototype.createOrUpdateSketchPoint_=function(t){var e=t.coordinate.slice();this.sketchPoint_?this.sketchPoint_.getGeometry().setCoordinates(e):(this.sketchPoint_=new Ji(new Dr(e)),this.updateSketchFeatures_())},t.prototype.startDrawing_=function(t){var e=t.coordinate;this.finishCoordinate_=e,this.mode_===jh.POINT?this.sketchCoords_=e.slice():this.mode_===jh.POLYGON?(this.sketchCoords_=[[e.slice(),e.slice()]],this.sketchLineCoords_=this.sketchCoords_[0]):this.sketchCoords_=[e.slice(),e.slice()],this.sketchLineCoords_&&(this.sketchLine_=new Ji(new Sn(this.sketchLineCoords_)));var i=this.geometryFunction_(this.sketchCoords_);this.sketchFeature_=new Ji,this.geometryName_&&this.sketchFeature_.setGeometryName(this.geometryName_),this.sketchFeature_.setGeometry(i),this.updateSketchFeatures_(),this.dispatchEvent(new Bh(Uh,this.sketchFeature_))},t.prototype.modifyDrawing_=function(t){var e,i,r,n=t.coordinate,o=this.sketchFeature_.getGeometry();(this.mode_===jh.POINT?i=this.sketchCoords_:this.mode_===jh.POLYGON?(i=(e=this.sketchCoords_[0])[e.length-1],this.atFinish_(t)&&(n=this.finishCoordinate_.slice())):i=(e=this.sketchCoords_)[e.length-1],i[0]=n[0],i[1]=n[1],this.geometryFunction_(this.sketchCoords_,o),this.sketchPoint_)&&this.sketchPoint_.getGeometry().setCoordinates(n);if(o instanceof Qr&&this.mode_!==jh.POLYGON){this.sketchLine_||(this.sketchLine_=new Ji);var s=o.getLinearRing(0);(r=this.sketchLine_.getGeometry())?(r.setFlatCoordinates(s.getLayout(),s.getFlatCoordinates()),r.changed()):(r=new Sn(s.getFlatCoordinates(),s.getLayout()),this.sketchLine_.setGeometry(r))}else this.sketchLineCoords_&&(r=this.sketchLine_.getGeometry()).setCoordinates(this.sketchLineCoords_);this.updateSketchFeatures_()},t.prototype.addToDrawing_=function(t){var e,i,r=t.coordinate,n=this.sketchFeature_.getGeometry();this.mode_===jh.LINE_STRING?(this.finishCoordinate_=r.slice(),(i=this.sketchCoords_).length>=this.maxPoints_&&(this.freehand_?i.pop():e=!0),i.push(r.slice()),this.geometryFunction_(i,n)):this.mode_===jh.POLYGON&&((i=this.sketchCoords_[0]).length>=this.maxPoints_&&(this.freehand_?i.pop():e=!0),i.push(r.slice()),e&&(this.finishCoordinate_=i[0]),this.geometryFunction_(this.sketchCoords_,n)),this.updateSketchFeatures_(),e&&this.finishDrawing()},t.prototype.removeLastPoint=function(){if(this.sketchFeature_){var t,e=this.sketchFeature_.getGeometry();this.mode_===jh.LINE_STRING?((t=this.sketchCoords_).splice(-2,1),this.geometryFunction_(t,e),2<=t.length&&(this.finishCoordinate_=t[t.length-2].slice())):this.mode_===jh.POLYGON&&((t=this.sketchCoords_[0]).splice(-2,1),this.sketchLine_.getGeometry().setCoordinates(t),this.geometryFunction_(this.sketchCoords_,e)),0===t.length&&(this.finishCoordinate_=null),this.updateSketchFeatures_()}},t.prototype.finishDrawing=function(){var t=this.abortDrawing_();if(t){var e=this.sketchCoords_,i=t.getGeometry();this.mode_===jh.LINE_STRING?(e.pop(),this.geometryFunction_(e,i)):this.mode_===jh.POLYGON&&(e[0].pop(),this.geometryFunction_(e,i),e=i.getCoordinates()),this.type_===Lt.MULTI_POINT?t.setGeometry(new ih([e])):this.type_===Lt.MULTI_LINE_STRING?t.setGeometry(new eh([e])):this.type_===Lt.MULTI_POLYGON&&t.setGeometry(new nh([e])),this.dispatchEvent(new Bh(Yh,t)),this.features_&&this.features_.push(t),this.source_&&this.source_.addFeature(t)}},t.prototype.abortDrawing_=function(){this.finishCoordinate_=null;var t=this.sketchFeature_;return t&&(this.sketchFeature_=null,this.sketchPoint_=null,this.sketchLine_=null,this.overlay_.getSource().clear(!0)),t},t.prototype.extend=function(t){var e=t.getGeometry();this.sketchFeature_=t,this.sketchCoords_=e.getCoordinates();var i=this.sketchCoords_[this.sketchCoords_.length-1];this.finishCoordinate_=i.slice(),this.sketchCoords_.push(i.slice()),this.updateSketchFeatures_(),this.dispatchEvent(new Bh(Uh,this.sketchFeature_))},t.prototype.updateSketchFeatures_=function(){var t=[];this.sketchFeature_&&t.push(this.sketchFeature_),this.sketchLine_&&t.push(this.sketchLine_),this.sketchPoint_&&t.push(this.sketchPoint_);var e=this.overlay_.getSource();e.clear(!0),e.addFeatures(t)},t.prototype.updateState_=function(){var t=this.getMap(),e=this.getActive();t&&e||this.abortDrawing_(),this.overlay_.setMap(e?t:null)},t}(aa);function zh(t){t.originalEvent.type===w.CONTEXTMENU&&t.preventDefault(),this.freehand_=this.mode_!==jh.POINT&&this.freehandCondition_(t);var e=t.type===qn.POINTERMOVE,i=!0;this.lastDragTime_&&t.type===qn.POINTERDRAG&&(Date.now()-this.lastDragTime_>=this.dragVertexDelay_?(this.downPx_=t.pixel,this.shouldHandle_=!this.freehand_,e=!0):this.lastDragTime_=void 0,this.shouldHandle_&&this.downTimeout_&&(clearTimeout(this.downTimeout_),this.downTimeout_=void 0));return this.freehand_&&t.type===qn.POINTERDRAG&&null!==this.sketchFeature_?(this.addToDrawing_(t),i=!1):this.freehand_&&t.type===qn.POINTERDOWN?i=!1:e?(i=t.type===qn.POINTERMOVE)&&this.freehand_?i=this.handlePointerMove_(t):(t.pointerEvent.pointerType==ho||t.type===qn.POINTERDRAG&&!this.downTimeout_)&&this.handlePointerMove_(t):t.type===qn.DBLCLICK&&(i=!1),la.call(this,t)&&i}function Vh(t){return this.shouldHandle_=!this.freehand_,this.freehand_?(this.downPx_=t.pixel,this.finishCoordinate_||this.startDrawing_(t),!0):!!this.condition_(t)&&(this.lastDragTime_=Date.now(),this.downTimeout_=setTimeout(function(){this.handlePointerMove_(new Jn(qn.POINTERMOVE,t.map,t.pointerEvent,t.frameState))}.bind(this),this.dragVertexDelay_),this.downPx_=t.pixel,!0)}function Wh(t){var e=!0;this.downTimeout_&&(clearTimeout(this.downTimeout_),this.downTimeout_=void 0),this.handlePointerMove_(t);var i=this.mode_===jh.CIRCLE;return this.shouldHandle_?(this.finishCoordinate_?this.freehand_||i?this.finishDrawing():this.atFinish_(t)?this.finishCondition_(t)&&this.finishDrawing():this.addToDrawing_(t):(this.startDrawing_(t),this.mode_===jh.POINT&&this.finishDrawing()),e=!1):this.freehand_&&(this.finishCoordinate_=null,this.abortDrawing_()),!e&&this.stopClick_&&t.stopPropagation(),e}var Kh="extentchanged",Hh=function(e){function t(t){e.call(this,Kh),this.extent=t}return e&&(t.__proto__=e),(t.prototype=Object.create(e&&e.prototype)).constructor=t}(m),Zh=function(n){function t(t){n.call(this,{handleDownEvent:Jh,handleDragEvent:Qh,handleEvent:qh,handleUpEvent:$h});var i,r,e=t||{};this.extent_=null,this.pointerHandler_=null,this.pixelTolerance_=void 0!==e.pixelTolerance?e.pixelTolerance:10,this.snappedToVertex_=!1,this.extentFeature_=null,this.vertexFeature_=null,t||(t={}),this.extentOverlay_=new lh({source:new Dh({useSpatialIndex:!1,wrapX:!!t.wrapX}),style:t.boxStyle?t.boxStyle:(i=Zi(),function(t,e){return i[Lt.POLYGON]}),updateWhileAnimating:!0,updateWhileInteracting:!0}),this.vertexOverlay_=new lh({source:new Dh({useSpatialIndex:!1,wrapX:!!t.wrapX}),style:t.pointerStyle?t.pointerStyle:(r=Zi(),function(t,e){return r[Lt.POINT]}),updateWhileAnimating:!0,updateWhileInteracting:!0}),t.extent&&this.setExtent(t.extent)}return n&&(t.__proto__=n),((t.prototype=Object.create(n&&n.prototype)).constructor=t).prototype.snapToVertex_=function(t,e){var i,r=e.getCoordinateFromPixel(t),n=this.getExtent();if(n){var o=[[[(i=n)[0],i[1]],[i[0],i[3]]],[[i[0],i[3]],[i[2],i[3]]],[[i[2],i[3]],[i[2],i[1]]],[[i[2],i[1]],[i[0],i[1]]]];o.sort(function(t,e){return gn(r,t)-gn(r,e)});var s=o[0],a=hn(r,s),h=e.getPixelFromCoordinate(a);if(_n(t,h)<=this.pixelTolerance_){var l=e.getPixelFromCoordinate(s[0]),u=e.getPixelFromCoordinate(s[1]),c=fn(h,l),p=fn(h,u),d=Math.sqrt(Math.min(c,p));return this.snappedToVertex_=d<=this.pixelTolerance_,this.snappedToVertex_&&(a=p<c?s[1]:s[0]),a}}return null},t.prototype.handlePointerMove_=function(t){var e=t.pixel,i=t.map,r=this.snapToVertex_(e,i);r||(r=i.getCoordinateFromPixel(e)),this.createOrUpdatePointerFeature_(r)},t.prototype.createOrUpdateExtentFeature_=function(t){var e=this.extentFeature_;return e?t?e.setGeometry(tn(t)):e.setGeometry(void 0):(e=new Ji(t?tn(t):{}),this.extentFeature_=e,this.extentOverlay_.getSource().addFeature(e)),e},t.prototype.createOrUpdatePointerFeature_=function(t){var e=this.vertexFeature_;e?e.getGeometry().setCoordinates(t):(e=new Ji(new Dr(t)),this.vertexFeature_=e,this.vertexOverlay_.getSource().addFeature(e));return e},t.prototype.setMap=function(t){this.extentOverlay_.setMap(t),this.vertexOverlay_.setMap(t),n.prototype.setMap.call(this,t)},t.prototype.getExtent=function(){return this.extent_},t.prototype.setExtent=function(t){this.extent_=t||null,this.createOrUpdateExtentFeature_(t),this.dispatchEvent(new Hh(this.extent_))},t}(aa);function qh(t){return!(t instanceof Jn)||(t.type!=qn.POINTERMOVE||this.handlingDownUpSequence||this.handlePointerMove_(t),la.call(this,t),!1)}function Jh(t){var e=t.pixel,i=t.map,r=this.getExtent(),n=this.snapToVertex_(e,i),o=function(t){var e=null,i=null;return t[0]==r[0]?e=r[2]:t[0]==r[2]&&(e=r[0]),t[1]==r[1]?i=r[3]:t[1]==r[3]&&(i=r[1]),null!==e&&null!==i?[e,i]:null};if(n&&r){var s=n[0]==r[0]||n[0]==r[2]?n[0]:null,a=n[1]==r[1]||n[1]==r[3]?n[1]:null;null!==s&&null!==a?this.pointerHandler_=tl(o(n)):null!==s?this.pointerHandler_=el(o([s,r[1]]),o([s,r[3]])):null!==a&&(this.pointerHandler_=el(o([r[0],a]),o([r[2],a])))}else n=i.getCoordinateFromPixel(e),this.setExtent([n[0],n[1],n[0],n[1]]),this.pointerHandler_=tl(n);return!0}function Qh(t){if(this.pointerHandler_){var e=t.coordinate;this.setExtent(this.pointerHandler_(e)),this.createOrUpdatePointerFeature_(e)}return!0}function $h(t){this.pointerHandler_=null;var e=this.getExtent();return e&&0!==it(e)||this.setExtent(null),!1}function tl(e){return function(t){return A([e,t])}}function el(e,i){return e[0]==i[0]?function(t){return A([e,[t[0],i[1]]])}:e[1]==i[1]?function(t){return A([e,[i[0],t[1]]])}:null}var il=0,rl=1,nl={MODIFYSTART:"modifystart",MODIFYEND:"modifyend"},ol=function(r){function t(t,e,i){r.call(this,t),this.features=e,this.mapBrowserEvent=i}return r&&(t.__proto__=r),(t.prototype=Object.create(r&&r.prototype)).constructor=t}(m),sl=function(r){function t(t){var i,e;if(r.call(this,{handleDownEvent:hl,handleDragEvent:ll,handleEvent:cl,handleUpEvent:ul}),this.condition_=t.condition?t.condition:ia,this.defaultDeleteCondition_=function(t){return Vs(t)&&Js(t)},this.deleteCondition_=t.deleteCondition?t.deleteCondition:this.defaultDeleteCondition_,this.insertVertexCondition_=t.insertVertexCondition?t.insertVertexCondition:Ks,this.vertexFeature_=null,this.vertexSegments_=null,this.lastPixel_=[0,0],this.ignoreNextSingleClick_=!1,this.modified_=!1,this.rBush_=new Gh,this.pixelTolerance_=void 0!==t.pixelTolerance?t.pixelTolerance:10,this.snappedToVertex_=!1,this.changingFeature_=!1,this.dragSegments_=[],this.overlay_=new lh({source:new Dh({useSpatialIndex:!1,wrapX:!!t.wrapX}),style:t.style?t.style:(i=Zi(),function(t,e){return i[Lt.POINT]}),updateWhileAnimating:!0,updateWhileInteracting:!0}),this.SEGMENT_WRITERS_={Point:this.writePointGeometry_,LineString:this.writeLineStringGeometry_,LinearRing:this.writeLineStringGeometry_,Polygon:this.writePolygonGeometry_,MultiPoint:this.writeMultiPointGeometry_,MultiLineString:this.writeMultiLineStringGeometry_,MultiPolygon:this.writeMultiPolygonGeometry_,Circle:this.writeCircleGeometry_,GeometryCollection:this.writeGeometryCollectionGeometry_},this.source_=null,t.source?(this.source_=t.source,e=new M(this.source_.getFeatures()),E(this.source_,_h,this.handleSourceAdd_,this),E(this.source_,vh,this.handleSourceRemove_,this)):e=t.features,!e)throw new Error("The modify interaction requires features or a source");this.features_=e,this.features_.forEach(this.addFeature_.bind(this)),E(this.features_,h,this.handleFeatureAdd_,this),E(this.features_,l,this.handleFeatureRemove_,this),this.lastPointerEvent_=null}return r&&(t.__proto__=r),((t.prototype=Object.create(r&&r.prototype)).constructor=t).prototype.addFeature_=function(t){var e=t.getGeometry();e&&e.getType()in this.SEGMENT_WRITERS_&&this.SEGMENT_WRITERS_[e.getType()].call(this,t,e);var i=this.getMap();i&&i.isRendered()&&this.getActive()&&this.handlePointerAtPixel_(this.lastPixel_,i),E(t,w.CHANGE,this.handleFeatureChange_,this)},t.prototype.willModifyFeatures_=function(t){this.modified_||(this.modified_=!0,this.dispatchEvent(new ol(nl.MODIFYSTART,this.features_,t)))},t.prototype.removeFeature_=function(t){this.removeFeatureSegmentData_(t),this.vertexFeature_&&0===this.features_.getLength()&&(this.overlay_.getSource().removeFeature(this.vertexFeature_),this.vertexFeature_=null),d(t,w.CHANGE,this.handleFeatureChange_,this)},t.prototype.removeFeatureSegmentData_=function(e){var t=this.rBush_,i=[];t.forEach(function(t){e===t.feature&&i.push(t)});for(var r=i.length-1;0<=r;--r)t.remove(i[r])},t.prototype.setActive=function(t){this.vertexFeature_&&!t&&(this.overlay_.getSource().removeFeature(this.vertexFeature_),this.vertexFeature_=null),r.prototype.setActive.call(this,t)},t.prototype.setMap=function(t){this.overlay_.setMap(t),r.prototype.setMap.call(this,t)},t.prototype.handleSourceAdd_=function(t){t.feature&&this.features_.push(t.feature)},t.prototype.handleSourceRemove_=function(t){t.feature&&this.features_.remove(t.feature)},t.prototype.handleFeatureAdd_=function(t){this.addFeature_(t.element)},t.prototype.handleFeatureChange_=function(t){if(!this.changingFeature_){var e=t.target;this.removeFeature_(e),this.addFeature_(e)}},t.prototype.handleFeatureRemove_=function(t){var e=t.element;this.removeFeature_(e)},t.prototype.writePointGeometry_=function(t,e){var i=e.getCoordinates(),r={feature:t,geometry:e,segment:[i,i]};this.rBush_.insert(e.getExtent(),r)},t.prototype.writeMultiPointGeometry_=function(t,e){for(var i=e.getCoordinates(),r=0,n=i.length;r<n;++r){var o=i[r],s={feature:t,geometry:e,depth:[r],index:r,segment:[o,o]};this.rBush_.insert(e.getExtent(),s)}},t.prototype.writeLineStringGeometry_=function(t,e){for(var i=e.getCoordinates(),r=0,n=i.length-1;r<n;++r){var o=i.slice(r,r+2),s={feature:t,geometry:e,index:r,segment:o};this.rBush_.insert(A(o),s)}},t.prototype.writeMultiLineStringGeometry_=function(t,e){for(var i=e.getCoordinates(),r=0,n=i.length;r<n;++r)for(var o=i[r],s=0,a=o.length-1;s<a;++s){var h=o.slice(s,s+2),l={feature:t,geometry:e,depth:[r],index:s,segment:h};this.rBush_.insert(A(h),l)}},t.prototype.writePolygonGeometry_=function(t,e){for(var i=e.getCoordinates(),r=0,n=i.length;r<n;++r)for(var o=i[r],s=0,a=o.length-1;s<a;++s){var h=o.slice(s,s+2),l={feature:t,geometry:e,depth:[r],index:s,segment:h};this.rBush_.insert(A(h),l)}},t.prototype.writeMultiPolygonGeometry_=function(t,e){for(var i=e.getCoordinates(),r=0,n=i.length;r<n;++r)for(var o=i[r],s=0,a=o.length;s<a;++s)for(var h=o[s],l=0,u=h.length-1;l<u;++l){var c=h.slice(l,l+2),p={feature:t,geometry:e,depth:[s,r],index:l,segment:c};this.rBush_.insert(A(c),p)}},t.prototype.writeCircleGeometry_=function(t,e){var i=e.getCenter(),r={feature:t,geometry:e,index:il,segment:[i,i]},n={feature:t,geometry:e,index:rl,segment:[i,i]},o=[r,n];r.featureSegments=n.featureSegments=o,this.rBush_.insert(V(i),r),this.rBush_.insert(e.getExtent(),n)},t.prototype.writeGeometryCollectionGeometry_=function(t,e){for(var i=e.getGeometriesArray(),r=0;r<i.length;++r)this.SEGMENT_WRITERS_[i[r].getType()].call(this,t,i[r])},t.prototype.createOrUpdateVertexFeature_=function(t){var e=this.vertexFeature_;e?e.getGeometry().setCoordinates(t):(e=new Ji(new Dr(t)),this.vertexFeature_=e,this.overlay_.getSource().addFeature(e));return e},t.prototype.handlePointerMove_=function(t){this.lastPixel_=t.pixel,this.handlePointerAtPixel_(t.pixel,t.map)},t.prototype.handlePointerAtPixel_=function(t,e){var i=e.getCoordinateFromPixel(t),r=G(V(i),e.getView().getResolution()*this.pixelTolerance_),n=this.rBush_.getInExtent(r);if(0<n.length){n.sort(function(t,e){return pl(i,t)-pl(i,e)});var o=n[0],s=o.segment,a=dl(i,o),h=e.getPixelFromCoordinate(a),l=_n(t,h);if(l<=this.pixelTolerance_){var u={};if(o.geometry.getType()===Lt.CIRCLE&&o.index===rl)this.snappedToVertex_=!0,this.createOrUpdateVertexFeature_(a);else{var c=e.getPixelFromCoordinate(s[0]),p=e.getPixelFromCoordinate(s[1]),d=fn(h,c),f=fn(h,p);l=Math.sqrt(Math.min(d,f)),this.snappedToVertex_=l<=this.pixelTolerance_,this.snappedToVertex_&&(a=f<d?s[1]:s[0]),this.createOrUpdateVertexFeature_(a);for(var _=1,g=n.length;_<g;++_){var y=n[_].segment;if(!(cn(s[0],y[0])&&cn(s[1],y[1])||cn(s[0],y[1])&&cn(s[1],y[0])))break;u[Et(y)]=!0}}return u[Et(s)]=!0,void(this.vertexSegments_=u)}}this.vertexFeature_&&(this.overlay_.getSource().removeFeature(this.vertexFeature_),this.vertexFeature_=null)},t.prototype.insertVertex_=function(t,e){for(var i,r=t.segment,n=t.feature,o=t.geometry,s=t.depth,a=t.index;e.length<o.getStride();)e.push(0);switch(o.getType()){case Lt.MULTI_LINE_STRING:case Lt.POLYGON:(i=o.getCoordinates())[s[0]].splice(a+1,0,e);break;case Lt.MULTI_POLYGON:(i=o.getCoordinates())[s[1]][s[0]].splice(a+1,0,e);break;case Lt.LINE_STRING:(i=o.getCoordinates()).splice(a+1,0,e);break;default:return}this.setGeometryCoordinates_(o,i);var h=this.rBush_;h.remove(t),this.updateSegmentIndices_(o,a,s,1);var l={segment:[r[0],e],feature:n,geometry:o,depth:s,index:a};h.insert(A(l.segment),l),this.dragSegments_.push([l,1]);var u={segment:[e,r[1]],feature:n,geometry:o,depth:s,index:a+1};h.insert(A(u.segment),u),this.dragSegments_.push([u,0]),this.ignoreNextSingleClick_=!0},t.prototype.removePoint=function(){if(this.lastPointerEvent_&&this.lastPointerEvent_.type!=qn.POINTERDRAG){var t=this.lastPointerEvent_;return this.willModifyFeatures_(t),this.removeVertex_(),this.dispatchEvent(new ol(nl.MODIFYEND,this.features_,t)),!(this.modified_=!1)}return!1},t.prototype.removeVertex_=function(){var t,e,i,r,n,o,s,a,h,l,u,c=this.dragSegments_,p={},d=!1;for(n=c.length-1;0<=n;--n)u=Et((l=(i=c[n])[0]).feature),l.depth&&(u+="-"+l.depth.join("-")),u in p||(p[u]={}),0===i[1]?(p[u].right=l,p[u].index=l.index):1==i[1]&&(p[u].left=l,p[u].index=l.index+1);for(u in p){switch(h=p[u].right,s=p[u].left,(a=(o=p[u].index)-1)<0&&(a=0),t=e=(r=(l=void 0!==s?s:h).geometry).getCoordinates(),d=!1,r.getType()){case Lt.MULTI_LINE_STRING:2<e[l.depth[0]].length&&(e[l.depth[0]].splice(o,1),d=!0);break;case Lt.LINE_STRING:2<e.length&&(e.splice(o,1),d=!0);break;case Lt.MULTI_POLYGON:t=t[l.depth[1]];case Lt.POLYGON:4<(t=t[l.depth[0]]).length&&(o==t.length-1&&(o=0),t.splice(o,1),d=!0,0===o&&(t.pop(),t.push(t[0]),a=t.length-1))}if(d){this.setGeometryCoordinates_(r,e);var f=[];if(void 0!==s&&(this.rBush_.remove(s),f.push(s.segment[0])),void 0!==h&&(this.rBush_.remove(h),f.push(h.segment[1])),void 0!==s&&void 0!==h){var _={depth:l.depth,feature:l.feature,geometry:l.geometry,index:a,segment:f};this.rBush_.insert(A(_.segment),_)}this.updateSegmentIndices_(r,o,l.depth,-1),this.vertexFeature_&&(this.overlay_.getSource().removeFeature(this.vertexFeature_),this.vertexFeature_=null),c.length=0}}return d},t.prototype.setGeometryCoordinates_=function(t,e){this.changingFeature_=!0,t.setCoordinates(e),this.changingFeature_=!1},t.prototype.updateSegmentIndices_=function(e,i,r,n){this.rBush_.forEachInExtent(e.getExtent(),function(t){t.geometry===e&&(void 0===r||void 0===t.depth||fr(t.depth,r))&&t.index>i&&(t.index+=n)})},t}(aa);function al(t,e){return t.index-e.index}function hl(t){if(!this.condition_(t))return!1;this.handlePointerAtPixel_(t.pixel,t.map);var e=t.map.getCoordinateFromPixel(t.pixel);this.dragSegments_.length=0,this.modified_=!1;var i=this.vertexFeature_;if(i){var r=[],n=i.getGeometry().getCoordinates(),o=A([n]),s=this.rBush_.getInExtent(o),a={};s.sort(al);for(var h=0,l=s.length;h<l;++h){var u=s[h],c=u.segment,p=Et(u.feature),d=u.depth;if(d&&(p+="-"+d.join("-")),a[p]||(a[p]=new Array(2)),u.geometry.getType()===Lt.CIRCLE&&u.index===rl)cn(dl(e,u),n)&&!a[p][0]&&(this.dragSegments_.push([u,0]),a[p][0]=u);else if(cn(c[0],n)&&!a[p][0])this.dragSegments_.push([u,0]),a[p][0]=u;else if(cn(c[1],n)&&!a[p][1]){if((u.geometry.getType()===Lt.LINE_STRING||u.geometry.getType()===Lt.MULTI_LINE_STRING)&&a[p][0]&&0===a[p][0].index)continue;this.dragSegments_.push([u,1]),a[p][1]=u}else this.insertVertexCondition_(t)&&Et(c)in this.vertexSegments_&&!a[p][0]&&!a[p][1]&&r.push([u,n])}r.length&&this.willModifyFeatures_(t);for(var f=r.length-1;0<=f;--f)this.insertVertex_.apply(this,r[f])}return!!this.vertexFeature_}function ll(t){this.ignoreNextSingleClick_=!1,this.willModifyFeatures_(t);for(var e=t.coordinate,i=0,r=this.dragSegments_.length;i<r;++i){for(var n=this.dragSegments_[i],o=n[0],s=o.depth,a=o.geometry,h=void 0,l=o.segment,u=n[1];e.length<a.getStride();)e.push(l[u][e.length]);switch(a.getType()){case Lt.POINT:h=e,l[0]=l[1]=e;break;case Lt.MULTI_POINT:(h=a.getCoordinates())[o.index]=e,l[0]=l[1]=e;break;case Lt.LINE_STRING:(h=a.getCoordinates())[o.index+u]=e,l[u]=e;break;case Lt.MULTI_LINE_STRING:case Lt.POLYGON:(h=a.getCoordinates())[s[0]][o.index+u]=e,l[u]=e;break;case Lt.MULTI_POLYGON:(h=a.getCoordinates())[s[1]][s[0]][o.index+u]=e,l[u]=e;break;case Lt.CIRCLE:l[0]=l[1]=e,o.index===il?(this.changingFeature_=!0,a.setCenter(e)):(this.changingFeature_=!0,a.setRadius(_n(a.getCenter(),e))),this.changingFeature_=!1}h&&this.setGeometryCoordinates_(a,h)}this.createOrUpdateVertexFeature_(e)}function ul(t){for(var e=this.dragSegments_.length-1;0<=e;--e){var i=this.dragSegments_[e][0],r=i.geometry;if(r.getType()===Lt.CIRCLE){var n=r.getCenter(),o=i.featureSegments[0],s=i.featureSegments[1];o.segment[0]=o.segment[1]=n,s.segment[0]=s.segment[1]=n,this.rBush_.update(V(n),o),this.rBush_.update(r.getExtent(),s)}else this.rBush_.update(A(i.segment),i)}return this.modified_&&(this.dispatchEvent(new ol(nl.MODIFYEND,this.features_,t)),this.modified_=!1),!1}function cl(t){return!(t instanceof Jn)||((this.lastPointerEvent_=t).map.getView().getInteracting()||t.type!=qn.POINTERMOVE||this.handlingDownUpSequence||this.handlePointerMove_(t),this.vertexFeature_&&this.deleteCondition_(t)&&(e=!(t.type!=qn.SINGLECLICK||!this.ignoreNextSingleClick_)||this.removePoint()),t.type==qn.SINGLECLICK&&(this.ignoreNextSingleClick_=!1),la.call(this,t)&&!e);var e}function pl(t,e){var i=e.geometry;if(i.getType()===Lt.CIRCLE){var r=i;if(e.index===rl){var n=fn(r.getCenter(),t),o=Math.sqrt(n)-r.getRadius();return o*o}}return gn(t,e.segment)}function dl(t,e){var i=e.geometry;return i.getType()===Lt.CIRCLE&&e.index===rl?i.getClosestPoint(t):hn(t,e.segment)}var fl={SELECT:"select"},_l=function(n){function t(t,e,i,r){n.call(this,t),this.selected=e,this.deselected=i,this.mapBrowserEvent=r}return n&&(t.__proto__=n),(t.prototype=Object.create(n&&n.prototype)).constructor=t}(m),gl=function(a){function t(t){a.call(this,{handleEvent:yl});var e=t||{};this.condition_=e.condition?e.condition:Js,this.addCondition_=e.addCondition?e.addCondition:Zs,this.removeCondition_=e.removeCondition?e.removeCondition:Zs,this.toggleCondition_=e.toggleCondition?e.toggleCondition:$s,this.multi_=!!e.multi&&e.multi,this.filter_=e.filter?e.filter:y,this.hitTolerance_=e.hitTolerance?e.hitTolerance:0;var i,r,n=new lh({source:new Dh({useSpatialIndex:!1,features:e.features,wrapX:e.wrapX}),style:e.style?e.style:(i=Zi(),pr(i[Lt.POLYGON],i[Lt.LINE_STRING]),pr(i[Lt.GEOMETRY_COLLECTION],i[Lt.LINE_STRING]),function(t,e){return t.getGeometry()?i[t.getGeometry().getType()]:null}),updateWhileAnimating:!0,updateWhileInteracting:!0});if(this.featureOverlay_=n,e.layers)if("function"==typeof e.layers)r=e.layers;else{var o=e.layers;r=function(t){return lr(o,t)}}else r=y;this.layerFilter_=r,this.featureLayerAssociation_={};var s=this.featureOverlay_.getSource().getFeaturesCollection();E(s,h,this.addFeature_,this),E(s,l,this.removeFeature_,this)}return a&&(t.__proto__=a),((t.prototype=Object.create(a&&a.prototype)).constructor=t).prototype.addFeatureLayerAssociation_=function(t,e){var i=Et(t);this.featureLayerAssociation_[i]=e},t.prototype.getFeatures=function(){return this.featureOverlay_.getSource().getFeaturesCollection()},t.prototype.getHitTolerance=function(){return this.hitTolerance_},t.prototype.getLayer=function(t){var e=Et(t);return this.featureLayerAssociation_[e]},t.prototype.setHitTolerance=function(t){this.hitTolerance_=t},t.prototype.setMap=function(t){var e=this.getMap(),i=this.featureOverlay_.getSource().getFeaturesCollection();e&&i.forEach(e.unskipFeature.bind(e)),a.prototype.setMap.call(this,t),this.featureOverlay_.setMap(t),t&&i.forEach(t.skipFeature.bind(t))},t.prototype.addFeature_=function(t){var e=this.getMap();e&&e.skipFeature(t.element)},t.prototype.removeFeature_=function(t){var e=this.getMap();e&&e.unskipFeature(t.element)},t.prototype.removeFeatureLayerAssociation_=function(t){var e=Et(t);delete this.featureLayerAssociation_[e]},t}(ks);function yl(t){if(!this.condition_(t))return!0;var i=this.addCondition_(t),r=this.removeCondition_(t),n=this.toggleCondition_(t),e=!i&&!r&&!n,o=t.map,s=this.featureOverlay_.getSource().getFeaturesCollection(),a=[],h=[];if(e){_(this.featureLayerAssociation_),o.forEachFeatureAtPixel(t.pixel,function(t,e){if(this.filter_(t,e))return h.push(t),this.addFeatureLayerAssociation_(t,e),!this.multi_}.bind(this),{layerFilter:this.layerFilter_,hitTolerance:this.hitTolerance_});for(var l=s.getLength()-1;0<=l;--l){var u=s.item(l),c=h.indexOf(u);-1<c?h.splice(c,1):(s.remove(u),a.push(u))}0!==h.length&&s.extend(h)}else{o.forEachFeatureAtPixel(t.pixel,function(t,e){if(this.filter_(t,e))return!i&&!n||lr(s.getArray(),t)?(r||n)&&lr(s.getArray(),t)&&(a.push(t),this.removeFeatureLayerAssociation_(t)):(h.push(t),this.addFeatureLayerAssociation_(t,e)),!this.multi_}.bind(this),{layerFilter:this.layerFilter_,hitTolerance:this.hitTolerance_});for(var p=a.length-1;0<=p;--p)s.remove(a[p]);s.extend(h)}return(0<h.length||0<a.length)&&this.dispatchEvent(new _l(fl.SELECT,h,a,t)),qs(t)}var vl=function(n){function t(t){n.call(this,{handleEvent:ml,handleDownEvent:y,handleUpEvent:xl,stopDown:v});var e=t||{};this.source_=e.source?e.source:null,this.vertex_=void 0===e.vertex||e.vertex,this.edge_=void 0===e.edge||e.edge,this.features_=e.features?e.features:null,this.featuresListenerKeys_=[],this.featureChangeListenerKeys_={},this.indexedFeaturesExtents_={},this.pendingFeatures_={},this.pixelCoordinate_=null,this.pixelTolerance_=void 0!==e.pixelTolerance?e.pixelTolerance:10,this.sortByDistance_=function(t,e){var i=gn(this.pixelCoordinate_,t.segment),r=gn(this.pixelCoordinate_,e.segment);return i-r}.bind(this),this.rBush_=new Gh,this.SEGMENT_WRITERS_={Point:this.writePointGeometry_,LineString:this.writeLineStringGeometry_,LinearRing:this.writeLineStringGeometry_,Polygon:this.writePolygonGeometry_,MultiPoint:this.writeMultiPointGeometry_,MultiLineString:this.writeMultiLineStringGeometry_,MultiPolygon:this.writeMultiPolygonGeometry_,GeometryCollection:this.writeGeometryCollectionGeometry_,Circle:this.writeCircleGeometry_}}return n&&(t.__proto__=n),((t.prototype=Object.create(n&&n.prototype)).constructor=t).prototype.addFeature=function(t,e){var i=void 0===e||e,r=Et(t),n=t.getGeometry();if(n){var o=this.SEGMENT_WRITERS_[n.getType()];o&&(this.indexedFeaturesExtents_[r]=n.getExtent([1/0,1/0,-1/0,-1/0]),o.call(this,t,n))}i&&(this.featureChangeListenerKeys_[r]=E(t,w.CHANGE,this.handleFeatureChange_,this))},t.prototype.forEachFeatureAdd_=function(t){this.addFeature(t)},t.prototype.forEachFeatureRemove_=function(t){this.removeFeature(t)},t.prototype.getFeatures_=function(){var t;return this.features_?t=this.features_:this.source_&&(t=this.source_.getFeatures()),t},t.prototype.handleFeatureAdd_=function(t){var e;t instanceof kh?e=t.feature:t instanceof F&&(e=t.element),this.addFeature(e)},t.prototype.handleFeatureRemove_=function(t){var e;t instanceof kh?e=t.feature:t instanceof F&&(e=t.element),this.removeFeature(e)},t.prototype.handleFeatureChange_=function(t){var e=t.target;if(this.handlingDownUpSequence){var i=Et(e);i in this.pendingFeatures_||(this.pendingFeatures_[i]=e)}else this.updateFeature_(e)},t.prototype.removeFeature=function(e,t){var i=void 0===t||t,r=Et(e),n=this.indexedFeaturesExtents_[r];if(n){var o=this.rBush_,s=[];o.forEachInExtent(n,function(t){e===t.feature&&s.push(t)});for(var a=s.length-1;0<=a;--a)o.remove(s[a])}i&&(g(this.featureChangeListenerKeys_[r]),delete this.featureChangeListenerKeys_[r])},t.prototype.setMap=function(t){var e=this.getMap(),i=this.featuresListenerKeys_,r=this.getFeatures_();e&&(i.forEach(g),i.length=0,r.forEach(this.forEachFeatureRemove_.bind(this))),n.prototype.setMap.call(this,t),t&&(this.features_?i.push(E(this.features_,h,this.handleFeatureAdd_,this),E(this.features_,l,this.handleFeatureRemove_,this)):this.source_&&i.push(E(this.source_,_h,this.handleFeatureAdd_,this),E(this.source_,vh,this.handleFeatureRemove_,this)),r.forEach(this.forEachFeatureAdd_.bind(this)))},t.prototype.snapTo=function(t,e,i){var r=A([i.getCoordinateFromPixel([t[0]-this.pixelTolerance_,t[1]+this.pixelTolerance_]),i.getCoordinateFromPixel([t[0]+this.pixelTolerance_,t[1]-this.pixelTolerance_])]),n=this.rBush_.getInExtent(r);this.vertex_&&!this.edge_&&(n=n.filter(function(t){return t.feature.getGeometry().getType()!==Lt.CIRCLE}));var o,s,a,h,l=!1,u=null,c=null;if(0<n.length){this.pixelCoordinate_=e,n.sort(this.sortByDistance_);var p=n[0].segment,d=n[0].feature.getGeometry().getType()===Lt.CIRCLE;this.vertex_&&!this.edge_?(o=i.getPixelFromCoordinate(p[0]),s=i.getPixelFromCoordinate(p[1]),a=fn(t,o),h=fn(t,s),Math.sqrt(Math.min(a,h))<=this.pixelTolerance_&&(l=!0,u=h<a?p[1]:p[0],c=i.getPixelFromCoordinate(u))):this.edge_&&(u=d?function(t,e){var i=e.getRadius(),r=e.getCenter(),n=r[0],o=r[1],s=t[0]-n,a=t[1]-o;0===s&&0===a&&(s=1);var h=Math.sqrt(s*s+a*a);return[n+i*s/h,o+i*a/h]}(e,n[0].feature.getGeometry()):hn(e,p),_n(t,c=i.getPixelFromCoordinate(u))<=this.pixelTolerance_&&(l=!0,this.vertex_&&!d&&(o=i.getPixelFromCoordinate(p[0]),s=i.getPixelFromCoordinate(p[1]),a=fn(c,o),h=fn(c,s),Math.sqrt(Math.min(a,h))<=this.pixelTolerance_&&(u=h<a?p[1]:p[0],c=i.getPixelFromCoordinate(u))))),l&&(c=[Math.round(c[0]),Math.round(c[1])])}return{snapped:l,vertex:u,vertexPixel:c}},t.prototype.updateFeature_=function(t){this.removeFeature(t,!1),this.addFeature(t,!1)},t.prototype.writeCircleGeometry_=function(t,e){for(var i=en(e).getCoordinates()[0],r=0,n=i.length-1;r<n;++r){var o=i.slice(r,r+2),s={feature:t,segment:o};this.rBush_.insert(A(o),s)}},t.prototype.writeGeometryCollectionGeometry_=function(t,e){for(var i=e.getGeometriesArray(),r=0;r<i.length;++r){var n=this.SEGMENT_WRITERS_[i[r].getType()];n&&n.call(this,t,i[r])}},t.prototype.writeLineStringGeometry_=function(t,e){for(var i=e.getCoordinates(),r=0,n=i.length-1;r<n;++r){var o=i.slice(r,r+2),s={feature:t,segment:o};this.rBush_.insert(A(o),s)}},t.prototype.writeMultiLineStringGeometry_=function(t,e){for(var i=e.getCoordinates(),r=0,n=i.length;r<n;++r)for(var o=i[r],s=0,a=o.length-1;s<a;++s){var h=o.slice(s,s+2),l={feature:t,segment:h};this.rBush_.insert(A(h),l)}},t.prototype.writeMultiPointGeometry_=function(t,e){for(var i=e.getCoordinates(),r=0,n=i.length;r<n;++r){var o=i[r],s={feature:t,segment:[o,o]};this.rBush_.insert(e.getExtent(),s)}},t.prototype.writeMultiPolygonGeometry_=function(t,e){for(var i=e.getCoordinates(),r=0,n=i.length;r<n;++r)for(var o=i[r],s=0,a=o.length;s<a;++s)for(var h=o[s],l=0,u=h.length-1;l<u;++l){var c=h.slice(l,l+2),p={feature:t,segment:c};this.rBush_.insert(A(c),p)}},t.prototype.writePointGeometry_=function(t,e){var i=e.getCoordinates(),r={feature:t,segment:[i,i]};this.rBush_.insert(e.getExtent(),r)},t.prototype.writePolygonGeometry_=function(t,e){for(var i=e.getCoordinates(),r=0,n=i.length;r<n;++r)for(var o=i[r],s=0,a=o.length-1;s<a;++s){var h=o.slice(s,s+2),l={feature:t,segment:h};this.rBush_.insert(A(h),l)}},t}(aa);function ml(t){var e=this.snapTo(t.pixel,t.coordinate,t.map);return e.snapped&&(t.coordinate=e.vertex.slice(0,2),t.pixel=e.vertexPixel),la.call(this,t)}function xl(t){var e=o(this.pendingFeatures_);return e.length&&(e.forEach(this.updateFeature_.bind(this)),this.pendingFeatures_={}),!1}var Sl={TRANSLATESTART:"translatestart",TRANSLATING:"translating",TRANSLATEEND:"translateend"},Cl=function(r){function t(t,e,i){r.call(this,t),this.features=e,this.coordinate=i}return r&&(t.__proto__=r),(t.prototype=Object.create(r&&r.prototype)).constructor=t}(m),El=function(n){function t(t){n.call(this,{handleDownEvent:Tl,handleDragEvent:Rl,handleMoveEvent:Il,handleUpEvent:wl});var e,i=t||{};if(this.lastCoordinate_=null,this.features_=void 0!==i.features?i.features:null,i.layers)if("function"==typeof i.layers)e=i.layers;else{var r=i.layers;e=function(t){return lr(r,t)}}else e=y;this.layerFilter_=e,this.hitTolerance_=i.hitTolerance?i.hitTolerance:0,this.lastFeature_=null,E(this,b(Gs),this.handleActiveChanged_,this)}return n&&(t.__proto__=n),((t.prototype=Object.create(n&&n.prototype)).constructor=t).prototype.featuresAtPixel_=function(t,e){return e.forEachFeatureAtPixel(t,function(t){if(!this.features_||lr(this.features_.getArray(),t))return t}.bind(this),{layerFilter:this.layerFilter_,hitTolerance:this.hitTolerance_})},t.prototype.getHitTolerance=function(){return this.hitTolerance_},t.prototype.setHitTolerance=function(t){this.hitTolerance_=t},t.prototype.setMap=function(t){var e=this.getMap();n.prototype.setMap.call(this,t),this.updateState_(e)},t.prototype.handleActiveChanged_=function(){this.updateState_(null)},t.prototype.updateState_=function(t){var e=this.getMap(),i=this.getActive();e&&i||(e=e||t)&&e.getViewport().classList.remove("ol-grab","ol-grabbing")},t}(aa);function Tl(t){if(this.lastFeature_=this.featuresAtPixel_(t.pixel,t.map),!this.lastCoordinate_&&this.lastFeature_){this.lastCoordinate_=t.coordinate,Il.call(this,t);var e=this.features_||new M([this.lastFeature_]);return this.dispatchEvent(new Cl(Sl.TRANSLATESTART,e,t.coordinate)),!0}return!1}function wl(t){if(this.lastCoordinate_){this.lastCoordinate_=null,Il.call(this,t);var e=this.features_||new M([this.lastFeature_]);return this.dispatchEvent(new Cl(Sl.TRANSLATEEND,e,t.coordinate)),!0}return!1}function Rl(t){if(this.lastCoordinate_){var e=t.coordinate,i=e[0]-this.lastCoordinate_[0],r=e[1]-this.lastCoordinate_[1],n=this.features_||new M([this.lastFeature_]);n.forEach(function(t){var e=t.getGeometry();e.translate(i,r),t.setGeometry(e)}),this.lastCoordinate_=e,this.dispatchEvent(new Cl(Sl.TRANSLATING,n,e))}}function Il(t){var e=t.map.getViewport();this.featuresAtPixel_(t.pixel,t.map)?(e.classList.remove(this.lastCoordinate_?"ol-grab":"ol-grabbing"),e.classList.add(this.lastCoordinate_?"ol-grabbing":"ol-grab")):e.classList.remove("ol-grab","ol-grabbing")}function Ll(t){var e=t||{},i=new M,r=new Kn(-.005,.05,100);return(void 0===e.altShiftDragRotate||e.altShiftDragRotate)&&i.push(new _a),(void 0===e.doubleClickZoom||e.doubleClickZoom)&&i.push(new Xs({delta:e.zoomDelta,duration:e.zoomDuration})),(void 0===e.dragPan||e.dragPan)&&i.push(new ca({kinetic:r})),(void 0===e.pinchRotate||e.pinchRotate)&&i.push(new ka),(void 0===e.pinchZoom||e.pinchZoom)&&i.push(new Ya({constrainResolution:e.constrainResolution,duration:e.zoomDuration})),(void 0===e.keyboard||e.keyboard)&&(i.push(new Pa),i.push(new Ma({delta:e.zoomDelta,duration:e.zoomDuration}))),(void 0===e.mouseWheelZoom||e.mouseWheelZoom)&&i.push(new Aa({constrainResolution:e.constrainResolution,duration:e.zoomDuration})),(void 0===e.shiftDragZoom||e.shiftDragZoom)&&i.push(new Ia({duration:e.zoomDuration})),i}var bl=function(s){function t(t,e,i,r,n){var o=void 0!==n?di.IDLE:di.LOADED;s.call(this,t,e,i,o),this.loader_=void 0!==n?n:null,this.canvas_=r,this.error_=null}return s&&(t.__proto__=s),((t.prototype=Object.create(s&&s.prototype)).constructor=t).prototype.getError=function(){return this.error_},t.prototype.handleLoad_=function(t){t?(this.error_=t,this.state=di.ERROR):this.state=di.LOADED,this.changed()},t.prototype.load=function(){this.state==di.IDLE&&(this.state=di.LOADING,this.changed(),this.loader_(this.handleLoad_.bind(this)))},t.prototype.getImage=function(){return this.canvas_},t}(Mn),Pl=function(o){function t(t,e,i,r,n){o.call(this,t),this.vectorContext=e,this.frameState=i,this.context=r,this.glContext=n}return o&&(t.__proto__=o),(t.prototype=Object.create(o&&o.prototype)).constructor=t}(m),Fl=function(){};Fl.prototype.drawCustom=function(t,e,i){},Fl.prototype.drawGeometry=function(t){},Fl.prototype.setStyle=function(t){},Fl.prototype.drawCircle=function(t,e){},Fl.prototype.drawFeature=function(t,e){},Fl.prototype.drawGeometryCollection=function(t,e){},Fl.prototype.drawLineString=function(t,e){},Fl.prototype.drawMultiLineString=function(t,e){},Fl.prototype.drawMultiPoint=function(t,e){},Fl.prototype.drawMultiPolygon=function(t,e){},Fl.prototype.drawPoint=function(t,e){},Fl.prototype.drawPolygon=function(t,e){},Fl.prototype.drawText=function(t,e){},Fl.prototype.setFillStrokeStyle=function(t,e){},Fl.prototype.setImageStyle=function(t,e){},Fl.prototype.setTextStyle=function(t,e){};var Ml=function(o){function t(t,e,i,r,n){o.call(this),this.context_=t,this.pixelRatio_=e,this.extent_=i,this.transform_=r,this.viewRotation_=n,this.contextFillState_=null,this.contextStrokeState_=null,this.contextTextState_=null,this.fillState_=null,this.strokeState_=null,this.image_=null,this.imageAnchorX_=0,this.imageAnchorY_=0,this.imageHeight_=0,this.imageOpacity_=0,this.imageOriginX_=0,this.imageOriginY_=0,this.imageRotateWithView_=!1,this.imageRotation_=0,this.imageScale_=0,this.imageSnapToPixel_=!1,this.imageWidth_=0,this.text_="",this.textOffsetX_=0,this.textOffsetY_=0,this.textRotateWithView_=!1,this.textRotation_=0,this.textScale_=0,this.textFillState_=null,this.textStrokeState_=null,this.textState_=null,this.pixelCoordinates_=[],this.tmpLocalTransform_=[1,0,0,1,0,0]}return o&&(t.__proto__=o),((t.prototype=Object.create(o&&o.prototype)).constructor=t).prototype.drawImages_=function(t,e,i,r){var n=this;if(this.image_){var o=Rt(t,e,i,2,this.transform_,this.pixelCoordinates_),s=this.context_,a=this.tmpLocalTransform_,h=s.globalAlpha;1!=this.imageOpacity_&&(s.globalAlpha=h*this.imageOpacity_);var l=this.imageRotation_;this.imageRotateWithView_&&(l+=this.viewRotation_);for(var u=0,c=o.length;u<c;u+=2){var p=o[u]-n.imageAnchorX_,d=o[u+1]-n.imageAnchorY_;if(n.imageSnapToPixel_&&(p=Math.round(p),d=Math.round(d)),0!==l||1!=n.imageScale_){var f=p+n.imageAnchorX_,_=d+n.imageAnchorY_;Te(a,f,_,n.imageScale_,n.imageScale_,l,-f,-_),s.setTransform.apply(s,a)}s.drawImage(n.image_,n.imageOriginX_,n.imageOriginY_,n.imageWidth_,n.imageHeight_,p,d,n.imageWidth_,n.imageHeight_)}0===l&&1==this.imageScale_||s.setTransform(1,0,0,1,0,0),1!=this.imageOpacity_&&(s.globalAlpha=h)}},t.prototype.drawText_=function(t,e,i,r){var n=this;if(this.textState_&&""!==this.text_){this.textFillState_&&this.setContextFillState_(this.textFillState_),this.textStrokeState_&&this.setContextStrokeState_(this.textStrokeState_),this.setContextTextState_(this.textState_);var o=Rt(t,e,i,r,this.transform_,this.pixelCoordinates_),s=this.context_,a=this.textRotation_;for(this.textRotateWithView_&&(a+=this.viewRotation_);e<i;e+=r){var h=o[e]+n.textOffsetX_,l=o[e+1]+n.textOffsetY_;if(0!==a||1!=n.textScale_){var u=Te(n.tmpLocalTransform_,h,l,n.textScale_,n.textScale_,a,-h,-l);s.setTransform.apply(s,u)}n.textStrokeState_&&s.strokeText(n.text_,h,l),n.textFillState_&&s.fillText(n.text_,h,l)}0===a&&1==this.textScale_||s.setTransform(1,0,0,1,0,0)}},t.prototype.moveToLineTo_=function(t,e,i,r,n){var o=this.context_,s=Rt(t,e,i,r,this.transform_,this.pixelCoordinates_);o.moveTo(s[0],s[1]);var a=s.length;n&&(a-=2);for(var h=2;h<a;h+=2)o.lineTo(s[h],s[h+1]);return n&&o.closePath(),i},t.prototype.drawRings_=function(t,e,i,r){for(var n=0,o=i.length;n<o;++n)e=this.moveToLineTo_(t,e,i[n],r,!0);return e},t.prototype.drawCircle=function(t){if(wt(this.extent_,t.getExtent())){if(this.fillState_||this.strokeState_){this.fillState_&&this.setContextFillState_(this.fillState_),this.strokeState_&&this.setContextStrokeState_(this.strokeState_);var e=function(t,e,i){var r=t.getFlatCoordinates();if(r){var n=t.getStride();return Rt(r,0,r.length,n,e,i)}return null}(t,this.transform_,this.pixelCoordinates_),i=e[2]-e[0],r=e[3]-e[1],n=Math.sqrt(i*i+r*r),o=this.context_;o.beginPath(),o.arc(e[0],e[1],n,0,2*Math.PI),this.fillState_&&o.fill(),this.strokeState_&&o.stroke()}""!==this.text_&&this.drawText_(t.getCenter(),0,2,2)}},t.prototype.setStyle=function(t){this.setFillStrokeStyle(t.getFill(),t.getStroke()),this.setImageStyle(t.getImage()),this.setTextStyle(t.getText())},t.prototype.drawGeometry=function(t){switch(t.getType()){case Lt.POINT:this.drawPoint(t);break;case Lt.LINE_STRING:this.drawLineString(t);break;case Lt.POLYGON:this.drawPolygon(t);break;case Lt.MULTI_POINT:this.drawMultiPoint(t);break;case Lt.MULTI_LINE_STRING:this.drawMultiLineString(t);break;case Lt.MULTI_POLYGON:this.drawMultiPolygon(t);break;case Lt.GEOMETRY_COLLECTION:this.drawGeometryCollection(t);break;case Lt.CIRCLE:this.drawCircle(t)}},t.prototype.drawFeature=function(t,e){var i=e.getGeometryFunction()(t);i&&wt(this.extent_,i.getExtent())&&(this.setStyle(e),this.drawGeometry(i))},t.prototype.drawGeometryCollection=function(t){for(var e=t.getGeometriesArray(),i=0,r=e.length;i<r;++i)this.drawGeometry(e[i])},t.prototype.drawPoint=function(t){var e=t.getFlatCoordinates(),i=t.getStride();this.image_&&this.drawImages_(e,0,e.length,i),""!==this.text_&&this.drawText_(e,0,e.length,i)},t.prototype.drawMultiPoint=function(t){var e=t.getFlatCoordinates(),i=t.getStride();this.image_&&this.drawImages_(e,0,e.length,i),""!==this.text_&&this.drawText_(e,0,e.length,i)},t.prototype.drawLineString=function(t){if(wt(this.extent_,t.getExtent())){if(this.strokeState_){this.setContextStrokeState_(this.strokeState_);var e=this.context_,i=t.getFlatCoordinates();e.beginPath(),this.moveToLineTo_(i,0,i.length,t.getStride(),!1),e.stroke()}if(""!==this.text_){var r=t.getFlatMidpoint();this.drawText_(r,0,2,2)}}},t.prototype.drawMultiLineString=function(t){var e=t.getExtent();if(wt(this.extent_,e)){if(this.strokeState_){this.setContextStrokeState_(this.strokeState_);var i=this.context_,r=t.getFlatCoordinates(),n=0,o=t.getEnds(),s=t.getStride();i.beginPath();for(var a=0,h=o.length;a<h;++a)n=this.moveToLineTo_(r,n,o[a],s,!1);i.stroke()}if(""!==this.text_){var l=t.getFlatMidpoints();this.drawText_(l,0,l.length,2)}}},t.prototype.drawPolygon=function(t){if(wt(this.extent_,t.getExtent())){if(this.strokeState_||this.fillState_){this.fillState_&&this.setContextFillState_(this.fillState_),this.strokeState_&&this.setContextStrokeState_(this.strokeState_);var e=this.context_;e.beginPath(),this.drawRings_(t.getOrientedFlatCoordinates(),0,t.getEnds(),t.getStride()),this.fillState_&&e.fill(),this.strokeState_&&e.stroke()}if(""!==this.text_){var i=t.getFlatInteriorPoint();this.drawText_(i,0,2,2)}}},t.prototype.drawMultiPolygon=function(t){if(wt(this.extent_,t.getExtent())){if(this.strokeState_||this.fillState_){this.fillState_&&this.setContextFillState_(this.fillState_),this.strokeState_&&this.setContextStrokeState_(this.strokeState_);var e=this.context_,i=t.getOrientedFlatCoordinates(),r=0,n=t.getEndss(),o=t.getStride();e.beginPath();for(var s=0,a=n.length;s<a;++s){var h=n[s];r=this.drawRings_(i,r,h,o)}this.fillState_&&e.fill(),this.strokeState_&&e.stroke()}if(""!==this.text_){var l=t.getFlatInteriorPoints();this.drawText_(l,0,l.length,2)}}},t.prototype.setContextFillState_=function(t){var e=this.context_,i=this.contextFillState_;i?i.fillStyle!=t.fillStyle&&(i.fillStyle=e.fillStyle=t.fillStyle):(e.fillStyle=t.fillStyle,this.contextFillState_={fillStyle:t.fillStyle})},t.prototype.setContextStrokeState_=function(t){var e=this.context_,i=this.contextStrokeState_;i?(i.lineCap!=t.lineCap&&(i.lineCap=e.lineCap=t.lineCap),hi&&(fr(i.lineDash,t.lineDash)||e.setLineDash(i.lineDash=t.lineDash),i.lineDashOffset!=t.lineDashOffset&&(i.lineDashOffset=e.lineDashOffset=t.lineDashOffset)),i.lineJoin!=t.lineJoin&&(i.lineJoin=e.lineJoin=t.lineJoin),i.lineWidth!=t.lineWidth&&(i.lineWidth=e.lineWidth=t.lineWidth),i.miterLimit!=t.miterLimit&&(i.miterLimit=e.miterLimit=t.miterLimit),i.strokeStyle!=t.strokeStyle&&(i.strokeStyle=e.strokeStyle=t.strokeStyle)):(e.lineCap=t.lineCap,hi&&(e.setLineDash(t.lineDash),e.lineDashOffset=t.lineDashOffset),e.lineJoin=t.lineJoin,e.lineWidth=t.lineWidth,e.miterLimit=t.miterLimit,e.strokeStyle=t.strokeStyle,this.contextStrokeState_={lineCap:t.lineCap,lineDash:t.lineDash,lineDashOffset:t.lineDashOffset,lineJoin:t.lineJoin,lineWidth:t.lineWidth,miterLimit:t.miterLimit,strokeStyle:t.strokeStyle})},t.prototype.setContextTextState_=function(t){var e=this.context_,i=this.contextTextState_,r=t.textAlign?t.textAlign:Ri;i?(i.font!=t.font&&(i.font=e.font=t.font),i.textAlign!=r&&(i.textAlign=e.textAlign=r),i.textBaseline!=t.textBaseline&&(i.textBaseline=e.textBaseline=t.textBaseline)):(e.font=t.font,e.textAlign=r,e.textBaseline=t.textBaseline,this.contextTextState_={font:t.font,textAlign:r,textBaseline:t.textBaseline})},t.prototype.setFillStrokeStyle=function(t,e){if(t){var i=t.getColor();this.fillState_={fillStyle:ke(i||Si)}}else this.fillState_=null;if(e){var r=e.getColor(),n=e.getLineCap(),o=e.getLineDash(),s=e.getLineDashOffset(),a=e.getLineJoin(),h=e.getWidth(),l=e.getMiterLimit();this.strokeState_={lineCap:void 0!==n?n:Ci,lineDash:o||Ei,lineDashOffset:s||0,lineJoin:void 0!==a?a:Ti,lineWidth:this.pixelRatio_*(void 0!==h?h:1),miterLimit:void 0!==l?l:10,strokeStyle:ke(r||wi)}}else this.strokeState_=null},t.prototype.setImageStyle=function(t){if(t){var e=t.getAnchor(),i=t.getImage(1),r=t.getOrigin(),n=t.getSize();this.imageAnchorX_=e[0],this.imageAnchorY_=e[1],this.imageHeight_=n[1],this.image_=i,this.imageOpacity_=t.getOpacity(),this.imageOriginX_=r[0],this.imageOriginY_=r[1],this.imageRotateWithView_=t.getRotateWithView(),this.imageRotation_=t.getRotation(),this.imageScale_=t.getScale()*this.pixelRatio_,this.imageSnapToPixel_=t.getSnapToPixel(),this.imageWidth_=n[0]}else this.image_=null},t.prototype.setTextStyle=function(t){if(t){var e=t.getFill();if(e){var i=e.getColor();this.textFillState_={fillStyle:ke(i||Si)}}else this.textFillState_=null;var r=t.getStroke();if(r){var n=r.getColor(),o=r.getLineCap(),s=r.getLineDash(),a=r.getLineDashOffset(),h=r.getLineJoin(),l=r.getWidth(),u=r.getMiterLimit();this.textStrokeState_={lineCap:void 0!==o?o:Ci,lineDash:s||Ei,lineDashOffset:a||0,lineJoin:void 0!==h?h:Ti,lineWidth:void 0!==l?l:1,miterLimit:void 0!==u?u:10,strokeStyle:ke(n||wi)}}else this.textStrokeState_=null;var c=t.getFont(),p=t.getOffsetX(),d=t.getOffsetY(),f=t.getRotateWithView(),_=t.getRotation(),g=t.getScale(),y=t.getText(),v=t.getTextAlign(),m=t.getTextBaseline();this.textState_={font:void 0!==c?c:xi,textAlign:void 0!==v?v:Ri,textBaseline:void 0!==m?m:"middle"},this.text_=void 0!==y?y:"",this.textOffsetX_=void 0!==p?this.pixelRatio_*p:0,this.textOffsetY_=void 0!==d?this.pixelRatio_*d:0,this.textRotateWithView_=void 0!==f&&f,this.textRotation_=void 0!==_?_:0,this.textScale_=this.pixelRatio_*(void 0!==g?g:1)}else this.text_=""},t}(Fl),Ol=function(){this.cache_={},this.cacheSize_=0,this.maxCacheSize_=32};function Nl(t,e,i){return e+":"+t+":"+(i?Pe(i):"null")}Ol.prototype.clear=function(){this.cache_={},this.cacheSize_=0},Ol.prototype.expire=function(){if(this.cacheSize_>this.maxCacheSize_){var t=0;for(var e in this.cache_){var i=this.cache_[e];0!=(3&t++)||i.hasListener()||(delete this.cache_[e],--this.cacheSize_)}}},Ol.prototype.get=function(t,e,i){var r=Nl(t,e,i);return r in this.cache_?this.cache_[r]:null},Ol.prototype.set=function(t,e,i,r){var n=Nl(t,e,i);this.cache_[n]=r,++this.cacheSize_},Ol.prototype.setSize=function(t){this.maxCacheSize_=t,this.expire()};var Al=new Ol,Gl=function(e){function t(t){e.call(this),this.map_=t,this.layerRenderers_={},this.layerRendererListeners_={},this.layerRendererConstructors_=[]}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.registerLayerRenderers=function(t){this.layerRendererConstructors_.push.apply(this.layerRendererConstructors_,t)},t.prototype.getLayerRendererConstructors=function(){return this.layerRendererConstructors_},t.prototype.calculateMatrices2D=function(t){var e=t.viewState,i=t.coordinateToPixelTransform,r=t.pixelToCoordinateTransform;Te(i,t.size[0]/2,t.size[1]/2,1/e.resolution,-1/e.resolution,-e.rotation,-e.center[0],-e.center[1]),we(me(r,i))},t.prototype.removeLayerRenderers=function(){for(var t in this.layerRenderers_)this.removeLayerRendererByKey_(t).dispose()},t.prototype.forEachFeatureAtCoordinate=function(t,n,e,o,s,i,r){var a,h=n.viewState,l=h.resolution;function u(t,e){var i=Et(t).toString(),r=n.layerStates[Et(e)].managed;if(!(i in n.skippedFeatureUids)||r)return o.call(s,t,r?e:null)}var c=h.projection,p=t;if(c.canWrapX()){var d=c.getExtent(),f=ct(d),_=t[0];if(_<d[0]||_>d[2])p=[_+f*Math.ceil((d[0]-_)/f),t[1]]}var g,y=n.layerStatesArray;for(g=y.length-1;0<=g;--g){var v=y[g],m=v.layer;if(bs(v,l)&&i.call(r,m)){var x=this.getLayerRenderer(m);if(m.getSource()&&(a=x.forEachFeatureAtCoordinate(m.getSource().getWrapX()?p:t,n,e,u,s)),a)return a}}},t.prototype.forEachLayerAtPixel=function(t,e,i,r,n,o,s){},t.prototype.hasFeatureAtCoordinate=function(t,e,i,r,n){return void 0!==this.forEachFeatureAtCoordinate(t,e,i,y,this,r,n)},t.prototype.getLayerRenderer=function(t){var e=Et(t).toString();if(e in this.layerRenderers_)return this.layerRenderers_[e];for(var i,r=0,n=this.layerRendererConstructors_.length;r<n;++r){var o=this.layerRendererConstructors_[r];if(o.handles(t)){i=o.create(this,t);break}}if(!i)throw new Error("Unable to create renderer for layer: "+t.getType());return this.layerRenderers_[e]=i,this.layerRendererListeners_[e]=E(i,w.CHANGE,this.handleLayerRendererChange_,this),i},t.prototype.getLayerRendererByKey=function(t){return this.layerRenderers_[t]},t.prototype.getLayerRenderers=function(){return this.layerRenderers_},t.prototype.getMap=function(){return this.map_},t.prototype.handleLayerRendererChange_=function(){this.map_.render()},t.prototype.removeLayerRendererByKey_=function(t){var e=this.layerRenderers_[t];return delete this.layerRenderers_[t],g(this.layerRendererListeners_[t]),delete this.layerRendererListeners_[t],e},t.prototype.removeUnusedLayerRenderers_=function(t,e){for(var i in this.layerRenderers_)e&&i in e.layerStates||this.removeLayerRendererByKey_(i).dispose()},t.prototype.scheduleExpireIconCache=function(t){t.postRenderFunctions.push(kl)},t.prototype.scheduleRemoveUnusedLayerRenderers=function(t){for(var e in this.layerRenderers_)if(!(e in t.layerStates))return void t.postRenderFunctions.push(this.removeUnusedLayerRenderers_.bind(this))},t}(t);function kl(t,e){Al.expire()}function Dl(t,e){return t.zIndex-e.zIndex}Gl.prototype.renderFrame=L;var jl=[],Ul=function(n){function t(t){n.call(this,t);var e=t.getViewport();this.context_=De(),this.canvas_=this.context_.canvas,this.canvas_.style.width="100%",this.canvas_.style.height="100%",this.canvas_.style.display="block",this.canvas_.className=_i,e.insertBefore(this.canvas_,e.childNodes[0]||null),this.renderedVisible_=!0,this.transform_=[1,0,0,1,0,0]}return n&&(t.__proto__=n),((t.prototype=Object.create(n&&n.prototype)).constructor=t).prototype.dispatchComposeEvent_=function(t,e){var i=this.getMap(),r=this.context_;if(i.hasListener(t)){var n=e.extent,o=e.pixelRatio,s=e.viewState.rotation,a=this.getTransform(e),h=new Ml(r,o,n,a,s),l=new Pl(t,h,e,r,null);i.dispatchEvent(l)}},t.prototype.getTransform=function(t){var e=t.viewState,i=this.canvas_.width/2,r=this.canvas_.height/2,n=t.pixelRatio/e.resolution,o=-n,s=-e.rotation,a=-e.center[0],h=-e.center[1];return Te(this.transform_,i,r,n,o,s,a,h)},t.prototype.renderFrame=function(t){if(t){var e=this.context_,i=t.pixelRatio,r=Math.round(t.size[0]*i),n=Math.round(t.size[1]*i);this.canvas_.width!=r||this.canvas_.height!=n?(this.canvas_.width=r,this.canvas_.height=n):e.clearRect(0,0,r,n);var o=t.viewState.rotation;this.calculateMatrices2D(t),this.dispatchComposeEvent_(Tn,t);var s=t.layerStatesArray;_r(s,Dl),o&&(e.save(),Di(e,o,r/2,n/2));var a,h,l,u,c,p=t.viewState.resolution;for(a=0,h=s.length;a<h;++a)l=(c=s[a]).layer,u=this.getLayerRenderer(l),bs(c,p)&&c.sourceState==ms&&u.prepareFrame(t,c)&&u.composeFrame(t,c,e);o&&e.restore(),this.dispatchComposeEvent_(En,t),this.renderedVisible_||(this.canvas_.style.display="",this.renderedVisible_=!0),this.scheduleRemoveUnusedLayerRenderers(t),this.scheduleExpireIconCache(t)}else this.renderedVisible_&&(this.canvas_.style.display="none",this.renderedVisible_=!1)},t.prototype.forEachLayerAtPixel=function(t,e,i,r,n,o,s){var a,h,l=e.viewState.resolution,u=e.layerStatesArray,c=u.length,p=xe(e.pixelToCoordinateTransform,t.slice());for(h=c-1;0<=h;--h){var d=u[h],f=d.layer;if(bs(d,l)&&o.call(s,f))if(a=this.getLayerRenderer(f).forEachLayerAtCoordinate(p,e,i,r,n))return a}},t.prototype.registerLayerRenderers=function(t){n.prototype.registerLayerRenderers.call(this,t);for(var e=0,i=t.length;e<i;++e){var r=t[e];lr(jl,r)||jl.push(r)}},t}(Gl),Yl=function(e){function t(t){e.call(this),this.layer_=t}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.createLoadedTileFinder=function(i,r,n){return function(e,t){return i.forEachLoadedTile(r,e,t,function(t){n[e]||(n[e]={}),n[e][t.tileCoord.toString()]=t})}},t.prototype.getLayer=function(){return this.layer_},t.prototype.handleImageChange_=function(t){t.target.getState()===di.LOADED&&this.renderIfReadyAndVisible()},t.prototype.loadImage=function(t){var e=t.getState();return e!=di.LOADED&&e!=di.ERROR&&E(t,w.CHANGE,this.handleImageChange_,this),e==di.IDLE&&(t.load(),e=t.getState()),e==di.LOADED},t.prototype.renderIfReadyAndVisible=function(){var t=this.getLayer();t.getVisible()&&t.getSourceState()==ms&&this.changed()},t.prototype.scheduleExpireCache=function(t,e){if(e.canExpireCache()){var i=function(t,e,i){var r=Et(t).toString();r in i.usedTiles&&t.expireCache(i.viewState.projection,i.usedTiles[r])}.bind(null,e);t.postRenderFunctions.push(i)}},t.prototype.updateUsedTiles=function(t,e,i,r){var n=Et(e).toString(),o=i.toString();n in t?o in t[n]?t[n][o].extend(r):t[n][o]=r:(t[n]={},t[n][o]=r)},t.prototype.manageTilePyramid=function(t,e,i,r,n,o,s,a,h,l){var u=Et(e).toString();u in t.wantedTiles||(t.wantedTiles[u]={});var c,p,d,f,_,g,y=t.wantedTiles[u],v=t.tileQueue;for(g=i.getMinZoom();g<=s;++g)for(p=i.getTileRangeForExtentAndZ(o,g,p),d=i.getResolution(g),f=p.minX;f<=p.maxX;++f)for(_=p.minY;_<=p.maxY;++_)s-g<=a?((c=e.getTile(g,f,_,r,n)).getState()==Nn&&(y[c.getKey()]=!0,v.isKeyQueued(c.getKey())||v.enqueue([c,u,i.getTileCoordCenter(c.tileCoord),d])),void 0!==h&&h.call(l,c)):e.useTile(g,f,_,n)},t}(S);Yl.prototype.forEachFeatureAtCoordinate=L,Yl.prototype.hasFeatureAtCoordinate=v;var Bl=function(e){function t(t){e.call(this,t),this.renderedResolution,this.transform_=[1,0,0,1,0,0]}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.clip=function(t,e,i){var r=e.pixelRatio,n=e.size[0]*r,o=e.size[1]*r,s=e.viewState.rotation,a=lt(i),h=ut(i),l=nt(i),u=rt(i);xe(e.coordinateToPixelTransform,a),xe(e.coordinateToPixelTransform,h),xe(e.coordinateToPixelTransform,l),xe(e.coordinateToPixelTransform,u),t.save(),Di(t,-s,n/2,o/2),t.beginPath(),t.moveTo(a[0]*r,a[1]*r),t.lineTo(h[0]*r,h[1]*r),t.lineTo(l[0]*r,l[1]*r),t.lineTo(u[0]*r,u[1]*r),t.clip(),Di(t,s,n/2,o/2)},t.prototype.dispatchComposeEvent_=function(t,e,i,r){var n=this.getLayer();if(n.hasListener(t)){var o=i.size[0]*i.pixelRatio,s=i.size[1]*i.pixelRatio,a=i.viewState.rotation;Di(e,-a,o/2,s/2);var h=void 0!==r?r:this.getTransform(i,0),l=new Ml(e,i.pixelRatio,i.extent,h,i.viewState.rotation),u=new Pl(t,l,i,e,null);n.dispatchEvent(u),Di(e,a,o/2,s/2)}},t.prototype.forEachLayerAtCoordinate=function(t,e,i,r,n){return this.forEachFeatureAtCoordinate(t,e,i,y,this)?r.call(n,this.getLayer(),null):void 0},t.prototype.postCompose=function(t,e,i,r){this.dispatchComposeEvent_(En,t,e,r)},t.prototype.preCompose=function(t,e,i){this.dispatchComposeEvent_(Tn,t,e,i)},t.prototype.dispatchRenderEvent=function(t,e,i){this.dispatchComposeEvent_(wn,t,e,i)},t.prototype.getTransform=function(t,e){var i=t.viewState,r=t.pixelRatio,n=r*t.size[0]/2,o=r*t.size[1]/2,s=r/i.resolution,a=-s,h=-i.rotation,l=-i.center[0]+e,u=-i.center[1];return Te(this.transform_,n,o,s,a,h,l,u)},t.prototype.composeFrame=function(t,e,i){},t.prototype.prepareFrame=function(t,e){},t}(Yl),Xl=function(a){function t(t){a.call(this,t),this.coordinateToCanvasPixelTransform=[1,0,0,1,0,0],this.hitCanvasContext_=null}return a&&(t.__proto__=a),((t.prototype=Object.create(a&&a.prototype)).constructor=t).prototype.composeFrame=function(t,e,i){this.preCompose(i,t);var r=this.getImage();if(r){var n=e.extent,o=void 0!==n&&!Q(n,t.extent)&&wt(n,t.extent);o&&this.clip(i,t,n);var s=this.getImageTransform(),a=i.globalAlpha;i.globalAlpha=e.opacity;var h=s[4],l=s[5],u=r.width*s[0],c=r.height*s[3];i.drawImage(r,0,0,+r.width,+r.height,Math.round(h),Math.round(l),Math.round(u),Math.round(c)),i.globalAlpha=a,o&&i.restore()}this.postCompose(i,t,e)},t.prototype.getImage=function(){},t.prototype.getImageTransform=function(){},t.prototype.forEachFeatureAtCoordinate=function(t,e,i,r,n){var o=this.getLayer(),s=o.getSource(),a=e.viewState.resolution,h=e.viewState.rotation,l=e.skippedFeatureUids;return s.forEachFeatureAtCoordinate(t,a,h,i,l,function(t){return r.call(n,t,o)})},t.prototype.forEachLayerAtCoordinate=function(t,e,i,r,n){if(this.getImage()){if(this.getLayer().getSource().forEachFeatureAtCoordinate!==L)return a.prototype.forEachLayerAtCoordinate.apply(this,arguments);var o=xe(this.coordinateToCanvasPixelTransform,t.slice());dn(o,e.viewState.resolution/this.renderedResolution),this.hitCanvasContext_||(this.hitCanvasContext_=De(1,1)),this.hitCanvasContext_.clearRect(0,0,1,1),this.hitCanvasContext_.drawImage(this.getImage(),o[0],o[1],1,1,0,0,1,1);var s=this.hitCanvasContext_.getImageData(0,0,1,1).data;return 0<s[3]?r.call(n,this.getLayer(),s):void 0}},t}(Bl),zl=function(o){function n(t){if(o.call(this,t),this.image_=null,this.imageTransform_=[1,0,0,1,0,0],this.skippedFeatures_=[],this.vectorRenderer_=null,t.getType()===oh.VECTOR)for(var e=0,i=jl.length;e<i;++e){var r=jl[e];if(r!==n&&r.handles(t)){this.vectorRenderer_=new r(t);break}}}return o&&(n.__proto__=o),((n.prototype=Object.create(o&&o.prototype)).constructor=n).prototype.disposeInternal=function(){this.vectorRenderer_&&this.vectorRenderer_.dispose(),o.prototype.disposeInternal.call(this)},n.prototype.getImage=function(){return this.image_?this.image_.getImage():null},n.prototype.getImageTransform=function(){return this.imageTransform_},n.prototype.prepareFrame=function(t,e){var i,r=t.pixelRatio,n=t.size,o=t.viewState,s=o.center,a=o.resolution,h=this.getLayer().getSource(),l=t.viewHints,u=this.vectorRenderer_,c=t.extent;if(u||void 0===e.extent||(c=ht(c,e.extent)),!l[rs.ANIMATING]&&!l[rs.INTERACTING]&&!pt(c)){var p=o.projection,d=this.skippedFeatures_;if(u){var f=u.context,_=C({},t,{size:[ct(c)/a,at(c)/a],viewState:C({},t.viewState,{rotation:0})}),g=Object.keys(_.skippedFeatureUids).sort();i=new bl(c,a,r,f.canvas,function(t){!u.prepareFrame(_,e)||!u.replayGroupChanged&&fr(d,g)||(f.canvas.width=_.size[0]*r,f.canvas.height=_.size[1]*r,u.compose(f,_,e),d=g,t())})}else i=h.getImage(c,a,r,p);i&&this.loadImage(i)&&(this.image_=i,this.skippedFeatures_=d)}if(this.image_){var y=(i=this.image_).getExtent(),v=i.getResolution(),m=i.getPixelRatio(),x=r*v/(a*m),S=Te(this.imageTransform_,r*n[0]/2,r*n[1]/2,x,x,0,m*(y[0]-s[0])/v,m*(s[1]-y[3])/v);Te(this.coordinateToCanvasPixelTransform,r*n[0]/2-S[4],r*n[1]/2-S[5],r/a,-r/a,0,-s[0],-s[1]),this.renderedResolution=v*r/m}return!!this.image_},n.prototype.forEachFeatureAtCoordinate=function(t,e,i,r,n){return this.vectorRenderer_?this.vectorRenderer_.forEachFeatureAtCoordinate(t,e,i,r,n):o.prototype.forEachFeatureAtCoordinate.call(this,t,e,i,r,n)},n}(Xl);zl.handles=function(t){return t.getType()===oh.IMAGE||t.getType()===oh.VECTOR&&t.getRenderMode()===sh},zl.create=function(t,e){return new zl(e)};var Vl=function(t,e,i,r){this.minX=t,this.maxX=e,this.minY=i,this.maxY=r};function Wl(t,e,i,r,n){return void 0!==n?(n.minX=t,n.maxX=e,n.minY=i,n.maxY=r,n):new Vl(t,e,i,r)}Vl.prototype.contains=function(t){return this.containsXY(t[1],t[2])},Vl.prototype.containsTileRange=function(t){return this.minX<=t.minX&&t.maxX<=this.maxX&&this.minY<=t.minY&&t.maxY<=this.maxY},Vl.prototype.containsXY=function(t,e){return this.minX<=t&&t<=this.maxX&&this.minY<=e&&e<=this.maxY},Vl.prototype.equals=function(t){return this.minX==t.minX&&this.minY==t.minY&&this.maxX==t.maxX&&this.maxY==t.maxY},Vl.prototype.extend=function(t){t.minX<this.minX&&(this.minX=t.minX),t.maxX>this.maxX&&(this.maxX=t.maxX),t.minY<this.minY&&(this.minY=t.minY),t.maxY>this.maxY&&(this.maxY=t.maxY)},Vl.prototype.getHeight=function(){return this.maxY-this.minY+1},Vl.prototype.getSize=function(){return[this.getWidth(),this.getHeight()]},Vl.prototype.getWidth=function(){return this.maxX-this.minX+1},Vl.prototype.intersects=function(t){return this.minX<=t.maxX&&this.maxX>=t.minX&&this.minY<=t.maxY&&this.maxY>=t.minY};var Kl=function(i){function t(t,e){i.call(this,t),this.context=e?null:De(),this.oversampling_,this.renderedExtent_=null,this.renderedRevision,this.renderedTiles=[],this.newTiles_=!1,this.tmpExtent=[1/0,1/0,-1/0,-1/0],this.tmpTileRange_=new Vl(0,0,0,0),this.imageTransform_=[1,0,0,1,0,0],this.zDirection=0}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.isDrawableTile_=function(t){var e=t.getState(),i=this.getLayer().getUseInterimTilesOnError();return e==Gn||e==Dn||e==kn&&!i},t.prototype.getTile=function(t,e,i,r,n){var o=this.getLayer(),s=o.getSource().getTile(t,e,i,r,n);return s.getState()==kn&&(o.getUseInterimTilesOnError()?0<o.getPreload()&&(this.newTiles_=!0):s.setState(Gn)),this.isDrawableTile_(s)||(s=s.getInterimTile()),s},t.prototype.prepareFrame=function(t,e){var i=t.pixelRatio,r=t.size,n=t.viewState,o=n.projection,s=n.resolution,a=n.center,h=this.getLayer(),l=h.getSource(),u=l.getRevision(),c=l.getTileGridForProjection(o),p=c.getZForResolution(s,this.zDirection),d=c.getResolution(p),f=Math.round(s/d)||1,_=t.extent;if(void 0!==e.extent&&(_=ht(_,e.extent)),pt(_))return!1;var g=c.getTileRangeForExtentAndZ(_,p),y=c.getTileRangeExtent(p,g),v=l.getTilePixelRatio(i),m={};m[p]={};var x,S,C,E=this.createLoadedTileFinder(l,o,m),T=t.viewHints,w=T[rs.ANIMATING]||T[rs.INTERACTING],R=this.tmpExtent,I=this.tmpTileRange_;for(this.newTiles_=!1,S=g.minX;S<=g.maxX;++S)for(C=g.minY;C<=g.maxY;++C)if(!(16<Date.now()-t.time&&w)){if(x=this.getTile(p,S,C,i,o),this.isDrawableTile_(x)){var L=Et(this);if(x.getState()==Gn){var b=(m[p][x.tileCoord.toString()]=x).inTransition(L);this.newTiles_||!b&&-1!==this.renderedTiles.indexOf(x)||(this.newTiles_=!0)}if(1===x.getAlpha(L,t.time))continue}var P=c.getTileCoordChildTileRange(x.tileCoord,I,R),F=!1;P&&(F=E(p+1,P)),F||c.forEachTileCoordParentTileRange(x.tileCoord,E,null,I,R)}var M=d*i/v*f;if(!(this.renderedResolution&&16<Date.now()-t.time&&w)&&(this.newTiles_||!this.renderedExtent_||!Q(this.renderedExtent_,_)||this.renderedRevision!=u||f!=this.oversampling_||!w&&M!=this.renderedResolution)){var O=this.context;if(O){var N=l.getTilePixelSize(p,i,o),A=Math.round(g.getWidth()*N[0]/f),G=Math.round(g.getHeight()*N[1]/f),k=O.canvas;k.width!=A||k.height!=G?(this.oversampling_=f,k.width=A,k.height=G):(this.renderedExtent_&&!$(y,this.renderedExtent_)&&O.clearRect(0,0,A,G),f=this.oversampling_)}this.renderedTiles.length=0;var D,j,U,Y,B,X,z,V,W,K,H=Object.keys(m).map(Number);for(H.sort(function(t,e){return t===p?1:e===p?-1:e<t?1:t<e?-1:0}),Y=0,B=H.length;Y<B;++Y)for(var Z in U=H[Y],j=l.getTilePixelSize(U,i,o),D=c.getResolution(U)/d,z=v*l.getGutter(o),V=m[U])x=V[Z],S=((X=c.getTileCoordExtent(x.getTileCoord(),R))[0]-y[0])/d*v/f,C=(y[3]-X[3])/d*v/f,W=j[0]*D/f,K=j[1]*D/f,this.drawTileImage(x,t,e,S,C,W,K,z,p===U),this.renderedTiles.push(x);this.renderedRevision=u,this.renderedResolution=d*i/v*f,this.renderedExtent_=y}var q=this.renderedResolution/s,J=Te(this.imageTransform_,i*r[0]/2,i*r[1]/2,q,q,0,(this.renderedExtent_[0]-a[0])/this.renderedResolution*i,(a[1]-this.renderedExtent_[3])/this.renderedResolution*i);return Te(this.coordinateToCanvasPixelTransform,i*r[0]/2-J[4],i*r[1]/2-J[5],i/s,-i/s,0,-a[0],-a[1]),this.updateUsedTiles(t.usedTiles,l,p,g),this.manageTilePyramid(t,l,c,i,o,_,p,h.getPreload()),this.scheduleExpireCache(t,l),0<this.renderedTiles.length},t.prototype.drawTileImage=function(t,e,i,r,n,o,s,a,h){var l=t.getImage(this.getLayer());if(l){var u=Et(this),c=h?t.getAlpha(u,e.time):1;1!==c||this.getLayer().getSource().getOpaque(e.viewState.projection)||this.context.clearRect(r,n,o,s);var p=c!==this.context.globalAlpha;p&&(this.context.save(),this.context.globalAlpha=c),this.context.drawImage(l,a,a,l.width-2*a,l.height-2*a,r,n,o,s),p&&this.context.restore(),1!==c?e.animate=!0:h&&t.endTransition(u)}},t.prototype.getImage=function(){var t=this.context;return t?t.canvas:null},t.prototype.getImageTransform=function(){return this.imageTransform_},t}(Xl);Kl.handles=function(t){return t.getType()===oh.TILE},Kl.create=function(t,e){return new Kl(e)},Kl.prototype.getLayer;var Hl=function(){};Hl.prototype.getReplay=function(t,e){},Hl.prototype.isEmpty=function(){};var Zl={CIRCLE:"Circle",DEFAULT:"Default",IMAGE:"Image",LINE_STRING:"LineString",POLYGON:"Polygon",TEXT:"Text"};function ql(t,e,i,r,n,o,s,a){for(var h,l,u,c=[],p=t[e]>t[i-r],d=n.length,f=t[e],_=t[e+1],g=t[e+=r],y=t[e+1],v=0,m=Math.sqrt(Math.pow(g-f,2)+Math.pow(y-_,2)),x="",S=0,C=0;C<d;++C){l=p?d-C-1:C;var E=n.charAt(l),T=o(x=p?E+x:x+E)-S;S+=T;for(var w=s+T/2;e<i-r&&v+m<w;)f=g,_=y,g=t[e+=r],y=t[e+1],v+=m,m=Math.sqrt(Math.pow(g-f,2)+Math.pow(y-_,2));var R=w-v,I=Math.atan2(y-_,g-f);if(p&&(I+=0<I?-Math.PI:Math.PI),void 0!==u){var L=I-u;if(L+=L>Math.PI?-2*Math.PI:L<-Math.PI?2*Math.PI:0,Math.abs(L)>a)return null}var b=R/m,P=It(f,g,b),F=It(_,y,b);u==I?(p&&(h[0]=P,h[1]=F,h[2]=T/2),h[4]=x):(h=[P,F,(S=T)/2,I,x=E],p?c.unshift(h):c.push(h),u=I),s+=T}return c}var Jl=0,Ql=1,$l=2,tu=3,eu=4,iu=5,ru=6,nu=7,ou=8,su=9,au=10,hu=11,lu=12,uu=[ou],cu=[lu],pu=[Ql],du=[tu],fu=[Zl.POLYGON,Zl.CIRCLE,Zl.LINE_STRING,Zl.IMAGE,Zl.TEXT,Zl.DEFAULT],_u={left:0,end:0,center:.5,right:1,start:1,top:0,middle:.5,hanging:.2,alphabetic:.8,ideographic:.8,bottom:1},gu=[1/0,1/0,-1/0,-1/0],yu=[1,0,0,1,0,0],vu=function(s){function t(t,e,i,r,n,o){s.call(this),this.declutterTree=o,this.tolerance=t,this.maxExtent=e,this.overlaps=n,this.pixelRatio=r,this.maxLineWidth=0,this.resolution=i,this.alignFill_,this.beginGeometryInstruction1_=null,this.beginGeometryInstruction2_=null,this.bufferedMaxExtent_=null,this.instructions=[],this.coordinates=[],this.coordinateCache_={},this.renderedTransform_=[1,0,0,1,0,0],this.hitDetectionInstructions=[],this.pixelCoordinates_=null,this.state={},this.viewRotation_=0}return s&&(t.__proto__=s),((t.prototype=Object.create(s&&s.prototype)).constructor=t).prototype.replayTextBackground_=function(t,e,i,r,n,o,s){t.beginPath(),t.moveTo.apply(t,e),t.lineTo.apply(t,i),t.lineTo.apply(t,r),t.lineTo.apply(t,n),t.lineTo.apply(t,e),o&&(this.alignFill_=o[2],this.fill_(t)),s&&(this.setStrokeStyle_(t,s),t.stroke())},t.prototype.replayImage_=function(t,e,i,r,n,o,s,a,h,l,u,c,p,d,f,_,g,y){var v=g||y;e-=n*=p,i-=o*=p;var m,x,S,C,E=f+l>r.width?r.width-l:f,T=a+u>r.height?r.height-u:a,w=_[3]+E*p+_[1],R=_[0]+T*p+_[2],I=e-_[3],L=i-_[0];(v||0!==c)&&(m=[I,L],x=[I+w,L],S=[I+w,L+R],C=[I,L+R]);var b=null;if(0!==c){var P=e+n,F=i+o;b=Te(yu,P,F,1,1,c,-P,-F),z(gu),q(gu,xe(yu,m)),q(gu,xe(yu,x)),q(gu,xe(yu,S)),q(gu,xe(yu,C))}else X(I,L,I+w,L+R,gu);var M=t.canvas,O=y?y[2]*p/2:0,N=gu[0]-O<=M.width&&0<=gu[2]+O&&gu[1]-O<=M.height&&0<=gu[3]+O;if(d&&(e=Math.round(e),i=Math.round(i)),s){if(!N&&1==s[4])return;H(s,gu);var A=N?[t,b?b.slice(0):null,h,r,l,u,E,T,e,i,p]:null;A&&v&&A.push(g,y,m,x,S,C),s.push(A)}else N&&(v&&this.replayTextBackground_(t,m,x,S,C,g,y),Ui(t,b,h,r,l,u,E,T,e,i,p))},t.prototype.applyPixelRatio=function(t){var e=this.pixelRatio;return 1==e?t:t.map(function(t){return t*e})},t.prototype.appendFlatCoordinates=function(t,e,i,r,n,o){var s=this.coordinates.length,a=this.getBufferedMaxExtent();o&&(e+=r);var h,l,u,c=[t[e],t[e+1]],p=[NaN,NaN],d=!0;for(h=e+r;h<i;h+=r)p[0]=t[h],p[1]=t[h+1],(u=Y(a,p))!==l?(d&&(this.coordinates[s++]=c[0],this.coordinates[s++]=c[1]),this.coordinates[s++]=p[0],this.coordinates[s++]=p[1],d=!1):u===N.INTERSECTING?(this.coordinates[s++]=p[0],this.coordinates[s++]=p[1],d=!1):d=!0,c[0]=p[0],c[1]=p[1],l=u;return(n&&d||h===e+r)&&(this.coordinates[s++]=c[0],this.coordinates[s++]=c[1]),s},t.prototype.drawCustomCoordinates_=function(t,e,i,r,n){for(var o=0,s=i.length;o<s;++o){var a=i[o],h=this.appendFlatCoordinates(t,e,a,r,!1,!1);n.push(h),e=a}return e},t.prototype.drawCustom=function(t,e,i){this.beginGeometry(t,e);var r,n,o,s,a,h=t.getType(),l=t.getStride(),u=this.coordinates.length;if(h==Lt.MULTI_POLYGON){r=(t=t).getOrientedFlatCoordinates(),s=[];for(var c=t.getEndss(),p=a=0,d=c.length;p<d;++p){var f=[];a=this.drawCustomCoordinates_(r,a,c[p],l,f),s.push(f)}this.instructions.push([eu,u,s,t,i,Mr])}else h==Lt.POLYGON||h==Lt.MULTI_LINE_STRING?(o=[],r=h==Lt.POLYGON?t.getOrientedFlatCoordinates():t.getFlatCoordinates(),a=this.drawCustomCoordinates_(r,0,t.getEnds(),l,o),this.instructions.push([eu,u,o,t,i,Fr])):h==Lt.LINE_STRING||h==Lt.MULTI_POINT?(r=t.getFlatCoordinates(),n=this.appendFlatCoordinates(r,0,r.length,l,!1,!1),this.instructions.push([eu,u,n,t,i,Pr])):h==Lt.POINT&&(r=t.getFlatCoordinates(),this.coordinates.push(r[0],r[1]),n=this.coordinates.length,this.instructions.push([eu,u,n,t,i]));this.endGeometry(t,e)},t.prototype.beginGeometry=function(t,e){this.beginGeometryInstruction1_=[Jl,e,0],this.instructions.push(this.beginGeometryInstruction1_),this.beginGeometryInstruction2_=[Jl,e,0],this.hitDetectionInstructions.push(this.beginGeometryInstruction2_)},t.prototype.fill_=function(t){if(this.alignFill_){var e=xe(this.renderedTransform_,[0,0]),i=512*this.pixelRatio;t.translate(e[0]%i,e[1]%i),t.rotate(this.viewRotation_)}t.fill(),this.alignFill_&&t.setTransform.apply(t,ji)},t.prototype.setStrokeStyle_=function(t,e){t.strokeStyle=e[1],t.lineWidth=e[2],t.lineCap=e[3],t.lineJoin=e[4],t.miterLimit=e[5],hi&&(t.lineDashOffset=e[7],t.setLineDash(e[6]))},t.prototype.renderDeclutter_=function(t,e){if(t&&5<t.length){var i=t[4];if(1==i||i==t.length-5){var r={minX:t[0],minY:t[1],maxX:t[2],maxY:t[3],value:e};if(!this.declutterTree.collides(r)){this.declutterTree.insert(r);for(var n=5,o=t.length;n<o;++n){var s=t[n];s&&(11<s.length&&this.replayTextBackground_(s[0],s[13],s[14],s[15],s[16],s[11],s[12]),Ui.apply(void 0,s))}}t.length=5,z(t)}}},t.prototype.replay_=function(t,e,i,r,n,o){var s,a=this;this.pixelCoordinates_&&fr(e,this.renderedTransform_)?s=this.pixelCoordinates_:(this.pixelCoordinates_||(this.pixelCoordinates_=[]),s=Rt(this.coordinates,0,this.coordinates.length,2,e,this.pixelCoordinates_),me(this.renderedTransform_,e));for(var h,l,u,c,p,d,f,_,g,y,v,m,x=!Tt(i),S=0,C=r.length,E=0,T=0,w=0,R=null,I=null,L=this.coordinateCache_,b=this.viewRotation_,P={context:t,pixelRatio:this.pixelRatio,resolution:this.resolution,rotation:b},F=this.instructions!=r||this.overlaps?0:200;S<C;){var M=r[S];switch(M[0]){case Jl:y=M[1],x&&i[Et(y).toString()]||!y.getGeometry()?S=M[2]:void 0===o||wt(o,y.getGeometry().getExtent())?++S:S=M[2]+1;break;case Ql:F<T&&(a.fill_(t),T=0),F<w&&(t.stroke(),w=0),T||w||(t.beginPath(),c=p=NaN),++S;break;case $l:var O=s[E=M[1]],N=s[E+1],A=s[E+2]-O,G=s[E+3]-N,k=Math.sqrt(A*A+G*G);t.moveTo(O+k,N),t.arc(O,N,k,0,2*Math.PI,!0),++S;break;case tu:t.closePath(),++S;break;case eu:E=M[1],h=M[2];var D=M[3],j=M[4],U=6==M.length?M[5]:void 0;P.geometry=D,P.feature=y,S in L||(L[S]=[]);var Y=L[S];U?U(s,E,h,2,Y):(Y[0]=s[E],Y[1]=s[E+1],Y.length=2),j(Y,P),++S;break;case ru:E=M[1],h=M[2],g=M[3],l=M[4],u=M[5],_=n?null:M[6];var B=M[7],X=M[8],z=M[9],V=M[10],W=M[11],K=M[12],H=M[13],Z=M[14],q=M[15],J=void 0,Q=void 0,$=void 0;for(16<M.length?(J=M[16],Q=M[17],$=M[18]):(J=Ii,Q=$=!1),W&&(K+=b);E<h;E+=2)a.replayImage_(t,s[E],s[E+1],g,l,u,_,B,X,z,V,K,H,Z,q,J,Q?R:null,$?I:null);a.renderDeclutter_(_,y),++S;break;case iu:var tt=M[1],et=M[2],it=M[3];_=n?null:M[4];var rt=M[5],nt=M[6],ot=M[7],st=M[8],at=M[9],ht=M[10],lt=M[11],ut=M[12],ct=M[13],pt=M[14],dt=xn(s,tt,et,2),ft=st(ut);if(rt||ft<=dt){var _t=a.textStates[ct].textAlign,gt=ql(s,tt,et,2,ut,st,(dt-ft)*_u[_t],ot);if(gt){var yt=void 0,vt=void 0,mt=void 0,xt=void 0,St=void 0;if(ht)for(yt=0,vt=gt.length;yt<vt;++yt)mt=(St=gt[yt])[4],xt=a.getImage(mt,ct,"",ht),l=St[2]+lt,u=it*xt.height+2*(.5-it)*lt-at,a.replayImage_(t,St[0],St[1],xt,l,u,_,xt.height,1,0,0,St[3],pt,!1,xt.width,Ii,null,null);if(nt)for(yt=0,vt=gt.length;yt<vt;++yt)mt=(St=gt[yt])[4],xt=a.getImage(mt,ct,nt,""),l=St[2],u=it*xt.height-at,a.replayImage_(t,St[0],St[1],xt,l,u,_,xt.height,1,0,0,St[3],pt,!1,xt.width,Ii,null,null)}}a.renderDeclutter_(_,y),++S;break;case nu:if(void 0!==n){var Ct=n(y=M[1]);if(Ct)return Ct}++S;break;case ou:F?T++:a.fill_(t),++S;break;case su:for(E=M[1],h=M[2],v=s[E],f=(m=s[E+1])+.5|0,(d=v+.5|0)===c&&f===p||(t.moveTo(v,m),c=d,p=f),E+=2;E<h;E+=2)d=(v=s[E])+.5|0,f=(m=s[E+1])+.5|0,E!=h-2&&d===c&&f===p||(t.lineTo(v,m),c=d,p=f);++S;break;case au:R=M,a.alignFill_=M[2],T&&(a.fill_(t),T=0,w&&(t.stroke(),w=0)),t.fillStyle=M[1],++S;break;case hu:I=M,w&&(t.stroke(),w=0),a.setStrokeStyle_(t,M),++S;break;case lu:F?w++:t.stroke(),++S;break;default:++S}}T&&this.fill_(t),w&&t.stroke()},t.prototype.replay=function(t,e,i,r){this.viewRotation_=i,this.replay_(t,e,r,this.instructions,void 0,void 0)},t.prototype.replayHitDetection=function(t,e,i,r,n,o){return this.viewRotation_=i,this.replay_(t,e,r,this.hitDetectionInstructions,n,o)},t.prototype.reverseHitDetectionInstructions=function(){var t,e=this.hitDetectionInstructions;e.reverse();var i,r,n=e.length,o=-1;for(t=0;t<n;++t)(r=(i=e[t])[0])==nu?o=t:r==Jl&&(i[2]=t,cr(this.hitDetectionInstructions,o,t),o=-1)},t.prototype.setFillStrokeStyle=function(t,e){var i=this.state;if(t){var r=t.getColor();i.fillStyle=ke(r||Si)}else i.fillStyle=void 0;if(e){var n=e.getColor();i.strokeStyle=ke(n||wi);var o=e.getLineCap();i.lineCap=void 0!==o?o:Ci;var s=e.getLineDash();i.lineDash=s?s.slice():Ei;var a=e.getLineDashOffset();i.lineDashOffset=a||0;var h=e.getLineJoin();i.lineJoin=void 0!==h?h:Ti;var l=e.getWidth();i.lineWidth=void 0!==l?l:1;var u=e.getMiterLimit();i.miterLimit=void 0!==u?u:10,i.lineWidth>this.maxLineWidth&&(this.maxLineWidth=i.lineWidth,this.bufferedMaxExtent_=null)}else i.strokeStyle=void 0,i.lineCap=void 0,i.lineDash=null,i.lineDashOffset=void 0,i.lineJoin=void 0,i.lineWidth=void 0,i.miterLimit=void 0},t.prototype.createFill=function(t,e){var i=t.fillStyle,r=[au,i];return"string"!=typeof i&&r.push(!0),r},t.prototype.applyStroke=function(t){this.instructions.push(this.createStroke(t))},t.prototype.createStroke=function(t){return[hu,t.strokeStyle,t.lineWidth*this.pixelRatio,t.lineCap,t.lineJoin,t.miterLimit,this.applyPixelRatio(t.lineDash),t.lineDashOffset*this.pixelRatio]},t.prototype.updateFillStyle=function(t,e,i){var r=t.fillStyle;"string"==typeof r&&t.currentFillStyle==r||(void 0!==r&&this.instructions.push(e.call(this,t,i)),t.currentFillStyle=r)},t.prototype.updateStrokeStyle=function(t,e){var i=t.strokeStyle,r=t.lineCap,n=t.lineDash,o=t.lineDashOffset,s=t.lineJoin,a=t.lineWidth,h=t.miterLimit;(t.currentStrokeStyle!=i||t.currentLineCap!=r||n!=t.currentLineDash&&!fr(t.currentLineDash,n)||t.currentLineDashOffset!=o||t.currentLineJoin!=s||t.currentLineWidth!=a||t.currentMiterLimit!=h)&&(void 0!==i&&e.call(this,t),t.currentStrokeStyle=i,t.currentLineCap=r,t.currentLineDash=n,t.currentLineDashOffset=o,t.currentLineJoin=s,t.currentLineWidth=a,t.currentMiterLimit=h)},t.prototype.endGeometry=function(t,e){this.beginGeometryInstruction1_[2]=this.instructions.length,this.beginGeometryInstruction1_=null,this.beginGeometryInstruction2_[2]=this.hitDetectionInstructions.length,this.beginGeometryInstruction2_=null;var i=[nu,e];this.instructions.push(i),this.hitDetectionInstructions.push(i)},t.prototype.getBufferedMaxExtent=function(){if(!this.bufferedMaxExtent_&&(this.bufferedMaxExtent_=k(this.maxExtent),0<this.maxLineWidth)){var t=this.resolution*(this.maxLineWidth+1)/2;G(this.bufferedMaxExtent_,t,this.bufferedMaxExtent_)}return this.bufferedMaxExtent_},t}(Fl);vu.prototype.finish=L;var mu=function(s){function t(t,e,i,r,n,o){s.call(this,t,e,i,r,n,o),this.declutterGroup_=null,this.hitDetectionImage_=null,this.image_=null,this.anchorX_=void 0,this.anchorY_=void 0,this.height_=void 0,this.opacity_=void 0,this.originX_=void 0,this.originY_=void 0,this.rotateWithView_=void 0,this.rotation_=void 0,this.scale_=void 0,this.snapToPixel_=void 0,this.width_=void 0}return s&&(t.__proto__=s),((t.prototype=Object.create(s&&s.prototype)).constructor=t).prototype.drawCoordinates_=function(t,e,i,r){return this.appendFlatCoordinates(t,e,i,r,!1,!1)},t.prototype.drawPoint=function(t,e){if(this.image_){this.beginGeometry(t,e);var i=t.getFlatCoordinates(),r=t.getStride(),n=this.coordinates.length,o=this.drawCoordinates_(i,0,i.length,r);this.instructions.push([ru,n,o,this.image_,this.anchorX_,this.anchorY_,this.declutterGroup_,this.height_,this.opacity_,this.originX_,this.originY_,this.rotateWithView_,this.rotation_,this.scale_*this.pixelRatio,this.snapToPixel_,this.width_]),this.hitDetectionInstructions.push([ru,n,o,this.hitDetectionImage_,this.anchorX_,this.anchorY_,this.declutterGroup_,this.height_,this.opacity_,this.originX_,this.originY_,this.rotateWithView_,this.rotation_,this.scale_,this.snapToPixel_,this.width_]),this.endGeometry(t,e)}},t.prototype.drawMultiPoint=function(t,e){if(this.image_){this.beginGeometry(t,e);var i=t.getFlatCoordinates(),r=t.getStride(),n=this.coordinates.length,o=this.drawCoordinates_(i,0,i.length,r);this.instructions.push([ru,n,o,this.image_,this.anchorX_,this.anchorY_,this.declutterGroup_,this.height_,this.opacity_,this.originX_,this.originY_,this.rotateWithView_,this.rotation_,this.scale_*this.pixelRatio,this.snapToPixel_,this.width_]),this.hitDetectionInstructions.push([ru,n,o,this.hitDetectionImage_,this.anchorX_,this.anchorY_,this.declutterGroup_,this.height_,this.opacity_,this.originX_,this.originY_,this.rotateWithView_,this.rotation_,this.scale_,this.snapToPixel_,this.width_]),this.endGeometry(t,e)}},t.prototype.finish=function(){this.reverseHitDetectionInstructions(),this.anchorX_=void 0,this.anchorY_=void 0,this.hitDetectionImage_=null,this.image_=null,this.height_=void 0,this.scale_=void 0,this.opacity_=void 0,this.originX_=void 0,this.originY_=void 0,this.rotateWithView_=void 0,this.rotation_=void 0,this.snapToPixel_=void 0,this.width_=void 0},t.prototype.setImageStyle=function(t,e){var i=t.getAnchor(),r=t.getSize(),n=t.getHitDetectionImage(1),o=t.getImage(1),s=t.getOrigin();this.anchorX_=i[0],this.anchorY_=i[1],this.declutterGroup_=e,this.hitDetectionImage_=n,this.image_=o,this.height_=r[1],this.opacity_=t.getOpacity(),this.originX_=s[0],this.originY_=s[1],this.rotateWithView_=t.getRotateWithView(),this.rotation_=t.getRotation(),this.scale_=t.getScale(),this.snapToPixel_=t.getSnapToPixel(),this.width_=r[0]},t}(vu),xu=function(s){function t(t,e,i,r,n,o){s.call(this,t,e,i,r,n,o)}return s&&(t.__proto__=s),((t.prototype=Object.create(s&&s.prototype)).constructor=t).prototype.drawFlatCoordinates_=function(t,e,i,r){var n=this.coordinates.length,o=this.appendFlatCoordinates(t,e,i,r,!1,!1),s=[su,n,o];return this.instructions.push(s),this.hitDetectionInstructions.push(s),i},t.prototype.drawLineString=function(t,e){var i=this.state,r=i.strokeStyle,n=i.lineWidth;if(void 0!==r&&void 0!==n){this.updateStrokeStyle(i,this.applyStroke),this.beginGeometry(t,e),this.hitDetectionInstructions.push([hu,i.strokeStyle,i.lineWidth,i.lineCap,i.lineJoin,i.miterLimit,i.lineDash,i.lineDashOffset],pu);var o=t.getFlatCoordinates(),s=t.getStride();this.drawFlatCoordinates_(o,0,o.length,s),this.hitDetectionInstructions.push(cu),this.endGeometry(t,e)}},t.prototype.drawMultiLineString=function(t,e){var i=this.state,r=i.strokeStyle,n=i.lineWidth;if(void 0!==r&&void 0!==n){this.updateStrokeStyle(i,this.applyStroke),this.beginGeometry(t,e),this.hitDetectionInstructions.push([hu,i.strokeStyle,i.lineWidth,i.lineCap,i.lineJoin,i.miterLimit,i.lineDash,i.lineDashOffset],pu);for(var o=t.getEnds(),s=t.getFlatCoordinates(),a=t.getStride(),h=0,l=0,u=o.length;l<u;++l)h=this.drawFlatCoordinates_(s,h,o[l],a);this.hitDetectionInstructions.push(cu),this.endGeometry(t,e)}},t.prototype.finish=function(){var t=this.state;null!=t.lastStroke&&t.lastStroke!=this.coordinates.length&&this.instructions.push(cu),this.reverseHitDetectionInstructions(),this.state=null},t.prototype.applyStroke=function(t){null!=t.lastStroke&&t.lastStroke!=this.coordinates.length&&(this.instructions.push(cu),t.lastStroke=this.coordinates.length),t.lastStroke=0,s.prototype.applyStroke.call(this,t),this.instructions.push(pu)},t}(vu),Su=function(s){function t(t,e,i,r,n,o){s.call(this,t,e,i,r,n,o)}return s&&(t.__proto__=s),((t.prototype=Object.create(s&&s.prototype)).constructor=t).prototype.drawFlatCoordinatess_=function(t,e,i,r){var n=this.state,o=void 0!==n.fillStyle,s=null!=n.strokeStyle,a=i.length;this.instructions.push(pu),this.hitDetectionInstructions.push(pu);for(var h=0;h<a;++h){var l=i[h],u=this.coordinates.length,c=this.appendFlatCoordinates(t,e,l,r,!0,!s),p=[su,u,c];this.instructions.push(p),this.hitDetectionInstructions.push(p),s&&(this.instructions.push(du),this.hitDetectionInstructions.push(du)),e=l}return o&&(this.instructions.push(uu),this.hitDetectionInstructions.push(uu)),s&&(this.instructions.push(cu),this.hitDetectionInstructions.push(cu)),e},t.prototype.drawCircle=function(t,e){var i=this.state,r=i.fillStyle,n=i.strokeStyle;if(void 0!==r||void 0!==n){this.setFillStrokeStyles_(t),this.beginGeometry(t,e),void 0!==i.fillStyle&&this.hitDetectionInstructions.push([au,Pe(Si)]),void 0!==i.strokeStyle&&this.hitDetectionInstructions.push([hu,i.strokeStyle,i.lineWidth,i.lineCap,i.lineJoin,i.miterLimit,i.lineDash,i.lineDashOffset]);var o=t.getFlatCoordinates(),s=t.getStride(),a=this.coordinates.length;this.appendFlatCoordinates(o,0,o.length,s,!1,!1);var h=[$l,a];this.instructions.push(pu,h),this.hitDetectionInstructions.push(pu,h),this.hitDetectionInstructions.push(uu),void 0!==i.fillStyle&&this.instructions.push(uu),void 0!==i.strokeStyle&&(this.instructions.push(cu),this.hitDetectionInstructions.push(cu)),this.endGeometry(t,e)}},t.prototype.drawPolygon=function(t,e){var i=this.state,r=i.fillStyle,n=i.strokeStyle;if(void 0!==r||void 0!==n){this.setFillStrokeStyles_(t),this.beginGeometry(t,e),void 0!==i.fillStyle&&this.hitDetectionInstructions.push([au,Pe(Si)]),void 0!==i.strokeStyle&&this.hitDetectionInstructions.push([hu,i.strokeStyle,i.lineWidth,i.lineCap,i.lineJoin,i.miterLimit,i.lineDash,i.lineDashOffset]);var o=t.getEnds(),s=t.getOrientedFlatCoordinates(),a=t.getStride();this.drawFlatCoordinatess_(s,0,o,a),this.endGeometry(t,e)}},t.prototype.drawMultiPolygon=function(t,e){var i=this.state,r=i.fillStyle,n=i.strokeStyle;if(void 0!==r||void 0!==n){this.setFillStrokeStyles_(t),this.beginGeometry(t,e),void 0!==i.fillStyle&&this.hitDetectionInstructions.push([au,Pe(Si)]),void 0!==i.strokeStyle&&this.hitDetectionInstructions.push([hu,i.strokeStyle,i.lineWidth,i.lineCap,i.lineJoin,i.miterLimit,i.lineDash,i.lineDashOffset]);for(var o=t.getEndss(),s=t.getOrientedFlatCoordinates(),a=t.getStride(),h=0,l=0,u=o.length;l<u;++l)h=this.drawFlatCoordinatess_(s,h,o[l],a);this.endGeometry(t,e)}},t.prototype.finish=function(){this.reverseHitDetectionInstructions(),this.state=null;var t=this.tolerance;if(0!==t)for(var e=this.coordinates,i=0,r=e.length;i<r;++i)e[i]=Nr(e[i],t)},t.prototype.setFillStrokeStyles_=function(t){var e=this.state;void 0!==e.fillStyle&&this.updateFillStyle(e,this.createFill,t),void 0!==e.strokeStyle&&this.updateStrokeStyle(e,this.applyStroke)},t}(vu);function Cu(t,e,i,r,n){var o,s,a,h,l,u,c,p,d,f=i,_=i,g=0,y=0,v=i;for(o=i;o<r;o+=n){var m=e[o],x=e[o+1];void 0!==h&&(p=m-h,d=x-l,a=Math.sqrt(p*p+d*d),void 0!==u&&(y+=s,t<Math.acos((u*p+c*d)/(s*a))&&(g<y&&(g=y,f=v,_=o),y=0,v=o-n)),s=a,u=p,c=d),h=m,l=x}return g<(y+=a)?[v,o]:[f,_]}var Eu={Circle:Su,Default:vu,Image:mu,LineString:xu,Polygon:Su,Text:function(s){function t(t,e,i,r,n,o){s.call(this,t,e,i,r,n,o),this.declutterGroup_,this.labels_=null,this.text_="",this.textOffsetX_=0,this.textOffsetY_=0,this.textRotateWithView_=void 0,this.textRotation_=0,this.textFillState_=null,this.fillStates={},this.textStrokeState_=null,this.strokeStates={},this.textState_={},this.textStates={},this.textKey_="",this.fillKey_="",this.strokeKey_="",this.widths_={},Li.prune()}return s&&(t.__proto__=s),((t.prototype=Object.create(s&&s.prototype)).constructor=t).prototype.drawText=function(t,e){var i=this.textFillState_,r=this.textStrokeState_,n=this.textState_;if(""!==this.text_&&n&&(i||r)){var o,s,a=this.coordinates.length,h=t.getType(),l=null,u=2,c=2;if(n.placement===In){if(!wt(this.getBufferedMaxExtent(),t.getExtent()))return;var p;if(l=t.getFlatCoordinates(),c=t.getStride(),h==Lt.LINE_STRING)p=[l.length];else if(h==Lt.MULTI_LINE_STRING)p=t.getEnds();else if(h==Lt.POLYGON)p=t.getEnds().slice(0,1);else if(h==Lt.MULTI_POLYGON){var d=t.getEndss();for(p=[],o=0,s=d.length;o<s;++o)p.push(d[o][0])}this.beginGeometry(t,e);for(var f,_=n.textAlign,g=0,y=0,v=p.length;y<v;++y){if(null==_){var m=Cu(n.maxAngle,l,g,p[y],c);g=m[0],f=m[1]}else f=p[y];for(o=g;o<f;o+=c)this.coordinates.push(l[o],l[o+1]);u=this.coordinates.length,g=p[y],this.drawChars_(a,u,this.declutterGroup_),a=u}this.endGeometry(t,e)}else{var x=this.getImage(this.text_,this.textKey_,this.fillKey_,this.strokeKey_),S=x.width/this.pixelRatio;switch(h){case Lt.POINT:case Lt.MULTI_POINT:u=(l=t.getFlatCoordinates()).length;break;case Lt.LINE_STRING:l=t.getFlatMidpoint();break;case Lt.CIRCLE:l=t.getCenter();break;case Lt.MULTI_LINE_STRING:u=(l=t.getFlatMidpoints()).length;break;case Lt.POLYGON:if(l=t.getFlatInteriorPoint(),!n.overflow&&l[2]/this.resolution<S)return;c=3;break;case Lt.MULTI_POLYGON:var C=t.getFlatInteriorPoints();for(l=[],o=0,s=C.length;o<s;o+=3)(n.overflow||C[o+2]/this.resolution>=S)&&l.push(C[o],C[o+1]);if(0==(u=l.length))return}u=this.appendFlatCoordinates(l,0,u,c,!1,!1),(n.backgroundFill||n.backgroundStroke)&&(this.setFillStrokeStyle(n.backgroundFill,n.backgroundStroke),n.backgroundFill&&(this.updateFillStyle(this.state,this.createFill,t),this.hitDetectionInstructions.push(this.createFill(this.state,t))),n.backgroundStroke&&(this.updateStrokeStyle(this.state,this.applyStroke),this.hitDetectionInstructions.push(this.createStroke(this.state)))),this.beginGeometry(t,e),this.drawTextImage_(x,a,u),this.endGeometry(t,e)}}},t.prototype.getImage=function(t,e,i,r){var n,o=r+e+t+i+this.pixelRatio;if(!Li.containsKey(o)){var s=r?this.strokeStates[r]||this.textStrokeState_:null,a=i?this.fillStates[i]||this.textFillState_:null,h=this.textStates[e]||this.textState_,l=this.pixelRatio,u=h.scale*l,c=_u[h.textAlign||Ri],p=r&&s.lineWidth?s.lineWidth:0,d=t.split("\n"),f=d.length,_=[],g=function(t,e,i){for(var r=e.length,n=0,o=0;o<r;++o){var s=ki(t,e[o]);n=Math.max(n,s),i.push(s)}return n}(h.font,d,_),y=Gi(h.font),v=y*f,m=g+p,x=De(Math.ceil(m*u),Math.ceil((v+p)*u));n=x.canvas,Li.set(o,n),1!=u&&x.scale(u,u),x.font=h.font,r&&(x.strokeStyle=s.strokeStyle,x.lineWidth=p,x.lineCap=s.lineCap,x.lineJoin=s.lineJoin,x.miterLimit=s.miterLimit,hi&&s.lineDash.length&&(x.setLineDash(s.lineDash),x.lineDashOffset=s.lineDashOffset)),i&&(x.fillStyle=a.fillStyle),x.textBaseline="middle",x.textAlign="center";var S,C=.5-c,E=c*n.width/u+C*p;if(r)for(S=0;S<f;++S)x.strokeText(d[S],E+C*_[S],.5*(p+y)+S*y);if(i)for(S=0;S<f;++S)x.fillText(d[S],E+C*_[S],.5*(p+y)+S*y)}return Li.get(o)},t.prototype.drawTextImage_=function(t,e,i){var r=this.textState_,n=this.textStrokeState_,o=this.pixelRatio,s=_u[r.textAlign||Ri],a=_u[r.textBaseline],h=n&&n.lineWidth?n.lineWidth:0,l=s*t.width/o+2*(.5-s)*h,u=a*t.height/o+2*(.5-a)*h;this.instructions.push([ru,e,i,t,(l-this.textOffsetX_)*o,(u-this.textOffsetY_)*o,this.declutterGroup_,t.height,1,0,0,this.textRotateWithView_,this.textRotation_,1,!0,t.width,r.padding==Ii?Ii:r.padding.map(function(t){return t*o}),!!r.backgroundFill,!!r.backgroundStroke]),this.hitDetectionInstructions.push([ru,e,i,t,(l-this.textOffsetX_)*o,(u-this.textOffsetY_)*o,this.declutterGroup_,t.height,1,0,0,this.textRotateWithView_,this.textRotation_,1/o,!0,t.width,r.padding,!!r.backgroundFill,!!r.backgroundStroke])},t.prototype.drawChars_=function(t,e,i){var r=this.textStrokeState_,n=this.textState_,o=this.textFillState_,s=this.strokeKey_;r&&(s in this.strokeStates||(this.strokeStates[s]={strokeStyle:r.strokeStyle,lineCap:r.lineCap,lineDashOffset:r.lineDashOffset,lineWidth:r.lineWidth,lineJoin:r.lineJoin,miterLimit:r.miterLimit,lineDash:r.lineDash}));var a=this.textKey_;this.textKey_ in this.textStates||(this.textStates[this.textKey_]={font:n.font,textAlign:n.textAlign||Ri,scale:n.scale});var h=this.fillKey_;o&&(h in this.fillStates||(this.fillStates[h]={fillStyle:o.fillStyle}));var l=this.pixelRatio,u=_u[n.textBaseline],c=this.textOffsetY_*l,p=this.text_,d=n.font,f=n.scale,_=r?r.lineWidth*f/2:0,g=this.widths_[d];g||(this.widths_[d]=g={}),this.instructions.push([iu,t,e,u,i,n.overflow,h,n.maxAngle,function(t){var e=g[t];return e||(e=g[t]=ki(d,t)),e*f*l},c,s,_*l,p,a,1]),this.hitDetectionInstructions.push([iu,t,e,u,i,n.overflow,h,n.maxAngle,function(t){var e=g[t];return e||(e=g[t]=ki(d,t)),e*f},c,s,_,p,a,1/l])},t.prototype.setTextStyle=function(t,e){var i,r,n;if(t){this.declutterGroup_=e;var o=t.getFill();o?((r=this.textFillState_)||(r=this.textFillState_={}),r.fillStyle=ke(o.getColor()||Si)):r=this.textFillState_=null;var s=t.getStroke();if(s){(n=this.textStrokeState_)||(n=this.textStrokeState_={});var a=s.getLineDash(),h=s.getLineDashOffset(),l=s.getWidth(),u=s.getMiterLimit();n.lineCap=s.getLineCap()||Ci,n.lineDash=a?a.slice():Ei,n.lineDashOffset=void 0===h?0:h,n.lineJoin=s.getLineJoin()||Ti,n.lineWidth=void 0===l?1:l,n.miterLimit=void 0===u?10:u,n.strokeStyle=ke(s.getColor()||wi)}else n=this.textStrokeState_=null;i=this.textState_;var c=t.getFont()||xi;Mi(c);var p=t.getScale();i.overflow=t.getOverflow(),i.font=c,i.maxAngle=t.getMaxAngle(),i.placement=t.getPlacement(),i.textAlign=t.getTextAlign(),i.textBaseline=t.getTextBaseline()||"middle",i.backgroundFill=t.getBackgroundFill(),i.backgroundStroke=t.getBackgroundStroke(),i.padding=t.getPadding()||Ii,i.scale=void 0===p?1:p;var d=t.getOffsetX(),f=t.getOffsetY(),_=t.getRotateWithView(),g=t.getRotation();this.text_=t.getText()||"",this.textOffsetX_=void 0===d?0:d,this.textOffsetY_=void 0===f?0:f,this.textRotateWithView_=void 0!==_&&_,this.textRotation_=void 0===g?0:g,this.strokeKey_=n?("string"==typeof n.strokeStyle?n.strokeStyle:Et(n.strokeStyle))+n.lineCap+n.lineDashOffset+"|"+n.lineWidth+n.lineJoin+n.miterLimit+"["+n.lineDash.join()+"]":"",this.textKey_=i.font+i.scale+(i.textAlign||"?"),this.fillKey_=r?"string"==typeof r.fillStyle?r.fillStyle:"|"+Et(r.fillStyle):""}else this.text_=""},t}(vu)},Tu=function(a){function t(t,e,i,r,n,o,s){a.call(this),this.declutterTree_=o,this.declutterGroup_=null,this.tolerance_=t,this.maxExtent_=e,this.overlaps_=n,this.pixelRatio_=r,this.resolution_=i,this.renderBuffer_=s,this.replaysByZIndex_={},this.hitDetectionContext_=De(1,1),this.hitDetectionTransform_=[1,0,0,1,0,0]}return a&&(t.__proto__=a),((t.prototype=Object.create(a&&a.prototype)).constructor=t).prototype.addDeclutter=function(t){var e=null;return this.declutterTree_&&(t?(e=this.declutterGroup_)[4]++:(e=this.declutterGroup_=[1/0,1/0,-1/0,-1/0]).push(1)),e},t.prototype.clip=function(t,e){var i=this.getClipCoords(e);t.beginPath(),t.moveTo(i[0],i[1]),t.lineTo(i[2],i[3]),t.lineTo(i[4],i[5]),t.lineTo(i[6],i[7]),t.clip()},t.prototype.hasReplays=function(t){for(var e in this.replaysByZIndex_)for(var i=this.replaysByZIndex_[e],r=0,n=t.length;r<n;++r)if(t[r]in i)return!0;return!1},t.prototype.finish=function(){for(var t in this.replaysByZIndex_){var e=this.replaysByZIndex_[t];for(var i in e)e[i].finish()}},t.prototype.forEachFeatureAtCoordinate=function(t,e,i,r,n,o,s){var a,h=2*(r=Math.round(r))+1,l=Te(this.hitDetectionTransform_,r+.5,r+.5,1/e,-1/e,-i,-t[0],-t[1]),u=this.hitDetectionContext_;u.canvas.width!==h||u.canvas.height!==h?(u.canvas.width=h,u.canvas.height=h):u.clearRect(0,0,h,h),void 0!==this.renderBuffer_&&(q(a=[1/0,1/0,-1/0,-1/0],t),G(a,e*(this.renderBuffer_+r),a));var c,p,d=function(t){if(void 0!==wu[t])return wu[t];for(var e=2*t+1,i=new Array(e),r=0;r<e;r++)i[r]=new Array(e);var n=t,o=0,s=0;for(;o<=n;)Ru(i,t+n,t+o),Ru(i,t+o,t+n),Ru(i,t-o,t+n),Ru(i,t-n,t+o),Ru(i,t-n,t-o),Ru(i,t-o,t-n),Ru(i,t+o,t-n),Ru(i,t+n,t-o),0<2*((s+=1+2*++o)-n)+1&&(s+=1-2*(n-=1));return wu[t]=i}(r);function f(t){for(var e=u.getImageData(0,0,h,h).data,i=0;i<h;i++)for(var r=0;r<h;r++)if(d[i][r]&&0<e[4*(r*h+i)+3]){var n=void 0;return(!c||p!=Zl.IMAGE&&p!=Zl.TEXT||-1!==c.indexOf(t))&&(n=o(t)),n||void u.clearRect(0,0,h,h)}}this.declutterTree_&&(c=this.declutterTree_.all().map(function(t){return t.value}));var _,g,y,v,m,x=Object.keys(this.replaysByZIndex_).map(Number);for(x.sort(hr),_=x.length-1;0<=_;--_){var S=x[_].toString();for(y=this.replaysByZIndex_[S],g=fu.length-1;0<=g;--g)if(void 0!==(v=y[p=fu[g]]))if(!s||p!=Zl.IMAGE&&p!=Zl.TEXT){if(m=v.replayHitDetection(u,l,i,n,f,a))return m}else{var C=s[S];C?C.push(v,l.slice(0)):s[S]=[v,l.slice(0)]}}},t.prototype.getClipCoords=function(t){var e=this.maxExtent_,i=e[0],r=e[1],n=e[2],o=e[3],s=[i,r,i,o,n,o,n,r];return Rt(s,0,8,2,t,s),s},t.prototype.getReplay=function(t,e){var i=void 0!==t?t.toString():"0",r=this.replaysByZIndex_[i];void 0===r&&(r={},this.replaysByZIndex_[i]=r);var n=r[e];void 0===n&&(n=new Eu[e](this.tolerance_,this.maxExtent_,this.resolution_,this.pixelRatio_,this.overlaps_,this.declutterTree_),r[e]=n);return n},t.prototype.getReplays=function(){return this.replaysByZIndex_},t.prototype.isEmpty=function(){return Tt(this.replaysByZIndex_)},t.prototype.replay=function(t,e,i,r,n,o){var s=Object.keys(this.replaysByZIndex_).map(Number);s.sort(hr),t.save(),this.clip(t,e);var a,h,l,u,c,p,d=n||fu;for(a=0,h=s.length;a<h;++a){var f=s[a].toString();for(c=this.replaysByZIndex_[f],l=0,u=d.length;l<u;++l){var _=d[l];if(p=c[_],void 0!==p)if(!o||_!=Zl.IMAGE&&_!=Zl.TEXT)p.replay(t,e,i,r);else{var g=o[f];g?g.push(p,e.slice(0)):o[f]=[p,e.slice(0)]}}}t.restore()},t}(Hl),wu={0:[[!0]]};function Ru(t,e,i){var r,n=Math.floor(t.length/2);if(n<=e)for(r=n;r<e;r++)t[r][i]=!0;else if(e<n)for(r=e+1;r<n;r++)t[r][i]=!0}var Iu=.5,Lu={Point:function(t,e,i,r){var n=i.getImage();if(n){if(n.getImageState()!=di.LOADED)return;var o=t.getReplay(i.getZIndex(),Zl.IMAGE);o.setImageStyle(n,t.addDeclutter(!1)),o.drawPoint(e,r)}var s=i.getText();if(s){var a=t.getReplay(i.getZIndex(),Zl.TEXT);a.setTextStyle(s,t.addDeclutter(!!n)),a.drawText(e,r)}},LineString:function(t,e,i,r){var n=i.getStroke();if(n){var o=t.getReplay(i.getZIndex(),Zl.LINE_STRING);o.setFillStrokeStyle(null,n),o.drawLineString(e,r)}var s=i.getText();if(s){var a=t.getReplay(i.getZIndex(),Zl.TEXT);a.setTextStyle(s,t.addDeclutter(!1)),a.drawText(e,r)}},Polygon:function(t,e,i,r){var n=i.getFill(),o=i.getStroke();if(n||o){var s=t.getReplay(i.getZIndex(),Zl.POLYGON);s.setFillStrokeStyle(n,o),s.drawPolygon(e,r)}var a=i.getText();if(a){var h=t.getReplay(i.getZIndex(),Zl.TEXT);h.setTextStyle(a,t.addDeclutter(!1)),h.drawText(e,r)}},MultiPoint:function(t,e,i,r){var n=i.getImage();if(n){if(n.getImageState()!=di.LOADED)return;var o=t.getReplay(i.getZIndex(),Zl.IMAGE);o.setImageStyle(n,t.addDeclutter(!1)),o.drawMultiPoint(e,r)}var s=i.getText();if(s){var a=t.getReplay(i.getZIndex(),Zl.TEXT);a.setTextStyle(s,t.addDeclutter(!!n)),a.drawText(e,r)}},MultiLineString:function(t,e,i,r){var n=i.getStroke();if(n){var o=t.getReplay(i.getZIndex(),Zl.LINE_STRING);o.setFillStrokeStyle(null,n),o.drawMultiLineString(e,r)}var s=i.getText();if(s){var a=t.getReplay(i.getZIndex(),Zl.TEXT);a.setTextStyle(s,t.addDeclutter(!1)),a.drawText(e,r)}},MultiPolygon:function(t,e,i,r){var n=i.getFill(),o=i.getStroke();if(o||n){var s=t.getReplay(i.getZIndex(),Zl.POLYGON);s.setFillStrokeStyle(n,o),s.drawMultiPolygon(e,r)}var a=i.getText();if(a){var h=t.getReplay(i.getZIndex(),Zl.TEXT);h.setTextStyle(a,t.addDeclutter(!1)),h.drawText(e,r)}},GeometryCollection:function(t,e,i,r){var n,o,s=e.getGeometriesArray();for(n=0,o=s.length;n<o;++n){var a=Lu[s[n].getType()];a(t,s[n],i,r)}},Circle:function(t,e,i,r){var n=i.getFill(),o=i.getStroke();if(n||o){var s=t.getReplay(i.getZIndex(),Zl.CIRCLE);s.setFillStrokeStyle(n,o),s.drawCircle(e,r)}var a=i.getText();if(a){var h=t.getReplay(i.getZIndex(),Zl.TEXT);h.setTextStyle(a,t.addDeclutter(!1)),h.drawText(e,r)}}};function bu(t,e){return Et(t)-Et(e)}function Pu(t,e){var i=Fu(t,e);return i*i}function Fu(t,e){return Iu*t/e}function Mu(t,e,i,r,n,o){var s=!1,a=i.getImage();if(a){var h=a.getImageState();h==di.LOADED||h==di.ERROR?a.unlistenImageChange(n,o):(h==di.IDLE&&a.load(),h=a.getImageState(),a.listenImageChange(n,o),s=!0)}return function(t,e,i,r){var n=i.getGeometryFunction()(e);if(!n)return;var o=n.getSimplifiedGeometry(r);if(i.getRenderer())!function t(e,i,r,n){if(i.getType()==Lt.GEOMETRY_COLLECTION){for(var o=i.getGeometries(),s=0,a=o.length;s<a;++s)t(e,o[s],r,n);return}var h=e.getReplay(r.getZIndex(),Zl.DEFAULT);h.drawCustom(i,n,r.getRenderer())}(t,o,i,e);else{var s=Lu[o.getType()];s(t,o,i,e)}}(t,e,i,r),s}var Ou=function(e){function t(t){e.call(this,t),this.declutterTree_=t.getDeclutter()?Sh(9,void 0):null,this.dirty_=!1,this.renderedRevision_=-1,this.renderedResolution_=NaN,this.renderedExtent_=[1/0,1/0,-1/0,-1/0],this.renderedRenderOrder_=null,this.replayGroup_=null,this.replayGroupChanged=!0,this.context=De(),E(Li,w.CLEAR,this.handleFontsChanged_,this)}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.disposeInternal=function(){d(Li,w.CLEAR,this.handleFontsChanged_,this),e.prototype.disposeInternal.call(this)},t.prototype.compose=function(t,e,i){var r=e.extent,n=e.pixelRatio,o=i.managed?e.skippedFeatureUids:{},s=e.viewState,a=s.projection,h=s.rotation,l=a.getExtent(),u=this.getLayer().getSource(),c=this.getTransform(e,0),p=i.extent,d=void 0!==p;d&&this.clip(t,e,p);var f=this.replayGroup_;if(f&&!f.isEmpty()){this.declutterTree_&&this.declutterTree_.clear();var _,g=this.getLayer(),y=0,v=0,m=1!==i.opacity,x=g.hasListener(wn);if(m||x){var S=t.canvas.width,C=t.canvas.height;if(h){var E=Math.round(Math.sqrt(S*S+C*C));y=(E-S)/2,v=(E-C)/2,S=C=E}this.context.canvas.width=S,this.context.canvas.height=C,_=this.context}else _=t;var T=_.globalAlpha;m||(_.globalAlpha=i.opacity),_!=t&&_.translate(y,v);var w=e.size[0]*n,R=e.size[1]*n;if(Di(_,-h,w/2,R/2),f.replay(_,c,h,o),u.getWrapX()&&a.canWrapX()&&!Q(l,r)){for(var I,L=r[0],b=ct(l),P=0;L<l[0];)I=b*--P,c=this.getTransform(e,I),f.replay(_,c,h,o),L+=b;for(P=0,L=r[2];L>l[2];)I=b*++P,c=this.getTransform(e,I),f.replay(_,c,h,o),L-=b}if(Di(_,h,w/2,R/2),x&&this.dispatchRenderEvent(_,e,c),_!=t){if(m){var F=t.globalAlpha;t.globalAlpha=i.opacity,t.drawImage(_.canvas,-y,-v),t.globalAlpha=F}else t.drawImage(_.canvas,-y,-v);_.translate(-y,-v)}m||(_.globalAlpha=T)}d&&t.restore()},t.prototype.composeFrame=function(t,e,i){var r=this.getTransform(t,0);this.preCompose(i,t,r),this.compose(i,t,e),this.postCompose(i,t,e,r)},t.prototype.forEachFeatureAtCoordinate=function(t,e,i,r,n){if(this.replayGroup_){var o=e.viewState.resolution,s=e.viewState.rotation,a=this.getLayer(),h={};return this.replayGroup_.forEachFeatureAtCoordinate(t,o,s,i,{},function(t){var e=Et(t).toString();if(!(e in h))return h[e]=!0,r.call(n,t,a)},null)}},t.prototype.handleFontsChanged_=function(t){var e=this.getLayer();e.getVisible()&&this.replayGroup_&&e.changed()},t.prototype.handleStyleImageChange_=function(t){this.renderIfReadyAndVisible()},t.prototype.prepareFrame=function(t,e){var n=this.getLayer(),i=n.getSource(),r=t.viewHints[rs.ANIMATING],o=t.viewHints[rs.INTERACTING],s=n.getUpdateWhileAnimating(),a=n.getUpdateWhileInteracting();if(!this.dirty_&&!s&&r||!a&&o)return!0;var h=t.extent,l=t.viewState,u=l.projection,c=l.resolution,p=t.pixelRatio,d=n.getRevision(),f=n.getRenderBuffer(),_=n.getRenderOrder();void 0===_&&(_=bu);var g=G(h,f*c),y=l.projection.getExtent();if(i.getWrapX()&&l.projection.canWrapX()&&!Q(y,t.extent)){var v=ct(y),m=Math.max(ct(g)/2,v);g[0]=y[0]-m,g[2]=y[2]+m}if(!this.dirty_&&this.renderedResolution_==c&&this.renderedRevision_==d&&this.renderedRenderOrder_==_&&Q(this.renderedExtent_,g))return!(this.replayGroupChanged=!1);this.replayGroup_=null,this.dirty_=!1;var x=new Tu(Fu(c,p),g,c,p,i.getOverlaps(),this.declutterTree_,n.getRenderBuffer());i.loadFeatures(g,c,u);var S=function(t){var e,i=t.getStyleFunction()||n.getStyleFunction();if(i&&(e=i(t,c)),e){var r=this.renderFeature(t,c,p,e,x);this.dirty_=this.dirty_||r}}.bind(this);if(_){var C=[];i.forEachFeatureInExtent(g,function(t){C.push(t)},this),C.sort(_);for(var E=0,T=C.length;E<T;++E)S(C[E])}else i.forEachFeatureInExtent(g,S,this);return x.finish(),this.renderedResolution_=c,this.renderedRevision_=d,this.renderedRenderOrder_=_,this.renderedExtent_=g,this.replayGroup_=x,this.replayGroupChanged=!0},t.prototype.renderFeature=function(t,e,i,r,n){if(!r)return!1;var o=!1;if(Array.isArray(r))for(var s=0,a=r.length;s<a;++s)o=Mu(n,t,r[s],Pu(e,i),this.handleStyleImageChange_,this)||o;else o=Mu(n,t,r,Pu(e,i),this.handleStyleImageChange_,this);return o},t}(Bl);Ou.handles=function(t){return t.getType()===oh.VECTOR},Ou.create=function(t,e){return new Ou(e)};var Nu="image",Au="hybrid",Gu="vector",ku={image:[Zl.POLYGON,Zl.CIRCLE,Zl.LINE_STRING,Zl.IMAGE,Zl.TEXT],hybrid:[Zl.POLYGON,Zl.LINE_STRING]},Du={image:[Zl.DEFAULT],hybrid:[Zl.IMAGE,Zl.TEXT,Zl.DEFAULT],vector:fu},ju=function(F){function t(t){F.call(this,t,!0),this.declutterTree_=t.getDeclutter()?Sh(9,void 0):null,this.dirty_=!1,this.renderedLayerRevision_,this.tmpTransform_=[1,0,0,1,0,0],this.zDirection=t.getRenderMode()==Gu?1:0,E(Li,w.CLEAR,this.handleFontsChanged_,this)}return F&&(t.__proto__=F),((t.prototype=Object.create(F&&F.prototype)).constructor=t).prototype.disposeInternal=function(){d(Li,w.CLEAR,this.handleFontsChanged_,this),F.prototype.disposeInternal.call(this)},t.prototype.getTile=function(t,e,i,r,n){var o=F.prototype.getTile.call(this,t,e,i,r,n);return o.getState()===Gn&&(this.createReplayGroup_(o,r,n),this.context&&this.renderTileImage_(o,r,n)),o},t.prototype.prepareFrame=function(t,e){var i=this.getLayer(),r=i.getRevision();if(this.renderedLayerRevision_!=r){this.renderedTiles.length=0;var n=i.getRenderMode();this.context||n==Gu||(this.context=De()),this.context&&n==Gu&&(this.context=null)}return this.renderedLayerRevision_=r,F.prototype.prepareFrame.apply(this,arguments)},t.prototype.createReplayGroup_=function(y,v,m){var x=this,S=this.getLayer(),t=S.getRevision(),C=S.getRenderOrder()||null,E=y.getReplayState(S);if(E.dirty||E.renderedRevision!=t||E.renderedRenderOrder!=C){for(var T=S.getSource(),w=T.getTileGrid(),R=T.getTileGridForProjection(m).getResolution(y.tileCoord[0]),I=y.extent,e=function(t,e){var i=y.getTile(y.tileKeys[t]);if(i.getState()==Gn){var r=i.tileCoord,n=w.getTileCoordExtent(r),o=ht(I,n),s=$(n,o)?null:G(o,S.getRenderBuffer()*R,x.tmpExtent),a=i.getProjection(),h=!1;ue(m,a)||(h=!0,i.setProjection(m)),E.dirty=!1;var l=new Tu(0,o,R,v,T.getOverlaps(),x.declutterTree_,S.getRenderBuffer()),u=Pu(R,v),c=function(t){var e,i=t.getStyleFunction()||S.getStyleFunction();if(i&&(e=i(t,R)),e){var r=this.renderFeature(t,u,e,l);this.dirty_=this.dirty_||r,E.dirty=E.dirty||r}},p=i.getFeatures();C&&C!==E.renderedRenderOrder&&p.sort(C);for(var d=0,f=p.length;d<f;++d){var _=p[d];h&&(a.getUnits()==Ot.TILE_PIXELS&&(a.setWorldExtent(n),a.setExtent(i.getExtent())),_.getGeometry().transform(a,m)),s&&!wt(s,_.getGeometry().getExtent())||c.call(x,_)}for(var g in l.finish(),l.getReplays());i.setReplayGroup(S,y.tileCoord.toString(),l)}},i=0,r=y.tileKeys.length;i<r;++i)e(i);E.renderedRevision=t,E.renderedRenderOrder=C}},t.prototype.forEachFeatureAtCoordinate=function(t,e,i,r,n){var o=e.viewState.resolution,s=e.viewState.rotation;i=null==i?0:i;var a,h,l,u,c,p=this.getLayer(),d={},f=this.renderedTiles;for(l=0,u=f.length;l<u;++l){var _=f[l];if(j(a=G(_.extent,i*o,a),t))for(var g=0,y=_.tileKeys.length;g<y;++g){var v=_.getTile(_.tileKeys[g]);v.getState()==Gn&&(c=v.getReplayGroup(p,_.tileCoord.toString()),h=h||c.forEachFeatureAtCoordinate(t,o,s,i,{},function(t){var e=Et(t).toString();if(!(e in d))return d[e]=!0,r.call(n,t,p)},null))}}return h},t.prototype.getReplayTransform_=function(t,e){var i=this.getLayer().getSource().getTileGrid(),r=t.tileCoord,n=i.getResolution(r[0]),o=e.viewState,s=e.pixelRatio,a=o.resolution/s,h=i.getTileCoordExtent(r,this.tmpExtent),l=o.center,u=lt(h),c=e.size,p=Math.round(s*c[0]/2),d=Math.round(s*c[1]/2);return Te(this.tmpTransform_,p,d,n/a,n/a,o.rotation,(u[0]-l[0])/n,(l[1]-u[1])/n)},t.prototype.handleFontsChanged_=function(t){var e=this.getLayer();e.getVisible()&&void 0!==this.renderedLayerRevision_&&e.changed()},t.prototype.handleStyleImageChange_=function(t){this.renderIfReadyAndVisible()},t.prototype.postCompose=function(t,e,i){var r=this.getLayer(),n=r.getRenderMode();if(n!=Nu){var o,s,a=r.getDeclutter()?{}:null,h=r.getSource(),l=Du[n],u=e.pixelRatio,c=e.viewState.rotation,p=e.size;c&&Di(t,-c,o=Math.round(u*p[0]/2),s=Math.round(u*p[1]/2)),a&&this.declutterTree_.clear();for(var d=this.renderedTiles,f=h.getTileGridForProjection(e.viewState.projection),_=[],g=[],y=d.length-1;0<=y;--y){var v=d[y];if(v.getState()!=jn)for(var m=v.tileCoord,x=f.getTileCoordExtent(m,this.tmpExtent)[0]-v.extent[0],S=void 0,C=0,E=v.tileKeys.length;C<E;++C){var T=v.getTile(v.tileKeys[C]);if(T.getState()==Gn){var w=T.getReplayGroup(r,m.toString());if(w&&w.hasReplays(l)){S||(S=this.getTransform(e,x));var R=T.tileCoord[0],I=w.getClipCoords(S);t.save(),t.globalAlpha=i.opacity;for(var L=0,b=_.length;L<b;++L){var P=_[L];R<g[L]&&(t.beginPath(),t.moveTo(I[0],I[1]),t.lineTo(I[2],I[3]),t.lineTo(I[4],I[5]),t.lineTo(I[6],I[7]),t.moveTo(P[6],P[7]),t.lineTo(P[4],P[5]),t.lineTo(P[2],P[3]),t.lineTo(P[0],P[1]),t.clip())}w.replay(t,S,c,{},l,a),t.restore(),_.push(I),g.push(R)}}}}a&&function(t,e,i){for(var r=Object.keys(t).map(Number).sort(hr),n={},o=0,s=r.length;o<s;++o)for(var a=t[r[o].toString()],h=0,l=a.length;h<l;){var u=a[h++],c=a[h++];u.replay(e,c,i,n)}}(a,t,c),c&&Di(t,c,o,s)}F.prototype.postCompose.apply(this,arguments)},t.prototype.renderFeature=function(t,e,i,r){if(!i)return!1;var n=!1;if(Array.isArray(i))for(var o=0,s=i.length;o<s;++o)n=Mu(r,t,i[o],e,this.handleStyleImageChange_,this)||n;else n=Mu(r,t,i,e,this.handleStyleImageChange_,this);return n},t.prototype.renderTileImage_=function(t,e,i){var r=this.getLayer(),n=t.getReplayState(r),o=r.getRevision(),s=ku[r.getRenderMode()];if(s&&n.renderedTileRevision!==o){n.renderedTileRevision=o;var a=t.wrappedTileCoord,h=a[0],l=r.getSource(),u=l.getTileGridForProjection(i),c=u.getResolution(h),p=t.getContext(r),d=l.getTilePixelSize(h,e,i);p.canvas.width=d[0],p.canvas.height=d[1];for(var f=u.getTileCoordExtent(a,this.tmpExtent),_=0,g=t.tileKeys.length;_<g;++_){var y=t.getTile(t.tileKeys[_]);if(y.getState()==Gn){var v=e/c,m=ge(this.tmpTransform_);Ce(m,v,-v),Ee(m,-f[0],-f[3]),y.getReplayGroup(r,t.tileCoord.toString()).replay(p,m,0,{},s)}}}},t}(Kl);ju.handles=function(t){return t.getType()===oh.VECTOR_TILE},ju.create=function(t,e){return new ju(e)};var Uu,Yu=function(e){function t(t){(t=C({},t)).controls||(t.controls=As()),t.interactions||(t.interactions=Ll()),e.call(this,t)}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.createRenderer=function(){var t=new Ul(this);return t.registerLayerRenderers([zl,Kl,Ou,ju]),t},t}(Rs),Bu="bottom-left",Xu="bottom-center",zu="bottom-right",Vu="center-left",Wu="center-center",Ku="center-right",Hu="top-left",Zu="top-center",qu="top-right",Ju="element",Qu="map",$u="offset",tc="position",ec="positioning",ic=function(e){function t(t){e.call(this),this.options=t,this.id=t.id,this.insertFirst=void 0===t.insertFirst||t.insertFirst,this.stopEvent=void 0===t.stopEvent||t.stopEvent,this.element=document.createElement("DIV"),this.element.className=void 0!==t.className?t.className:"ol-overlay-container ol-selectable",this.element.style.position="absolute",this.autoPan=void 0!==t.autoPan&&t.autoPan,this.autoPanAnimation=t.autoPanAnimation||{},this.autoPanMargin=void 0!==t.autoPanMargin?t.autoPanMargin:20,this.rendered={bottom_:"",left_:"",right_:"",top_:"",visible:!0},this.mapPostrenderListenerKey=null,E(this,b(Ju),this.handleElementChanged,this),E(this,b(Qu),this.handleMapChanged,this),E(this,b($u),this.handleOffsetChanged,this),E(this,b(tc),this.handlePositionChanged,this),E(this,b(ec),this.handlePositioningChanged,this),void 0!==t.element&&this.setElement(t.element),this.setOffset(void 0!==t.offset?t.offset:[0,0]),this.setPositioning(void 0!==t.positioning?t.positioning:Hu),void 0!==t.position&&this.setPosition(t.position)}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.getElement=function(){return this.get(Ju)},t.prototype.getId=function(){return this.id},t.prototype.getMap=function(){return this.get(Qu)},t.prototype.getOffset=function(){return this.get($u)},t.prototype.getPosition=function(){return this.get(tc)},t.prototype.getPositioning=function(){return this.get(ec)},t.prototype.handleElementChanged=function(){Ye(this.element);var t=this.getElement();t&&this.element.appendChild(t)},t.prototype.handleMapChanged=function(){this.mapPostrenderListenerKey&&(Ue(this.element),g(this.mapPostrenderListenerKey),this.mapPostrenderListenerKey=null);var t=this.getMap();if(t){this.mapPostrenderListenerKey=E(t,Wo,this.render,this),this.updatePixelPosition();var e=this.stopEvent?t.getOverlayContainerStopEvent():t.getOverlayContainer();this.insertFirst?e.insertBefore(this.element,e.childNodes[0]||null):e.appendChild(this.element)}},t.prototype.render=function(){this.updatePixelPosition()},t.prototype.handleOffsetChanged=function(){this.updatePixelPosition()},t.prototype.handlePositionChanged=function(){this.updatePixelPosition(),this.get(tc)&&this.autoPan&&this.panIntoView()},t.prototype.handlePositioningChanged=function(){this.updatePixelPosition()},t.prototype.setElement=function(t){this.set(Ju,t)},t.prototype.setMap=function(t){this.set(Qu,t)},t.prototype.setOffset=function(t){this.set($u,t)},t.prototype.setPosition=function(t){this.set(tc,t)},t.prototype.panIntoView=function(){var t=this.getMap();if(t&&t.getTargetElement()){var e,i,r,n,o,s,a=this.getRect(t.getTargetElement(),t.getSize()),h=this.getElement(),l=this.getRect(h,[(n=h,o=n.offsetWidth,s=getComputedStyle(n),o+=parseInt(s.marginLeft,10)+parseInt(s.marginRight,10)),(e=h,i=e.offsetHeight,r=getComputedStyle(e),i+=parseInt(r.marginTop,10)+parseInt(r.marginBottom,10))]),u=this.autoPanMargin;if(!Q(a,l)){var c=l[0]-a[0],p=a[2]-l[2],d=l[1]-a[1],f=a[3]-l[3],_=[0,0];if(c<0?_[0]=c-u:p<0&&(_[0]=Math.abs(p)+u),d<0?_[1]=d-u:f<0&&(_[1]=Math.abs(f)+u),0!==_[0]||0!==_[1]){var g=t.getView().getCenter(),y=t.getPixelFromCoordinate(g),v=[y[0]+_[0],y[1]+_[1]];t.getView().animate({center:t.getCoordinateFromPixel(v),duration:this.autoPanAnimation.duration,easing:this.autoPanAnimation.easing})}}}},t.prototype.getRect=function(t,e){var i=t.getBoundingClientRect(),r=i.left+window.pageXOffset,n=i.top+window.pageYOffset;return[r,n,r+e[0],n+e[1]]},t.prototype.setPositioning=function(t){this.set(ec,t)},t.prototype.setVisible=function(t){this.rendered.visible!==t&&(this.element.style.display=t?"":"none",this.rendered.visible=t)},t.prototype.updatePixelPosition=function(){var t=this.getMap(),e=this.getPosition();if(t&&t.isRendered()&&e){var i=t.getPixelFromCoordinate(e),r=t.getSize();this.updateRenderedPosition(i,r)}else this.setVisible(!1)},t.prototype.updateRenderedPosition=function(t,e){var i=this.element.style,r=this.getOffset(),n=this.getPositioning();this.setVisible(!0);var o=r[0],s=r[1];if(n==zu||n==Ku||n==qu){""!==this.rendered.left_&&(this.rendered.left_=i.left="");var a=Math.round(e[0]-t[0]-o)+"px";this.rendered.right_!=a&&(this.rendered.right_=i.right=a)}else{""!==this.rendered.right_&&(this.rendered.right_=i.right=""),n!=Xu&&n!=Wu&&n!=Zu||(o-=this.element.offsetWidth/2);var h=Math.round(t[0]+o)+"px";this.rendered.left_!=h&&(this.rendered.left_=i.left=h)}if(n==Bu||n==Xu||n==zu){""!==this.rendered.top_&&(this.rendered.top_=i.top="");var l=Math.round(e[1]-t[1]-s)+"px";this.rendered.bottom_!=l&&(this.rendered.bottom_=i.bottom=l)}else{""!==this.rendered.bottom_&&(this.rendered.bottom_=i.bottom=""),n!=Vu&&n!=Wu&&n!=Ku||(s-=this.element.offsetHeight/2);var u=Math.round(t[1]+s)+"px";this.rendered.top_!=u&&(this.rendered.top_=i.top=u)}},t.prototype.getOptions=function(){return this.options},t}(R),rc=[0,0,4096,4096],nc=function(s){function t(t,e,i,r,n,o){s.call(this,t,e,o),this.consumers=0,this.extent_=null,this.format_=r,this.features_=null,this.loader_,this.projection_=null,this.replayGroups_={},this.tileLoadFunction_=n,this.url_=i}return s&&(t.__proto__=s),((t.prototype=Object.create(s&&s.prototype)).constructor=t).prototype.disposeInternal=function(){this.features_=null,this.replayGroups_={},this.state=jn,this.changed(),s.prototype.disposeInternal.call(this)},t.prototype.getExtent=function(){return this.extent_||rc},t.prototype.getFormat=function(){return this.format_},t.prototype.getFeatures=function(){return this.features_},t.prototype.getKey=function(){return this.url_},t.prototype.getProjection=function(){return this.projection_},t.prototype.getReplayGroup=function(t,e){return this.replayGroups_[Et(t)+","+e]},t.prototype.load=function(){this.state==Nn&&(this.setState(An),this.tileLoadFunction_(this,this.url_),this.loader_(null,NaN,null))},t.prototype.onLoad=function(t,e,i){this.setProjection(e),this.setFeatures(t),this.setExtent(i)},t.prototype.onError=function(){this.setState(kn)},t.prototype.setExtent=function(t){this.extent_=t},t.prototype.setFeatures=function(t){this.features_=t,this.setState(Gn)},t.prototype.setProjection=function(t){this.projection_=t},t.prototype.setReplayGroup=function(t,e,i){this.replayGroups_[Et(t)+","+e]=i},t.prototype.setLoader=function(t){this.loader_=t},t}(zn),oc=function(){if(!Uu){var t=document.body;t.webkitRequestFullscreen?Uu="webkitfullscreenchange":t.mozRequestFullScreen?Uu="mozfullscreenchange":t.msRequestFullscreen?Uu="MSFullscreenChange":t.requestFullscreen&&(Uu="fullscreenchange")}return Uu},sc=function(h){function t(t){var e=t||{};h.call(this,{element:document.createElement("div"),target:e.target}),this.cssClassName_=void 0!==e.className?e.className:"ol-full-screen";var i=void 0!==e.label?e.label:"⤢";this.labelNode_="string"==typeof i?document.createTextNode(i):i;var r=void 0!==e.labelActive?e.labelActive:"×";this.labelActiveNode_="string"==typeof r?document.createTextNode(r):r;var n=e.tipLabel?e.tipLabel:"Toggle full-screen",o=document.createElement("button");o.className=this.cssClassName_+"-"+hc(),o.setAttribute("type","button"),o.title=n,o.appendChild(this.labelNode_),E(o,w.CLICK,this.handleClick_,this);var s=this.cssClassName_+" "+_i+" "+gi+" "+(ac()?"":"ol-unsupported"),a=this.element;a.className=s,a.appendChild(o),this.keys_=void 0!==e.keys&&e.keys,this.source_=e.source}return h&&(t.__proto__=h),((t.prototype=Object.create(h&&h.prototype)).constructor=t).prototype.handleClick_=function(t){t.preventDefault(),this.handleFullScreen_()},t.prototype.handleFullScreen_=function(){if(ac()){var t,e,i=this.getMap();if(i)if(hc())document.exitFullscreen?document.exitFullscreen():document.msExitFullscreen?document.msExitFullscreen():document.mozCancelFullScreen?document.mozCancelFullScreen():document.webkitExitFullscreen&&document.webkitExitFullscreen();else t=this.source_?"string"==typeof this.source_?document.getElementById(this.source_):this.source_:i.getTargetElement(),this.keys_?(e=t).mozRequestFullScreenWithKeys?e.mozRequestFullScreenWithKeys():e.webkitRequestFullscreen?e.webkitRequestFullscreen(Element.ALLOW_KEYBOARD_INPUT):lc(e):lc(t)}},t.prototype.handleFullScreenChange_=function(){var t=this.element.firstElementChild,e=this.getMap();hc()?(t.className=this.cssClassName_+"-true",je(this.labelActiveNode_,this.labelNode_)):(t.className=this.cssClassName_+"-false",je(this.labelNode_,this.labelActiveNode_)),e&&e.updateSize()},t.prototype.setMap=function(t){h.prototype.setMap.call(this,t),t&&this.listenerKeys.push(E(document,oc(),this.handleFullScreenChange_,this))},t}(Is);function ac(){var t=document.body;return!!(t.webkitRequestFullscreen||t.mozRequestFullScreen&&document.mozFullScreenEnabled||t.msRequestFullscreen&&document.msFullscreenEnabled||t.requestFullscreen&&document.fullscreenEnabled)}function hc(){return!!(document.webkitIsFullScreen||document.mozFullScreen||document.msFullscreenElement||document.fullscreenElement)}function lc(t){t.requestFullscreen?t.requestFullscreen():t.msRequestFullscreen?t.msRequestFullscreen():t.mozRequestFullScreen?t.mozRequestFullScreen():t.webkitRequestFullscreen&&t.webkitRequestFullscreen()}var uc=function(y){function t(t){var e=t||{};y.call(this,{element:document.createElement("div"),render:e.render||cc,target:e.target}),this.collapsed_=void 0===e.collapsed||e.collapsed,this.collapsible_=void 0===e.collapsible||e.collapsible,this.collapsible_||(this.collapsed_=!1);var i=void 0!==e.className?e.className:"ol-overviewmap",r=void 0!==e.tipLabel?e.tipLabel:"Overview map",n=void 0!==e.collapseLabel?e.collapseLabel:"«";"string"==typeof n?(this.collapseLabel_=document.createElement("span"),this.collapseLabel_.textContent=n):this.collapseLabel_=n;var o=void 0!==e.label?e.label:"»";"string"==typeof o?(this.label_=document.createElement("span"),this.label_.textContent=o):this.label_=o;var s=this.collapsible_&&!this.collapsed_?this.collapseLabel_:this.label_,a=document.createElement("button");a.setAttribute("type","button"),a.title=r,a.appendChild(s),E(a,w.CLICK,this.handleClick_,this),this.ovmapDiv_=document.createElement("DIV"),this.ovmapDiv_.className="ol-overviewmap-map",this.ovmap_=new Yu({controls:new M,interactions:new M,view:e.view});var h=this.ovmap_;e.layers&&e.layers.forEach(function(t){h.addLayer(t)}.bind(this));var l=document.createElement("DIV");l.className="ol-overviewmap-box",l.style.boxSizing="border-box",this.boxOverlay_=new ic({position:[0,0],positioning:Bu,element:l}),this.ovmap_.addOverlay(this.boxOverlay_);var u=i+" "+_i+" "+gi+(this.collapsed_&&this.collapsible_?" "+yi:"")+(this.collapsible_?"":" ol-uncollapsible"),c=this.element;c.className=u,c.appendChild(this.ovmapDiv_),c.appendChild(a);var p=this,d=this.boxOverlay_,f=this.boxOverlay_.getElement(),_=function(t){var e,i=h.getEventCoordinate({clientX:(e=t).clientX-f.offsetWidth/2,clientY:e.clientY+f.offsetHeight/2});d.setPosition(i)},g=function(t){var e=h.getEventCoordinate(t);p.getMap().getView().setCenter(e),window.removeEventListener("mousemove",_),window.removeEventListener("mouseup",g)};f.addEventListener("mousedown",function(){window.addEventListener("mousemove",_),window.addEventListener("mouseup",g)})}return y&&(t.__proto__=y),((t.prototype=Object.create(y&&y.prototype)).constructor=t).prototype.setMap=function(t){var e=this.getMap();if(t!==e){if(e){var i=e.getView();i&&this.unbindView_(i),this.ovmap_.setTarget(null)}if(y.prototype.setMap.call(this,t),t){this.ovmap_.setTarget(this.ovmapDiv_),this.listenerKeys.push(E(t,a,this.handleMapPropertyChange_,this)),0===this.ovmap_.getLayers().getLength()&&this.ovmap_.setLayerGroup(t.getLayerGroup());var r=t.getView();r&&(this.bindView_(r),r.isDef()&&(this.ovmap_.updateSize(),this.resetExtent_()))}}},t.prototype.handleMapPropertyChange_=function(t){if(t.key===Zo.VIEW){var e=t.oldValue;e&&this.unbindView_(e);var i=this.getMap().getView();this.bindView_(i)}},t.prototype.bindView_=function(t){E(t,b(ss),this.handleRotationChanged_,this)},t.prototype.unbindView_=function(t){d(t,b(ss),this.handleRotationChanged_,this)},t.prototype.handleRotationChanged_=function(){this.ovmap_.getView().setRotation(this.getMap().getView().getRotation())},t.prototype.validateExtent_=function(){var t=this.getMap(),e=this.ovmap_;if(t.isRendered()&&e.isRendered()){var i=t.getSize(),r=t.getView().calculateExtent(i),n=e.getSize(),o=e.getView().calculateExtent(n),s=e.getPixelFromCoordinate(lt(r)),a=e.getPixelFromCoordinate(nt(r)),h=Math.abs(s[0]-a[0]),l=Math.abs(s[1]-a[1]),u=n[0],c=n[1];h<.1*u||l<.1*c||.75*u<h||.75*c<l?this.resetExtent_():Q(o,r)||this.recenter_()}},t.prototype.resetExtent_=function(){var t=this.getMap(),e=this.ovmap_,i=t.getSize(),r=t.getView().calculateExtent(i),n=e.getView(),o=Math.log(7.5)/Math.LN2;dt(r,1/(.1*Math.pow(2,o/2))),n.fit(r)},t.prototype.recenter_=function(){var t=this.getMap(),e=this.ovmap_,i=t.getView();e.getView().setCenter(i.getCenter())},t.prototype.updateBox_=function(){var t=this.getMap(),e=this.ovmap_;if(t.isRendered()&&e.isRendered()){var i=t.getSize(),r=t.getView(),n=e.getView(),o=r.getRotation(),s=this.boxOverlay_,a=this.boxOverlay_.getElement(),h=r.calculateExtent(i),l=n.getResolution(),u=rt(h),c=ut(h),p=this.calculateCoordinateRotate_(o,u);s.setPosition(p),a&&(a.style.width=Math.abs((u[0]-c[0])/l)+"px",a.style.height=Math.abs((c[1]-u[1])/l)+"px")}},t.prototype.calculateCoordinateRotate_=function(t,e){var i,r=this.getMap().getView().getCenter();return r&&(pn(i=[e[0]-r[0],e[1]-r[1]],t),an(i,r)),i},t.prototype.handleClick_=function(t){t.preventDefault(),this.handleToggle_()},t.prototype.handleToggle_=function(){this.element.classList.toggle(yi),this.collapsed_?je(this.collapseLabel_,this.label_):je(this.label_,this.collapseLabel_),this.collapsed_=!this.collapsed_;var t=this.ovmap_;this.collapsed_||t.isRendered()||(t.updateSize(),this.resetExtent_(),p(t,Wo,function(t){this.updateBox_()},this))},t.prototype.getCollapsible=function(){return this.collapsible_},t.prototype.setCollapsible=function(t){this.collapsible_!==t&&(this.collapsible_=t,this.element.classList.toggle("ol-uncollapsible"),!t&&this.collapsed_&&this.handleToggle_())},t.prototype.setCollapsed=function(t){this.collapsible_&&this.collapsed_!==t&&this.handleToggle_()},t.prototype.getCollapsed=function(){return this.collapsed_},t.prototype.getOverviewMap=function(){return this.ovmap_},t}(Is);function cc(t){this.validateExtent_(),this.updateBox_()}var pc="units",dc="degrees",fc="imperial",_c="nautical",gc="metric",yc="us",vc=[1,2,5],mc=function(r){function t(t){var e=t||{},i=void 0!==e.className?e.className:"ol-scale-line";r.call(this,{element:document.createElement("DIV"),render:e.render||xc,target:e.target}),this.innerElement_=document.createElement("DIV"),this.innerElement_.className=i+"-inner",this.element.className=i+" "+_i,this.element.appendChild(this.innerElement_),this.viewState_=null,this.minWidth_=void 0!==e.minWidth?e.minWidth:64,this.renderedVisible_=!1,this.renderedWidth_=void 0,this.renderedHTML_="",E(this,b(pc),this.handleUnitsChanged_,this),this.setUnits(e.units||gc)}return r&&(t.__proto__=r),((t.prototype=Object.create(r&&r.prototype)).constructor=t).prototype.getUnits=function(){return this.get(pc)},t.prototype.handleUnitsChanged_=function(){this.updateElement_()},t.prototype.setUnits=function(t){this.set(pc,t)},t.prototype.updateElement_=function(){var t=this.viewState_;if(t){var e=t.center,i=t.projection,r=this.getUnits(),n=r==dc?Ot.DEGREES:Ot.METERS,o=oe(i,t.resolution,e,n);i.getUnits()!=Ot.DEGREES&&i.getMetersPerUnit()&&n==Ot.METERS&&(o*=i.getMetersPerUnit());var s=this.minWidth_*o,a="";if(r==dc){var h=Nt[Ot.DEGREES];i.getUnits()==Ot.DEGREES?s*=h:o/=h,s<h/60?(a="″",o*=3600):s<h?(a="′",o*=60):a="°"}else r==fc?s<.9144?(a="in",o/=.0254):s<1609.344?(a="ft",o/=.3048):(a="mi",o/=1609.344):r==_c?(o/=1852,a="nm"):r==gc?s<.001?(a="μm",o*=1e6):s<1?(a="mm",o*=1e3):s<1e3?a="m":(a="km",o/=1e3):r==yc?s<.9144?(a="in",o*=39.37):s<1609.344?(a="ft",o/=.30480061):(a="mi",o/=1609.3472):Z(!1,33);for(var l,u,c=3*Math.floor(Math.log(this.minWidth_*o)/Math.log(10));;){if(l=vc[(c%3+3)%3]*Math.pow(10,Math.floor(c/3)),u=Math.round(l/o),isNaN(u))return this.element.style.display="none",void(this.renderedVisible_=!1);if(u>=this.minWidth_)break;++c}var p=l+" "+a;this.renderedHTML_!=p&&(this.innerElement_.innerHTML=p,this.renderedHTML_=p),this.renderedWidth_!=u&&(this.innerElement_.style.width=u+"px",this.renderedWidth_=u),this.renderedVisible_||(this.element.style.display="",this.renderedVisible_=!0)}else this.renderedVisible_&&(this.element.style.display="none",this.renderedVisible_=!1)},t}(Is);function xc(t){var e=t.frameState;this.viewState_=e?e.viewState:null,this.updateElement_()}var Sc=0,Cc=1,Ec=function(o){function t(t){var e=t||{};o.call(this,{element:document.createElement("div"),render:e.render||Tc}),this.currentResolution_=void 0,this.direction_=Sc,this.dragging_,this.heightLimit_=0,this.widthLimit_=0,this.previousX_,this.previousY_,this.thumbSize_=null,this.sliderInitialized_=!1,this.duration_=void 0!==e.duration?e.duration:200;var i=void 0!==e.className?e.className:"ol-zoomslider",r=document.createElement("button");r.setAttribute("type","button"),r.className=i+"-thumb "+_i;var n=this.element;n.className=i+" "+_i+" "+gi,n.appendChild(r),this.dragger_=new zo(n),E(this.dragger_,$n,this.handleDraggerStart_,this),E(this.dragger_,Qn,this.handleDraggerDrag_,this),E(this.dragger_,to,this.handleDraggerEnd_,this),E(n,w.CLICK,this.handleContainerClick_,this),E(r,w.CLICK,x)}return o&&(t.__proto__=o),((t.prototype=Object.create(o&&o.prototype)).constructor=t).prototype.disposeInternal=function(){this.dragger_.dispose(),o.prototype.disposeInternal.call(this)},t.prototype.setMap=function(t){o.prototype.setMap.call(this,t),t&&t.render()},t.prototype.initSlider_=function(){var t=this.element,e=t.offsetWidth,i=t.offsetHeight,r=t.firstElementChild,n=getComputedStyle(r),o=r.offsetWidth+parseFloat(n.marginRight)+parseFloat(n.marginLeft),s=r.offsetHeight+parseFloat(n.marginTop)+parseFloat(n.marginBottom);this.thumbSize_=[o,s],i<e?(this.direction_=Cc,this.widthLimit_=e-o):(this.direction_=Sc,this.heightLimit_=i-s),this.sliderInitialized_=!0},t.prototype.handleContainerClick_=function(t){var e=this.getMap().getView(),i=this.getRelativePosition_(t.offsetX-this.thumbSize_[0]/2,t.offsetY-this.thumbSize_[1]/2),r=this.getResolutionForPosition_(i);e.animate({resolution:e.constrainResolution(r),duration:this.duration_,easing:Yn})},t.prototype.handleDraggerStart_=function(t){this.dragging_||t.originalEvent.target!==this.element.firstElementChild||(this.getMap().getView().setHint(rs.INTERACTING,1),this.previousX_=t.clientX,this.previousY_=t.clientY,this.dragging_=!0)},t.prototype.handleDraggerDrag_=function(t){if(this.dragging_){var e=this.element.firstElementChild,i=t.clientX-this.previousX_+parseInt(e.style.left,10),r=t.clientY-this.previousY_+parseInt(e.style.top,10),n=this.getRelativePosition_(i,r);this.currentResolution_=this.getResolutionForPosition_(n),this.getMap().getView().setResolution(this.currentResolution_),this.setThumbPosition_(this.currentResolution_),this.previousX_=t.clientX,this.previousY_=t.clientY}},t.prototype.handleDraggerEnd_=function(t){if(this.dragging_){var e=this.getMap().getView();e.setHint(rs.INTERACTING,-1),e.animate({resolution:e.constrainResolution(this.currentResolution_),duration:this.duration_,easing:Yn}),this.dragging_=!1,this.previousX_=void 0,this.previousY_=void 0}},t.prototype.setThumbPosition_=function(t){var e=this.getPositionForResolution_(t),i=this.element.firstElementChild;this.direction_==Cc?i.style.left=this.widthLimit_*e+"px":i.style.top=this.heightLimit_*e+"px"},t.prototype.getRelativePosition_=function(t,e){return gt(this.direction_===Cc?t/this.widthLimit_:e/this.heightLimit_,0,1)},t.prototype.getResolutionForPosition_=function(t){return this.getMap().getView().getResolutionForValueFunction()(1-t)},t.prototype.getPositionForResolution_=function(t){return 1-this.getMap().getView().getValueForResolutionFunction()(t)},t}(Is);function Tc(t){if(t.frameState){this.sliderInitialized_||this.initSlider_();var e=t.frameState.viewState.resolution;e!==this.currentResolution_&&(this.currentResolution_=e,this.setThumbPosition_(e))}}var wc=function(h){function t(t){var e=t||{};h.call(this,{element:document.createElement("div"),target:e.target}),this.extent=e.extent?e.extent:null;var i=void 0!==e.className?e.className:"ol-zoom-extent",r=void 0!==e.label?e.label:"E",n=void 0!==e.tipLabel?e.tipLabel:"Fit to extent",o=document.createElement("button");o.setAttribute("type","button"),o.title=n,o.appendChild("string"==typeof r?document.createTextNode(r):r),E(o,w.CLICK,this.handleClick_,this);var s=i+" "+_i+" "+gi,a=this.element;a.className=s,a.appendChild(o)}return h&&(t.__proto__=h),((t.prototype=Object.create(h&&h.prototype)).constructor=t).prototype.handleClick_=function(t){t.preventDefault(),this.handleZoomToExtent()},t.prototype.handleZoomToExtent=function(){var t=this.getMap().getView(),e=this.extent?this.extent:t.getProjection().getExtent();t.fit(e)},t}(Is),Rc=function(t){this.source_=t};Rc.prototype.getType=function(){},Rc.prototype.getSource=function(){return this.source_},Rc.prototype.isAnimated=v;var Ic=function(e){function t(t){e.call(this,t)}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.getType=function(){return 35632},t}(Rc),Lc=function(e){function t(t){e.call(this,t)}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.getType=function(){return 35633},t}(Rc),bc=new Ic("precision mediump float;\nvarying vec2 v_center;\nvarying vec2 v_offset;\nvarying float v_halfWidth;\nvarying float v_pixelRatio;\n\n\n\nuniform float u_opacity;\nuniform vec4 u_fillColor;\nuniform vec4 u_strokeColor;\nuniform vec2 u_size;\n\nvoid main(void) {\n vec2 windowCenter = vec2((v_center.x + 1.0) / 2.0 * u_size.x * v_pixelRatio,\n (v_center.y + 1.0) / 2.0 * u_size.y * v_pixelRatio);\n vec2 windowOffset = vec2((v_offset.x + 1.0) / 2.0 * u_size.x * v_pixelRatio,\n (v_offset.y + 1.0) / 2.0 * u_size.y * v_pixelRatio);\n float radius = length(windowCenter - windowOffset);\n float dist = length(windowCenter - gl_FragCoord.xy);\n if (dist > radius + v_halfWidth) {\n if (u_strokeColor.a == 0.0) {\n gl_FragColor = u_fillColor;\n } else {\n gl_FragColor = u_strokeColor;\n }\n gl_FragColor.a = gl_FragColor.a - (dist - (radius + v_halfWidth));\n } else if (u_fillColor.a == 0.0) {\n // Hooray, no fill, just stroke. We can use real antialiasing.\n gl_FragColor = u_strokeColor;\n if (dist < radius - v_halfWidth) {\n gl_FragColor.a = gl_FragColor.a - (radius - v_halfWidth - dist);\n }\n } else {\n gl_FragColor = u_fillColor;\n float strokeDist = radius - v_halfWidth;\n float antialias = 2.0 * v_pixelRatio;\n if (dist > strokeDist) {\n gl_FragColor = u_strokeColor;\n } else if (dist >= strokeDist - antialias) {\n float step = smoothstep(strokeDist - antialias, strokeDist, dist);\n gl_FragColor = mix(u_fillColor, u_strokeColor, step);\n }\n }\n gl_FragColor.a = gl_FragColor.a * u_opacity;\n if (gl_FragColor.a <= 0.0) {\n discard;\n }\n}\n"),Pc=new Lc("varying vec2 v_center;\nvarying vec2 v_offset;\nvarying float v_halfWidth;\nvarying float v_pixelRatio;\n\n\nattribute vec2 a_position;\nattribute float a_instruction;\nattribute float a_radius;\n\nuniform mat4 u_projectionMatrix;\nuniform mat4 u_offsetScaleMatrix;\nuniform mat4 u_offsetRotateMatrix;\nuniform float u_lineWidth;\nuniform float u_pixelRatio;\n\nvoid main(void) {\n mat4 offsetMatrix = u_offsetScaleMatrix * u_offsetRotateMatrix;\n v_center = vec4(u_projectionMatrix * vec4(a_position, 0.0, 1.0)).xy;\n v_pixelRatio = u_pixelRatio;\n float lineWidth = u_lineWidth * u_pixelRatio;\n v_halfWidth = lineWidth / 2.0;\n if (lineWidth == 0.0) {\n lineWidth = 2.0 * u_pixelRatio;\n }\n vec2 offset;\n // Radius with anitaliasing (roughly).\n float radius = a_radius + 3.0 * u_pixelRatio;\n // Until we get gl_VertexID in WebGL, we store an instruction.\n if (a_instruction == 0.0) {\n // Offsetting the edges of the triangle by lineWidth / 2 is necessary, however\n // we should also leave some space for the antialiasing, thus we offset by lineWidth.\n offset = vec2(-1.0, 1.0);\n } else if (a_instruction == 1.0) {\n offset = vec2(-1.0, -1.0);\n } else if (a_instruction == 2.0) {\n offset = vec2(1.0, -1.0);\n } else {\n offset = vec2(1.0, 1.0);\n }\n\n gl_Position = u_projectionMatrix * vec4(a_position + offset * radius, 0.0, 1.0) +\n offsetMatrix * vec4(offset * lineWidth, 0.0, 0.0);\n v_offset = vec4(u_projectionMatrix * vec4(a_position.x + a_radius, a_position.y,\n 0.0, 1.0)).xy;\n\n if (distance(v_center, v_offset) > 20000.0) {\n gl_Position = vec4(v_center, 0.0, 1.0);\n }\n}\n\n\n"),Fc=function(t,e){this.u_projectionMatrix=t.getUniformLocation(e,"u_projectionMatrix"),this.u_offsetScaleMatrix=t.getUniformLocation(e,"u_offsetScaleMatrix"),this.u_offsetRotateMatrix=t.getUniformLocation(e,"u_offsetRotateMatrix"),this.u_lineWidth=t.getUniformLocation(e,"u_lineWidth"),this.u_pixelRatio=t.getUniformLocation(e,"u_pixelRatio"),this.u_opacity=t.getUniformLocation(e,"u_opacity"),this.u_fillColor=t.getUniformLocation(e,"u_fillColor"),this.u_strokeColor=t.getUniformLocation(e,"u_strokeColor"),this.u_size=t.getUniformLocation(e,"u_size"),this.a_position=t.getAttribLocation(e,"a_position"),this.a_instruction=t.getAttribLocation(e,"a_instruction"),this.a_radius=t.getAttribLocation(e,"a_radius")};function Mc(t,e){return t[0]=e[0],t[1]=e[1],t[4]=e[2],t[5]=e[3],t[12]=e[4],t[13]=e[5],t}var Oc=function(i){function t(t,e){i.call(this),this.tolerance=t,this.maxExtent=e,this.origin=ot(e),this.projectionMatrix_=[1,0,0,1,0,0],this.offsetRotateMatrix_=[1,0,0,1,0,0],this.offsetScaleMatrix_=[1,0,0,1,0,0],this.tmpMat4_=[1,0,0,0,0,1,0,0,0,0,1,0,0,0,0,1],this.indices=[],this.indicesBuffer=null,this.startIndices=[],this.startIndicesFeature=[],this.vertices=[],this.verticesBuffer=null,this.lineStringReplay=void 0}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.getDeleteResourcesFunction=function(t){},t.prototype.finish=function(t){},t.prototype.setUpProgram=function(t,e,i,r){},t.prototype.shutDownProgram=function(t,e){},t.prototype.drawReplay=function(t,e,i,r){},t.prototype.drawHitDetectionReplayOneByOne=function(t,e,i,r,n){},t.prototype.drawHitDetectionReplay=function(t,e,i,r,n,o){return n?this.drawHitDetectionReplayOneByOne(t,e,i,r,o):this.drawHitDetectionReplayAll(t,e,i,r)},t.prototype.drawHitDetectionReplayAll=function(t,e,i,r){t.clear(t.COLOR_BUFFER_BIT|t.DEPTH_BUFFER_BIT),this.drawReplay(t,e,i,!0);var n=r(null);return n||void 0},t.prototype.replay=function(t,e,i,r,n,o,s,a,h,l,u){var c,p,d,f,_,g,y,v,m=t.getGL();this.lineStringReplay&&(c=m.isEnabled(m.STENCIL_TEST),p=m.getParameter(m.STENCIL_FUNC),d=m.getParameter(m.STENCIL_VALUE_MASK),f=m.getParameter(m.STENCIL_REF),_=m.getParameter(m.STENCIL_WRITEMASK),g=m.getParameter(m.STENCIL_FAIL),y=m.getParameter(m.STENCIL_PASS_DEPTH_PASS),v=m.getParameter(m.STENCIL_PASS_DEPTH_FAIL),m.enable(m.STENCIL_TEST),m.clear(m.STENCIL_BUFFER_BIT),m.stencilMask(255),m.stencilFunc(m.ALWAYS,1,255),m.stencilOp(m.KEEP,m.KEEP,m.REPLACE),this.lineStringReplay.replay(t,e,i,r,n,o,s,a,h,l,u),m.stencilMask(0),m.stencilFunc(m.NOTEQUAL,1,255)),t.bindBuffer(ze,this.verticesBuffer),t.bindBuffer(34963,this.indicesBuffer);var x=this.setUpProgram(m,t,n,o),S=ge(this.projectionMatrix_);Ce(S,2/(i*n[0]),2/(i*n[1])),Se(S,-r),Ee(S,-(e[0]-this.origin[0]),-(e[1]-this.origin[1]));var C=ge(this.offsetScaleMatrix_);Ce(C,2/n[0],2/n[1]);var E,T=ge(this.offsetRotateMatrix_);return 0!==r&&Se(T,-r),m.uniformMatrix4fv(x.u_projectionMatrix,!1,Mc(this.tmpMat4_,S)),m.uniformMatrix4fv(x.u_offsetScaleMatrix,!1,Mc(this.tmpMat4_,C)),m.uniformMatrix4fv(x.u_offsetRotateMatrix,!1,Mc(this.tmpMat4_,T)),m.uniform1f(x.u_opacity,s),void 0===h?this.drawReplay(m,t,a,!1):E=this.drawHitDetectionReplay(m,t,a,h,l,u),this.shutDownProgram(m,x),this.lineStringReplay&&(c||m.disable(m.STENCIL_TEST),m.clear(m.STENCIL_BUFFER_BIT),m.stencilFunc(p,f,d),m.stencilMask(_),m.stencilOp(g,v,y)),E},t.prototype.drawElements=function(t,e,i,r){var n=e.hasOESElementIndexUint?5125:5123,o=r-i,s=i*(e.hasOESElementIndexUint?4:2);t.drawElements(4,o,n,s)},t}(Fl),Nc=[0,0,0,1],Ac=[],Gc=[0,0,0,1],kc=Number.EPSILON||2220446049250313e-31,Dc=function(t,e,i,r,n,o){var s=(i-t)*(o-e)-(n-t)*(r-e);return s<=kc&&-kc<=s?void 0:0<s},jc=35044,Uc=function(t,e){this.arr_=void 0!==t?t:[],this.usage_=void 0!==e?e:jc};Uc.prototype.getArray=function(){return this.arr_},Uc.prototype.getUsage=function(){return this.usage_};var Yc=function(i){function t(t,e){i.call(this,t,e),this.defaultLocations_=null,this.styles_=[],this.styleIndices_=[],this.radius_=0,this.state_={fillColor:null,strokeColor:null,lineDash:null,lineDashOffset:void 0,lineWidth:void 0,changed:!1}}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.drawCoordinates_=function(t,e,i,r){var n,o,s=this,a=this.vertices.length,h=this.indices.length,l=a/4;for(n=e,o=i;n<o;n+=r)s.vertices[a++]=t[n],s.vertices[a++]=t[n+1],s.vertices[a++]=0,s.vertices[a++]=s.radius_,s.vertices[a++]=t[n],s.vertices[a++]=t[n+1],s.vertices[a++]=1,s.vertices[a++]=s.radius_,s.vertices[a++]=t[n],s.vertices[a++]=t[n+1],s.vertices[a++]=2,s.vertices[a++]=s.radius_,s.vertices[a++]=t[n],s.vertices[a++]=t[n+1],s.vertices[a++]=3,s.vertices[a++]=s.radius_,s.indices[h++]=l,s.indices[h++]=l+1,s.indices[h++]=l+2,s.indices[h++]=l+2,s.indices[h++]=l+3,s.indices[h++]=l,l+=4},t.prototype.drawCircle=function(t,e){var i=t.getRadius(),r=t.getStride();if(i){this.startIndices.push(this.indices.length),this.startIndicesFeature.push(e),this.state_.changed&&(this.styleIndices_.push(this.indices.length),this.state_.changed=!1),this.radius_=i;var n=t.getFlatCoordinates();n=_t(n,0,2,r,-this.origin[0],-this.origin[1]),this.drawCoordinates_(n,0,2,r)}else if(this.state_.changed&&(this.styles_.pop(),this.styles_.length)){var o=this.styles_[this.styles_.length-1];this.state_.fillColor=o[0],this.state_.strokeColor=o[1],this.state_.lineWidth=o[2],this.state_.changed=!1}},t.prototype.finish=function(t){this.verticesBuffer=new Uc(this.vertices),this.indicesBuffer=new Uc(this.indices),this.startIndices.push(this.indices.length),0===this.styleIndices_.length&&0<this.styles_.length&&(this.styles_=[]),this.vertices=null,this.indices=null},t.prototype.getDeleteResourcesFunction=function(t){var e=this.verticesBuffer,i=this.indicesBuffer;return function(){t.deleteBuffer(e),t.deleteBuffer(i)}},t.prototype.setUpProgram=function(t,e,i,r){var n,o=e.getProgram(bc,Pc);return this.defaultLocations_?n=this.defaultLocations_:(n=new Fc(t,o),this.defaultLocations_=n),e.useProgram(o),t.enableVertexAttribArray(n.a_position),t.vertexAttribPointer(n.a_position,2,Ve,!1,16,0),t.enableVertexAttribArray(n.a_instruction),t.vertexAttribPointer(n.a_instruction,1,Ve,!1,16,8),t.enableVertexAttribArray(n.a_radius),t.vertexAttribPointer(n.a_radius,1,Ve,!1,16,12),t.uniform2fv(n.u_size,i),t.uniform1f(n.u_pixelRatio,r),n},t.prototype.shutDownProgram=function(t,e){t.disableVertexAttribArray(e.a_position),t.disableVertexAttribArray(e.a_instruction),t.disableVertexAttribArray(e.a_radius)},t.prototype.drawReplay=function(t,e,i,r){var n,o,s,a;if(Tt(i))for(s=this.startIndices[this.startIndices.length-1],n=this.styleIndices_.length-1;0<=n;--n)o=this.styleIndices_[n],a=this.styles_[n],this.setFillStyle_(t,a[0]),this.setStrokeStyle_(t,a[1],a[2]),this.drawElements(t,e,o,s),s=o;else this.drawReplaySkipping_(t,e,i)},t.prototype.drawHitDetectionReplayOneByOne=function(t,e,i,r,n){var o,s,a,h,l,u,c;for(c=this.startIndices.length-2,a=this.startIndices[c+1],o=this.styleIndices_.length-1;0<=o;--o)for(h=this.styles_[o],this.setFillStyle_(t,h[0]),this.setStrokeStyle_(t,h[1],h[2]),l=this.styleIndices_[o];0<=c&&this.startIndices[c]>=l;){if(s=this.startIndices[c],void 0===i[Et(u=this.startIndicesFeature[c]).toString()]&&u.getGeometry()&&(void 0===n||wt(n,u.getGeometry().getExtent()))){t.clear(t.COLOR_BUFFER_BIT|t.DEPTH_BUFFER_BIT),this.drawElements(t,e,s,a);var p=r(u);if(p)return p}c--,a=s}},t.prototype.drawReplaySkipping_=function(t,e,i){var r,n,o,s,a,h,l;for(h=this.startIndices.length-2,o=n=this.startIndices[h+1],r=this.styleIndices_.length-1;0<=r;--r){for(s=this.styles_[r],this.setFillStyle_(t,s[0]),this.setStrokeStyle_(t,s[1],s[2]),a=this.styleIndices_[r];0<=h&&this.startIndices[h]>=a;)l=this.startIndices[h],i[Et(this.startIndicesFeature[h]).toString()]&&(n!==o&&this.drawElements(t,e,n,o),o=l),h--,n=l;n!==o&&this.drawElements(t,e,n,o),n=o=a}},t.prototype.setFillStyle_=function(t,e){t.uniform4fv(this.defaultLocations_.u_fillColor,e)},t.prototype.setStrokeStyle_=function(t,e,i){t.uniform4fv(this.defaultLocations_.u_strokeColor,e),t.uniform1f(this.defaultLocations_.u_lineWidth,i)},t.prototype.setFillStrokeStyle=function(t,e){var i,r;if(e){var n=e.getLineDash();this.state_.lineDash=n||Ac;var o=e.getLineDashOffset();this.state_.lineDashOffset=o||0,i=(i=e.getColor())instanceof CanvasGradient||i instanceof CanvasPattern?Gc:Ne(i).map(function(t,e){return 3!=e?t/255:t})||Gc,r=void 0!==(r=e.getWidth())?r:1}else i=[0,0,0,0],r=0;var s=t?t.getColor():[0,0,0,0];s=s instanceof CanvasGradient||s instanceof CanvasPattern?Nc:Ne(s).map(function(t,e){return 3!=e?t/255:t})||Nc,this.state_.strokeColor&&fr(this.state_.strokeColor,i)&&this.state_.fillColor&&fr(this.state_.fillColor,s)&&this.state_.lineWidth===r||(this.state_.changed=!0,this.state_.fillColor=s,this.state_.strokeColor=i,this.state_.lineWidth=r,this.styles_.push([s,i,r]))},t}(Oc),Bc=new Ic("precision mediump float;\nvarying vec2 v_texCoord;\nvarying float v_opacity;\n\nuniform float u_opacity;\nuniform sampler2D u_image;\n\nvoid main(void) {\n vec4 texColor = texture2D(u_image, v_texCoord);\n gl_FragColor.rgb = texColor.rgb;\n float alpha = texColor.a * v_opacity * u_opacity;\n if (alpha == 0.0) {\n discard;\n }\n gl_FragColor.a = alpha;\n}\n"),Xc=new Lc("varying vec2 v_texCoord;\nvarying float v_opacity;\n\nattribute vec2 a_position;\nattribute vec2 a_texCoord;\nattribute vec2 a_offsets;\nattribute float a_opacity;\nattribute float a_rotateWithView;\n\nuniform mat4 u_projectionMatrix;\nuniform mat4 u_offsetScaleMatrix;\nuniform mat4 u_offsetRotateMatrix;\n\nvoid main(void) {\n mat4 offsetMatrix = u_offsetScaleMatrix;\n if (a_rotateWithView == 1.0) {\n offsetMatrix = u_offsetScaleMatrix * u_offsetRotateMatrix;\n }\n vec4 offsets = offsetMatrix * vec4(a_offsets, 0.0, 0.0);\n gl_Position = u_projectionMatrix * vec4(a_position, 0.0, 1.0) + offsets;\n v_texCoord = a_texCoord;\n v_opacity = a_opacity;\n}\n\n\n"),zc=function(t,e){this.u_projectionMatrix=t.getUniformLocation(e,"u_projectionMatrix"),this.u_offsetScaleMatrix=t.getUniformLocation(e,"u_offsetScaleMatrix"),this.u_offsetRotateMatrix=t.getUniformLocation(e,"u_offsetRotateMatrix"),this.u_opacity=t.getUniformLocation(e,"u_opacity"),this.u_image=t.getUniformLocation(e,"u_image"),this.a_position=t.getAttribLocation(e,"a_position"),this.a_texCoord=t.getAttribLocation(e,"a_texCoord"),this.a_offsets=t.getAttribLocation(e,"a_offsets"),this.a_opacity=t.getAttribLocation(e,"a_opacity"),this.a_rotateWithView=t.getAttribLocation(e,"a_rotateWithView")},Vc="webglcontextlost",Wc="webglcontextrestored",Kc=function(i){function t(t,e){i.call(this),this.canvas_=t,this.gl_=e,this.bufferCache_={},this.shaderCache_={},this.programCache_={},this.currentProgram_=null,this.hitDetectionFramebuffer_=null,this.hitDetectionTexture_=null,this.hitDetectionRenderbuffer_=null,this.hasOESElementIndexUint=lr(Xe,"OES_element_index_uint"),this.hasOESElementIndexUint&&e.getExtension("OES_element_index_uint"),E(this.canvas_,Vc,this.handleWebGLContextLost,this),E(this.canvas_,Wc,this.handleWebGLContextRestored,this)}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.bindBuffer=function(t,e){var i=this.getGL(),r=e.getArray(),n=String(Et(e));if(n in this.bufferCache_){var o=this.bufferCache_[n];i.bindBuffer(t,o.buffer)}else{var s,a=i.createBuffer();i.bindBuffer(t,a),t==ze?s=new Float32Array(r):34963==t&&(s=this.hasOESElementIndexUint?new Uint32Array(r):new Uint16Array(r)),i.bufferData(t,s,e.getUsage()),this.bufferCache_[n]={buf:e,buffer:a}}},t.prototype.deleteBuffer=function(t){var e=this.getGL(),i=String(Et(t)),r=this.bufferCache_[i];e.isContextLost()||e.deleteBuffer(r.buffer),delete this.bufferCache_[i]},t.prototype.disposeInternal=function(){f(this.canvas_);var t=this.getGL();if(!t.isContextLost()){for(var e in this.bufferCache_)t.deleteBuffer(this.bufferCache_[e].buffer);for(var i in this.programCache_)t.deleteProgram(this.programCache_[i]);for(var r in this.shaderCache_)t.deleteShader(this.shaderCache_[r]);t.deleteFramebuffer(this.hitDetectionFramebuffer_),t.deleteRenderbuffer(this.hitDetectionRenderbuffer_),t.deleteTexture(this.hitDetectionTexture_)}},t.prototype.getCanvas=function(){return this.canvas_},t.prototype.getGL=function(){return this.gl_},t.prototype.getHitDetectionFramebuffer=function(){return this.hitDetectionFramebuffer_||this.initHitDetectionFramebuffer_(),this.hitDetectionFramebuffer_},t.prototype.getShader=function(t){var e=String(Et(t));if(e in this.shaderCache_)return this.shaderCache_[e];var i=this.getGL(),r=i.createShader(t.getType());return i.shaderSource(r,t.getSource()),i.compileShader(r),this.shaderCache_[e]=r},t.prototype.getProgram=function(t,e){var i=Et(t)+"/"+Et(e);if(i in this.programCache_)return this.programCache_[i];var r=this.getGL(),n=r.createProgram();return r.attachShader(n,this.getShader(t)),r.attachShader(n,this.getShader(e)),r.linkProgram(n),this.programCache_[i]=n},t.prototype.handleWebGLContextLost=function(){_(this.bufferCache_),_(this.shaderCache_),_(this.programCache_),this.currentProgram_=null,this.hitDetectionFramebuffer_=null,this.hitDetectionTexture_=null,this.hitDetectionRenderbuffer_=null},t.prototype.handleWebGLContextRestored=function(){},t.prototype.initHitDetectionFramebuffer_=function(){var t=this.gl_,e=t.createFramebuffer();t.bindFramebuffer(t.FRAMEBUFFER,e);var i=Zc(t,1,1),r=t.createRenderbuffer();t.bindRenderbuffer(t.RENDERBUFFER,r),t.renderbufferStorage(t.RENDERBUFFER,t.DEPTH_COMPONENT16,1,1),t.framebufferTexture2D(t.FRAMEBUFFER,t.COLOR_ATTACHMENT0,t.TEXTURE_2D,i,0),t.framebufferRenderbuffer(t.FRAMEBUFFER,t.DEPTH_ATTACHMENT,t.RENDERBUFFER,r),t.bindTexture(t.TEXTURE_2D,null),t.bindRenderbuffer(t.RENDERBUFFER,null),t.bindFramebuffer(t.FRAMEBUFFER,null),this.hitDetectionFramebuffer_=e,this.hitDetectionTexture_=i,this.hitDetectionRenderbuffer_=r},t.prototype.useProgram=function(t){return t!=this.currentProgram_&&(this.getGL().useProgram(t),this.currentProgram_=t,!0)},t}(t);function Hc(t,e,i){var r=t.createTexture();return t.bindTexture(t.TEXTURE_2D,r),t.texParameteri(t.TEXTURE_2D,t.TEXTURE_MAG_FILTER,t.LINEAR),t.texParameteri(t.TEXTURE_2D,t.TEXTURE_MIN_FILTER,t.LINEAR),void 0!==e&&t.texParameteri(He,We,e),void 0!==i&&t.texParameteri(He,Ke,i),r}function Zc(t,e,i,r,n){var o=Hc(t,r,n);return t.texImage2D(t.TEXTURE_2D,0,t.RGBA,e,i,0,t.RGBA,t.UNSIGNED_BYTE,null),o}function qc(t,e,i,r){var n=Hc(t,i,r);return t.texImage2D(t.TEXTURE_2D,0,t.RGBA,t.RGBA,t.UNSIGNED_BYTE,e),n}var Jc=function(i){function t(t,e){i.call(this,t,e),this.anchorX=void 0,this.anchorY=void 0,this.groupIndices=[],this.hitDetectionGroupIndices=[],this.height=void 0,this.imageHeight=void 0,this.imageWidth=void 0,this.defaultLocations=null,this.opacity=void 0,this.originX=void 0,this.originY=void 0,this.rotateWithView=void 0,this.rotation=void 0,this.scale=void 0,this.width=void 0}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.getDeleteResourcesFunction=function(i){var r=this.verticesBuffer,n=this.indicesBuffer,o=this.getTextures(!0),s=i.getGL();return function(){var t,e;if(!s.isContextLost())for(t=0,e=o.length;t<e;++t)s.deleteTexture(o[t]);i.deleteBuffer(r),i.deleteBuffer(n)}},t.prototype.drawCoordinates=function(t,e,i,r){var n,o,s,a,h,l,u=this,c=this.anchorX,p=this.anchorY,d=this.height,f=this.imageHeight,_=this.imageWidth,g=this.opacity,y=this.originX,v=this.originY,m=this.rotateWithView?1:0,x=-this.rotation,S=this.scale,C=this.width,E=Math.cos(x),T=Math.sin(x),w=this.indices.length,R=this.vertices.length;for(n=e;n<i;n+=r)h=t[n]-u.origin[0],l=t[n+1]-u.origin[1],o=R/8,s=-S*c,a=-S*(d-p),u.vertices[R++]=h,u.vertices[R++]=l,u.vertices[R++]=s*E-a*T,u.vertices[R++]=s*T+a*E,u.vertices[R++]=y/_,u.vertices[R++]=(v+d)/f,u.vertices[R++]=g,u.vertices[R++]=m,s=S*(C-c),a=-S*(d-p),u.vertices[R++]=h,u.vertices[R++]=l,u.vertices[R++]=s*E-a*T,u.vertices[R++]=s*T+a*E,u.vertices[R++]=(y+C)/_,u.vertices[R++]=(v+d)/f,u.vertices[R++]=g,u.vertices[R++]=m,s=S*(C-c),a=S*p,u.vertices[R++]=h,u.vertices[R++]=l,u.vertices[R++]=s*E-a*T,u.vertices[R++]=s*T+a*E,u.vertices[R++]=(y+C)/_,u.vertices[R++]=v/f,u.vertices[R++]=g,u.vertices[R++]=m,s=-S*c,a=S*p,u.vertices[R++]=h,u.vertices[R++]=l,u.vertices[R++]=s*E-a*T,u.vertices[R++]=s*T+a*E,u.vertices[R++]=y/_,u.vertices[R++]=v/f,u.vertices[R++]=g,u.vertices[R++]=m,u.indices[w++]=o,u.indices[w++]=o+1,u.indices[w++]=o+2,u.indices[w++]=o,u.indices[w++]=o+2,u.indices[w++]=o+3;return R},t.prototype.createTextures=function(t,e,i,r){var n,o,s,a,h=e.length;for(a=0;a<h;++a)(s=Et(o=e[a]).toString())in i?n=i[s]:(n=qc(r,o,Ze,Ze),i[s]=n),t[a]=n},t.prototype.setUpProgram=function(t,e,i,r){var n,o=e.getProgram(Bc,Xc);return this.defaultLocations?n=this.defaultLocations:(n=new zc(t,o),this.defaultLocations=n),e.useProgram(o),t.enableVertexAttribArray(n.a_position),t.vertexAttribPointer(n.a_position,2,Ve,!1,32,0),t.enableVertexAttribArray(n.a_offsets),t.vertexAttribPointer(n.a_offsets,2,Ve,!1,32,8),t.enableVertexAttribArray(n.a_texCoord),t.vertexAttribPointer(n.a_texCoord,2,Ve,!1,32,16),t.enableVertexAttribArray(n.a_opacity),t.vertexAttribPointer(n.a_opacity,1,Ve,!1,32,24),t.enableVertexAttribArray(n.a_rotateWithView),t.vertexAttribPointer(n.a_rotateWithView,1,Ve,!1,32,28),n},t.prototype.shutDownProgram=function(t,e){t.disableVertexAttribArray(e.a_position),t.disableVertexAttribArray(e.a_offsets),t.disableVertexAttribArray(e.a_texCoord),t.disableVertexAttribArray(e.a_opacity),t.disableVertexAttribArray(e.a_rotateWithView)},t.prototype.drawReplay=function(t,e,i,r){var n,o,s,a=r?this.getHitDetectionTextures():this.getTextures(),h=r?this.hitDetectionGroupIndices:this.groupIndices;if(Tt(i))for(n=0,o=a.length,s=0;n<o;++n){t.bindTexture(He,a[n]);var l=h[n];this.drawElements(t,e,s,l),s=l}else this.drawReplaySkipping(t,e,i,a,h)},t.prototype.drawReplaySkipping=function(t,e,i,r,n){var o,s,a=0;for(o=0,s=r.length;o<s;++o){t.bindTexture(He,r[o]);for(var h=0<o?n[o-1]:0,l=n[o],u=h,c=h;a<this.startIndices.length&&this.startIndices[a]<=l;){void 0!==i[Et(this.startIndicesFeature[a]).toString()]?(u!==c&&this.drawElements(t,e,u,c),c=u=a===this.startIndices.length-1?l:this.startIndices[a+1]):c=a===this.startIndices.length-1?l:this.startIndices[a+1],a++}u!==c&&this.drawElements(t,e,u,c)}},t.prototype.drawHitDetectionReplayOneByOne=function(t,e,i,r,n){var o,s,a,h,l,u=this.startIndices.length-1,c=this.getHitDetectionTextures();for(o=c.length-1;0<=o;--o)for(t.bindTexture(He,c[o]),s=0<o?this.hitDetectionGroupIndices[o-1]:0,h=this.hitDetectionGroupIndices[o];0<=u&&this.startIndices[u]>=s;){if(a=this.startIndices[u],void 0===i[Et(l=this.startIndicesFeature[u]).toString()]&&l.getGeometry()&&(void 0===n||wt(n,l.getGeometry().getExtent()))){t.clear(t.COLOR_BUFFER_BIT|t.DEPTH_BUFFER_BIT),this.drawElements(t,e,a,h);var p=r(l);if(p)return p}h=a,u--}},t.prototype.finish=function(t){this.anchorX=void 0,this.anchorY=void 0,this.height=void 0,this.imageHeight=void 0,this.imageWidth=void 0,this.indices=null,this.opacity=void 0,this.originX=void 0,this.originY=void 0,this.rotateWithView=void 0,this.rotation=void 0,this.scale=void 0,this.vertices=null,this.width=void 0},t.prototype.getTextures=function(t){},t.prototype.getHitDetectionTextures=function(){},t}(Oc),Qc=function(n){function t(t,e){n.call(this,t,e),this.images_=[],this.hitDetectionImages_=[],this.textures_=[],this.hitDetectionTextures_=[]}return n&&(t.__proto__=n),((t.prototype=Object.create(n&&n.prototype)).constructor=t).prototype.drawMultiPoint=function(t,e){this.startIndices.push(this.indices.length),this.startIndicesFeature.push(e);var i=t.getFlatCoordinates(),r=t.getStride();this.drawCoordinates(i,0,i.length,r)},t.prototype.drawPoint=function(t,e){this.startIndices.push(this.indices.length),this.startIndicesFeature.push(e);var i=t.getFlatCoordinates(),r=t.getStride();this.drawCoordinates(i,0,i.length,r)},t.prototype.finish=function(t){var e=t.getGL();this.groupIndices.push(this.indices.length),this.hitDetectionGroupIndices.push(this.indices.length),this.verticesBuffer=new Uc(this.vertices);var i=this.indices;this.indicesBuffer=new Uc(i);var r={};this.createTextures(this.textures_,this.images_,r,e),this.createTextures(this.hitDetectionTextures_,this.hitDetectionImages_,r,e),this.images_=null,this.hitDetectionImages_=null,n.prototype.finish.call(this,t)},t.prototype.setImageStyle=function(t){var e=t.getAnchor(),i=t.getImage(1),r=t.getImageSize(),n=t.getHitDetectionImage(1),o=t.getOpacity(),s=t.getOrigin(),a=t.getRotateWithView(),h=t.getRotation(),l=t.getSize(),u=t.getScale();0===this.images_.length?this.images_.push(i):Et(this.images_[this.images_.length-1])!=Et(i)&&(this.groupIndices.push(this.indices.length),this.images_.push(i)),0===this.hitDetectionImages_.length?this.hitDetectionImages_.push(n):Et(this.hitDetectionImages_[this.hitDetectionImages_.length-1])!=Et(n)&&(this.hitDetectionGroupIndices.push(this.indices.length),this.hitDetectionImages_.push(n)),this.anchorX=e[0],this.anchorY=e[1],this.height=l[1],this.imageHeight=r[1],this.imageWidth=r[0],this.opacity=o,this.originX=s[0],this.originY=s[1],this.rotation=h,this.rotateWithView=a,this.scale=u,this.width=l[0]},t.prototype.getTextures=function(t){return t?this.textures_.concat(this.hitDetectionTextures_):this.textures_},t.prototype.getHitDetectionTextures=function(){return this.hitDetectionTextures_},t}(Jc);function $c(t,e,i,r){var n=i-r;return t[e]===t[n]&&t[e+1]===t[n+1]&&3<(i-e)/r&&!!xr(t,e,i,r)}var tp=new Ic("precision mediump float;\nvarying float v_round;\nvarying vec2 v_roundVertex;\nvarying float v_halfWidth;\n\n\n\nuniform float u_opacity;\nuniform vec4 u_color;\nuniform vec2 u_size;\nuniform float u_pixelRatio;\n\nvoid main(void) {\n if (v_round > 0.0) {\n vec2 windowCoords = vec2((v_roundVertex.x + 1.0) / 2.0 * u_size.x * u_pixelRatio,\n (v_roundVertex.y + 1.0) / 2.0 * u_size.y * u_pixelRatio);\n if (length(windowCoords - gl_FragCoord.xy) > v_halfWidth * u_pixelRatio) {\n discard;\n }\n }\n gl_FragColor = u_color;\n float alpha = u_color.a * u_opacity;\n if (alpha == 0.0) {\n discard;\n }\n gl_FragColor.a = alpha;\n}\n"),ep=new Lc("varying float v_round;\nvarying vec2 v_roundVertex;\nvarying float v_halfWidth;\n\n\nattribute vec2 a_lastPos;\nattribute vec2 a_position;\nattribute vec2 a_nextPos;\nattribute float a_direction;\n\nuniform mat4 u_projectionMatrix;\nuniform mat4 u_offsetScaleMatrix;\nuniform mat4 u_offsetRotateMatrix;\nuniform float u_lineWidth;\nuniform float u_miterLimit;\n\nbool nearlyEquals(in float value, in float ref) {\n float epsilon = 0.000000000001;\n return value >= ref - epsilon && value <= ref + epsilon;\n}\n\nvoid alongNormal(out vec2 offset, in vec2 nextP, in float turnDir, in float direction) {\n vec2 dirVect = nextP - a_position;\n vec2 normal = normalize(vec2(-turnDir * dirVect.y, turnDir * dirVect.x));\n offset = u_lineWidth / 2.0 * normal * direction;\n}\n\nvoid miterUp(out vec2 offset, out float round, in bool isRound, in float direction) {\n float halfWidth = u_lineWidth / 2.0;\n vec2 tangent = normalize(normalize(a_nextPos - a_position) + normalize(a_position - a_lastPos));\n vec2 normal = vec2(-tangent.y, tangent.x);\n vec2 dirVect = a_nextPos - a_position;\n vec2 tmpNormal = normalize(vec2(-dirVect.y, dirVect.x));\n float miterLength = abs(halfWidth / dot(normal, tmpNormal));\n offset = normal * direction * miterLength;\n round = 0.0;\n if (isRound) {\n round = 1.0;\n } else if (miterLength > u_miterLimit + u_lineWidth) {\n offset = halfWidth * tmpNormal * direction;\n }\n}\n\nbool miterDown(out vec2 offset, in vec4 projPos, in mat4 offsetMatrix, in float direction) {\n bool degenerate = false;\n vec2 tangent = normalize(normalize(a_nextPos - a_position) + normalize(a_position - a_lastPos));\n vec2 normal = vec2(-tangent.y, tangent.x);\n vec2 dirVect = a_lastPos - a_position;\n vec2 tmpNormal = normalize(vec2(-dirVect.y, dirVect.x));\n vec2 longOffset, shortOffset, longVertex;\n vec4 shortProjVertex;\n float halfWidth = u_lineWidth / 2.0;\n if (length(a_nextPos - a_position) > length(a_lastPos - a_position)) {\n longOffset = tmpNormal * direction * halfWidth;\n shortOffset = normalize(vec2(dirVect.y, -dirVect.x)) * direction * halfWidth;\n longVertex = a_nextPos;\n shortProjVertex = u_projectionMatrix * vec4(a_lastPos, 0.0, 1.0);\n } else {\n shortOffset = tmpNormal * direction * halfWidth;\n longOffset = normalize(vec2(dirVect.y, -dirVect.x)) * direction * halfWidth;\n longVertex = a_lastPos;\n shortProjVertex = u_projectionMatrix * vec4(a_nextPos, 0.0, 1.0);\n }\n //Intersection algorithm based on theory by Paul Bourke (http://paulbourke.net/geometry/pointlineplane/).\n vec4 p1 = u_projectionMatrix * vec4(longVertex, 0.0, 1.0) + offsetMatrix * vec4(longOffset, 0.0, 0.0);\n vec4 p2 = projPos + offsetMatrix * vec4(longOffset, 0.0, 0.0);\n vec4 p3 = shortProjVertex + offsetMatrix * vec4(-shortOffset, 0.0, 0.0);\n vec4 p4 = shortProjVertex + offsetMatrix * vec4(shortOffset, 0.0, 0.0);\n float denom = (p4.y - p3.y) * (p2.x - p1.x) - (p4.x - p3.x) * (p2.y - p1.y);\n float firstU = ((p4.x - p3.x) * (p1.y - p3.y) - (p4.y - p3.y) * (p1.x - p3.x)) / denom;\n float secondU = ((p2.x - p1.x) * (p1.y - p3.y) - (p2.y - p1.y) * (p1.x - p3.x)) / denom;\n float epsilon = 0.000000000001;\n if (firstU > epsilon && firstU < 1.0 - epsilon && secondU > epsilon && secondU < 1.0 - epsilon) {\n shortProjVertex.x = p1.x + firstU * (p2.x - p1.x);\n shortProjVertex.y = p1.y + firstU * (p2.y - p1.y);\n offset = shortProjVertex.xy;\n degenerate = true;\n } else {\n float miterLength = abs(halfWidth / dot(normal, tmpNormal));\n offset = normal * direction * miterLength;\n }\n return degenerate;\n}\n\nvoid squareCap(out vec2 offset, out float round, in bool isRound, in vec2 nextP,\n in float turnDir, in float direction) {\n round = 0.0;\n vec2 dirVect = a_position - nextP;\n vec2 firstNormal = normalize(dirVect);\n vec2 secondNormal = vec2(turnDir * firstNormal.y * direction, -turnDir * firstNormal.x * direction);\n vec2 hypotenuse = normalize(firstNormal - secondNormal);\n vec2 normal = vec2(turnDir * hypotenuse.y * direction, -turnDir * hypotenuse.x * direction);\n float length = sqrt(v_halfWidth * v_halfWidth * 2.0);\n offset = normal * length;\n if (isRound) {\n round = 1.0;\n }\n}\n\nvoid main(void) {\n bool degenerate = false;\n float direction = float(sign(a_direction));\n mat4 offsetMatrix = u_offsetScaleMatrix * u_offsetRotateMatrix;\n vec2 offset;\n vec4 projPos = u_projectionMatrix * vec4(a_position, 0.0, 1.0);\n bool round = nearlyEquals(mod(a_direction, 2.0), 0.0);\n\n v_round = 0.0;\n v_halfWidth = u_lineWidth / 2.0;\n v_roundVertex = projPos.xy;\n\n if (nearlyEquals(mod(a_direction, 3.0), 0.0) || nearlyEquals(mod(a_direction, 17.0), 0.0)) {\n alongNormal(offset, a_nextPos, 1.0, direction);\n } else if (nearlyEquals(mod(a_direction, 5.0), 0.0) || nearlyEquals(mod(a_direction, 13.0), 0.0)) {\n alongNormal(offset, a_lastPos, -1.0, direction);\n } else if (nearlyEquals(mod(a_direction, 23.0), 0.0)) {\n miterUp(offset, v_round, round, direction);\n } else if (nearlyEquals(mod(a_direction, 19.0), 0.0)) {\n degenerate = miterDown(offset, projPos, offsetMatrix, direction);\n } else if (nearlyEquals(mod(a_direction, 7.0), 0.0)) {\n squareCap(offset, v_round, round, a_nextPos, 1.0, direction);\n } else if (nearlyEquals(mod(a_direction, 11.0), 0.0)) {\n squareCap(offset, v_round, round, a_lastPos, -1.0, direction);\n }\n if (!degenerate) {\n vec4 offsets = offsetMatrix * vec4(offset, 0.0, 0.0);\n gl_Position = projPos + offsets;\n } else {\n gl_Position = vec4(offset, 0.0, 1.0);\n }\n}\n\n\n"),ip=function(t,e){this.u_projectionMatrix=t.getUniformLocation(e,"u_projectionMatrix"),this.u_offsetScaleMatrix=t.getUniformLocation(e,"u_offsetScaleMatrix"),this.u_offsetRotateMatrix=t.getUniformLocation(e,"u_offsetRotateMatrix"),this.u_lineWidth=t.getUniformLocation(e,"u_lineWidth"),this.u_miterLimit=t.getUniformLocation(e,"u_miterLimit"),this.u_opacity=t.getUniformLocation(e,"u_opacity"),this.u_color=t.getUniformLocation(e,"u_color"),this.u_size=t.getUniformLocation(e,"u_size"),this.u_pixelRatio=t.getUniformLocation(e,"u_pixelRatio"),this.a_lastPos=t.getAttribLocation(e,"a_lastPos"),this.a_position=t.getAttribLocation(e,"a_position"),this.a_nextPos=t.getAttribLocation(e,"a_nextPos"),this.a_direction=t.getAttribLocation(e,"a_direction")},rp=3,np=5,op=7,sp=11,ap=13,hp=17,lp=19,up=23,cp=function(i){function t(t,e){i.call(this,t,e),this.defaultLocations_=null,this.styles_=[],this.styleIndices_=[],this.state_={strokeColor:null,lineCap:void 0,lineDash:null,lineDashOffset:void 0,lineJoin:void 0,lineWidth:void 0,miterLimit:void 0,changed:!1}}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.drawCoordinates_=function(t,e,i,r){var n,o,s,a,h,l,u,c,p=this,d=this.vertices.length,f=this.indices.length,_="bevel"===this.state_.lineJoin?0:"miter"===this.state_.lineJoin?1:2,g="butt"===this.state_.lineCap?0:"square"===this.state_.lineCap?1:2,y=$c(t,e,i,r),v=f,m=1;for(n=e,o=i;n<o;n+=r){if(h=d/7,l=u,u=c||[t[n],t[n+1]],n===e){if(c=[t[n+r],t[n+r+1]],i-e==2*r&&fr(u,c))break;if(!y){g&&(d=p.addVertices_([0,0],u,c,m*op*g,d),d=p.addVertices_([0,0],u,c,-m*op*g,d),p.indices[f++]=h+2,p.indices[f++]=h,p.indices[f++]=h+1,p.indices[f++]=h+1,p.indices[f++]=h+3,p.indices[f++]=h+2),d=p.addVertices_([0,0],u,c,m*rp*(g||1),d),v=(d=p.addVertices_([0,0],u,c,-m*rp*(g||1),d))/7-1;continue}l=[t[i-2*r],t[i-2*r+1]],s=c}else{if(n===i-r){if(y){c=s;break}l=l||[0,0],d=p.addVertices_(l,u,[0,0],m*np*(g||1),d),d=p.addVertices_(l,u,[0,0],-m*np*(g||1),d),p.indices[f++]=h,p.indices[f++]=v-1,p.indices[f++]=v,p.indices[f++]=v,p.indices[f++]=h+1,p.indices[f++]=h,g&&(d=p.addVertices_(l,u,[0,0],m*sp*g,d),d=p.addVertices_(l,u,[0,0],-m*sp*g,d),p.indices[f++]=h+2,p.indices[f++]=h,p.indices[f++]=h+1,p.indices[f++]=h+1,p.indices[f++]=h+3,p.indices[f++]=h+2);break}c=[t[n+r],t[n+r+1]]}a=Dc(l[0],l[1],u[0],u[1],c[0],c[1])?-1:1,d=p.addVertices_(l,u,c,a*ap*(_||1),d),d=p.addVertices_(l,u,c,a*hp*(_||1),d),d=p.addVertices_(l,u,c,-a*lp*(_||1),d),e<n&&(p.indices[f++]=h,p.indices[f++]=v-1,p.indices[f++]=v,p.indices[f++]=h+2,p.indices[f++]=h,p.indices[f++]=0<m*a?v:v-1),p.indices[f++]=h,p.indices[f++]=h+2,p.indices[f++]=h+1,v=h+2,m=a,_&&(d=p.addVertices_(l,u,c,a*up*_,d),p.indices[f++]=h+1,p.indices[f++]=h+3,p.indices[f++]=h)}y&&(h=h||d/7,a=Hr([l[0],l[1],u[0],u[1],c[0],c[1]],0,6,2)?1:-1,d=this.addVertices_(l,u,c,a*ap*(_||1),d),d=this.addVertices_(l,u,c,-a*lp*(_||1),d),this.indices[f++]=h,this.indices[f++]=v-1,this.indices[f++]=v,this.indices[f++]=h+1,this.indices[f++]=h,this.indices[f++]=0<m*a?v:v-1)},t.prototype.addVertices_=function(t,e,i,r,n){return this.vertices[n++]=t[0],this.vertices[n++]=t[1],this.vertices[n++]=e[0],this.vertices[n++]=e[1],this.vertices[n++]=i[0],this.vertices[n++]=i[1],this.vertices[n++]=r,n},t.prototype.isValid_=function(t,e,i,r){var n=i-e;return!(n<2*r)&&(n!==2*r||!fr([t[e],t[e+1]],[t[e+r],t[e+r+1]]))},t.prototype.drawLineString=function(t,e){var i=t.getFlatCoordinates(),r=t.getStride();this.isValid_(i,0,i.length,r)&&(i=_t(i,0,i.length,r,-this.origin[0],-this.origin[1]),this.state_.changed&&(this.styleIndices_.push(this.indices.length),this.state_.changed=!1),this.startIndices.push(this.indices.length),this.startIndicesFeature.push(e),this.drawCoordinates_(i,0,i.length,r))},t.prototype.drawMultiLineString=function(t,e){var i=this.indices.length,r=t.getEnds();r.unshift(0);var n,o,s=t.getFlatCoordinates(),a=t.getStride();if(1<r.length)for(n=1,o=r.length;n<o;++n)if(this.isValid_(s,r[n-1],r[n],a)){var h=_t(s,r[n-1],r[n],a,-this.origin[0],-this.origin[1]);this.drawCoordinates_(h,0,h.length,a)}this.indices.length>i&&(this.startIndices.push(i),this.startIndicesFeature.push(e),this.state_.changed&&(this.styleIndices_.push(i),this.state_.changed=!1))},t.prototype.drawPolygonCoordinates=function(t,e,i){var r,n;if($c(t,0,t.length,i)||(t.push(t[0]),t.push(t[1])),this.drawCoordinates_(t,0,t.length,i),e.length)for(r=0,n=e.length;r<n;++r)$c(e[r],0,e[r].length,i)||(e[r].push(e[r][0]),e[r].push(e[r][1])),this.drawCoordinates_(e[r],0,e[r].length,i)},t.prototype.setPolygonStyle=function(t,e){var i=void 0===e?this.indices.length:e;this.startIndices.push(i),this.startIndicesFeature.push(t),this.state_.changed&&(this.styleIndices_.push(i),this.state_.changed=!1)},t.prototype.getCurrentIndex=function(){return this.indices.length},t.prototype.finish=function(t){this.verticesBuffer=new Uc(this.vertices),this.indicesBuffer=new Uc(this.indices),this.startIndices.push(this.indices.length),0===this.styleIndices_.length&&0<this.styles_.length&&(this.styles_=[]),this.vertices=null,this.indices=null},t.prototype.getDeleteResourcesFunction=function(t){var e=this.verticesBuffer,i=this.indicesBuffer;return function(){t.deleteBuffer(e),t.deleteBuffer(i)}},t.prototype.setUpProgram=function(t,e,i,r){var n,o=e.getProgram(tp,ep);return this.defaultLocations_?n=this.defaultLocations_:(n=new ip(t,o),this.defaultLocations_=n),e.useProgram(o),t.enableVertexAttribArray(n.a_lastPos),t.vertexAttribPointer(n.a_lastPos,2,Ve,!1,28,0),t.enableVertexAttribArray(n.a_position),t.vertexAttribPointer(n.a_position,2,Ve,!1,28,8),t.enableVertexAttribArray(n.a_nextPos),t.vertexAttribPointer(n.a_nextPos,2,Ve,!1,28,16),t.enableVertexAttribArray(n.a_direction),t.vertexAttribPointer(n.a_direction,1,Ve,!1,28,24),t.uniform2fv(n.u_size,i),t.uniform1f(n.u_pixelRatio,r),n},t.prototype.shutDownProgram=function(t,e){t.disableVertexAttribArray(e.a_lastPos),t.disableVertexAttribArray(e.a_position),t.disableVertexAttribArray(e.a_nextPos),t.disableVertexAttribArray(e.a_direction)},t.prototype.drawReplay=function(t,e,i,r){var n,o,s,a,h=t.getParameter(t.DEPTH_FUNC),l=t.getParameter(t.DEPTH_WRITEMASK);if(r||(t.enable(t.DEPTH_TEST),t.depthMask(!0),t.depthFunc(t.NOTEQUAL)),Tt(i))for(s=this.startIndices[this.startIndices.length-1],n=this.styleIndices_.length-1;0<=n;--n)o=this.styleIndices_[n],a=this.styles_[n],this.setStrokeStyle_(t,a[0],a[1],a[2]),this.drawElements(t,e,o,s),t.clear(t.DEPTH_BUFFER_BIT),s=o;else this.drawReplaySkipping_(t,e,i);r||(t.disable(t.DEPTH_TEST),t.clear(t.DEPTH_BUFFER_BIT),t.depthMask(l),t.depthFunc(h))},t.prototype.drawReplaySkipping_=function(t,e,i){var r,n,o,s,a,h,l;for(h=this.startIndices.length-2,o=n=this.startIndices[h+1],r=this.styleIndices_.length-1;0<=r;--r){for(s=this.styles_[r],this.setStrokeStyle_(t,s[0],s[1],s[2]),a=this.styleIndices_[r];0<=h&&this.startIndices[h]>=a;)l=this.startIndices[h],i[Et(this.startIndicesFeature[h]).toString()]&&(n!==o&&(this.drawElements(t,e,n,o),t.clear(t.DEPTH_BUFFER_BIT)),o=l),h--,n=l;n!==o&&(this.drawElements(t,e,n,o),t.clear(t.DEPTH_BUFFER_BIT)),n=o=a}},t.prototype.drawHitDetectionReplayOneByOne=function(t,e,i,r,n){var o,s,a,h,l,u,c;for(c=this.startIndices.length-2,a=this.startIndices[c+1],o=this.styleIndices_.length-1;0<=o;--o)for(h=this.styles_[o],this.setStrokeStyle_(t,h[0],h[1],h[2]),l=this.styleIndices_[o];0<=c&&this.startIndices[c]>=l;){if(s=this.startIndices[c],void 0===i[Et(u=this.startIndicesFeature[c]).toString()]&&u.getGeometry()&&(void 0===n||wt(n,u.getGeometry().getExtent()))){t.clear(t.COLOR_BUFFER_BIT|t.DEPTH_BUFFER_BIT),this.drawElements(t,e,s,a);var p=r(u);if(p)return p}c--,a=s}},t.prototype.setStrokeStyle_=function(t,e,i,r){t.uniform4fv(this.defaultLocations_.u_color,e),t.uniform1f(this.defaultLocations_.u_lineWidth,i),t.uniform1f(this.defaultLocations_.u_miterLimit,r)},t.prototype.setFillStrokeStyle=function(t,e){var i=e.getLineCap();this.state_.lineCap=void 0!==i?i:"round";var r=e.getLineDash();this.state_.lineDash=r||Ac;var n=e.getLineDashOffset();this.state_.lineDashOffset=n||0;var o=e.getLineJoin();this.state_.lineJoin=void 0!==o?o:"round";var s=e.getColor();s=s instanceof CanvasGradient||s instanceof CanvasPattern?Gc:Ne(s).map(function(t,e){return 3!=e?t/255:t})||Gc;var a=e.getWidth();a=void 0!==a?a:1;var h=e.getMiterLimit();h=void 0!==h?h:10,this.state_.strokeColor&&fr(this.state_.strokeColor,s)&&this.state_.lineWidth===a&&this.state_.miterLimit===h||(this.state_.changed=!0,this.state_.strokeColor=s,this.state_.lineWidth=a,this.state_.miterLimit=h,this.styles_.push([s,a,h]))},t}(Oc),pp=new Ic("precision mediump float;\n\n\n\nuniform vec4 u_color;\nuniform float u_opacity;\n\nvoid main(void) {\n gl_FragColor = u_color;\n float alpha = u_color.a * u_opacity;\n if (alpha == 0.0) {\n discard;\n }\n gl_FragColor.a = alpha;\n}\n"),dp=new Lc("\n\nattribute vec2 a_position;\n\nuniform mat4 u_projectionMatrix;\nuniform mat4 u_offsetScaleMatrix;\nuniform mat4 u_offsetRotateMatrix;\n\nvoid main(void) {\n gl_Position = u_projectionMatrix * vec4(a_position, 0.0, 1.0);\n}\n\n\n"),fp=function(t,e){this.u_projectionMatrix=t.getUniformLocation(e,"u_projectionMatrix"),this.u_offsetScaleMatrix=t.getUniformLocation(e,"u_offsetScaleMatrix"),this.u_offsetRotateMatrix=t.getUniformLocation(e,"u_offsetRotateMatrix"),this.u_color=t.getUniformLocation(e,"u_color"),this.u_opacity=t.getUniformLocation(e,"u_opacity"),this.a_position=t.getAttribLocation(e,"a_position")},_p=function(t){this.first_,this.last_,this.head_,this.circular_=void 0===t||t,this.length_=0};_p.prototype.insertItem=function(t){var e={prev:void 0,next:void 0,data:t},i=this.head_;if(i){var r=i.next;e.prev=i,e.next=r,i.next=e,r&&(r.prev=e),i===this.last_&&(this.last_=e)}else this.first_=e,this.last_=e,this.circular_&&((e.next=e).prev=e);this.head_=e,this.length_++},_p.prototype.removeItem=function(){var t=this.head_;if(t){var e=t.next,i=t.prev;e&&(e.prev=i),i&&(i.next=e),this.head_=e||i,this.first_===this.last_?(this.head_=void 0,this.first_=void 0,this.last_=void 0):this.first_===t?this.first_=this.head_:this.last_===t&&(this.last_=i?this.head_.prev:this.head_),this.length_--}},_p.prototype.firstItem=function(){if(this.head_=this.first_,this.head_)return this.head_.data},_p.prototype.lastItem=function(){if(this.head_=this.last_,this.head_)return this.head_.data},_p.prototype.nextItem=function(){if(this.head_&&this.head_.next)return this.head_=this.head_.next,this.head_.data},_p.prototype.getNextItem=function(){if(this.head_&&this.head_.next)return this.head_.next.data},_p.prototype.prevItem=function(){if(this.head_&&this.head_.prev)return this.head_=this.head_.prev,this.head_.data},_p.prototype.getPrevItem=function(){if(this.head_&&this.head_.prev)return this.head_.prev.data},_p.prototype.getCurrItem=function(){if(this.head_)return this.head_.data},_p.prototype.setFirstItem=function(){this.circular_&&this.head_&&(this.first_=this.head_,this.last_=this.head_.prev)},_p.prototype.concat=function(t){if(t.head_){if(this.head_){var e=this.head_.next;this.head_.next=t.first_,t.first_.prev=this.head_,e.prev=t.last_,t.last_.next=e,this.length_+=t.length_}else this.head_=t.head_,this.first_=t.first_,this.last_=t.last_,this.length_=t.length_;t.head_=void 0,t.first_=void 0,t.last_=void 0,t.length_=0}},_p.prototype.getLength=function(){return this.length_};var gp=function(i){function t(t,e){i.call(this,t,e),this.lineStringReplay=new cp(t,e),this.defaultLocations_=null,this.styles_=[],this.styleIndices_=[],this.state_={fillColor:null,changed:!1}}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.drawCoordinates_=function(t,e,i){var r=new _p,n=new Gh;this.processFlatCoordinates_(t,i,r,n,!0);var o=this.getMaxCoords_(r);if(e.length){var s,a,h=[];for(s=0,a=e.length;s<a;++s){var l={list:new _p,maxCoords:void 0,rtree:new Gh};h.push(l),this.processFlatCoordinates_(e[s],i,l.list,l.rtree,!1),this.classifyPoints_(l.list,l.rtree,!0),l.maxCoords=this.getMaxCoords_(l.list)}for(h.sort(function(t,e){return e.maxCoords[0]===t.maxCoords[0]?t.maxCoords[1]-e.maxCoords[1]:e.maxCoords[0]-t.maxCoords[0]}),s=0;s<h.length;++s){var u=h[s].list,c=u.firstItem(),p=c,d=void 0;do{if(this.getIntersections_(p,n).length){d=!0;break}p=u.nextItem()}while(c!==p);d||this.bridgeHole_(u,h[s].maxCoords[0],r,o[0],n)&&(n.concat(h[s].rtree),this.classifyPoints_(r,n,!1))}}else this.classifyPoints_(r,n,!1);this.triangulate_(r,n)},t.prototype.processFlatCoordinates_=function(t,e,i,r,n){var o,s,a,h,l,u=Hr(t,0,t.length,e),c=this.vertices.length/2,p=[],d=[];if(n===u){for(h=a=this.createPoint_(t[0],t[1],c++),o=e,s=t.length;o<s;o+=e)l=this.createPoint_(t[o],t[o+1],c++),d.push(this.insertItem_(h,l,i)),p.push([Math.min(h.x,l.x),Math.min(h.y,l.y),Math.max(h.x,l.x),Math.max(h.y,l.y)]),h=l;d.push(this.insertItem_(l,a,i)),p.push([Math.min(h.x,l.x),Math.min(h.y,l.y),Math.max(h.x,l.x),Math.max(h.y,l.y)])}else{var f=t.length-e;for(h=a=this.createPoint_(t[f],t[f+1],c++),o=f-e,s=0;s<=o;o-=e)l=this.createPoint_(t[o],t[o+1],c++),d.push(this.insertItem_(h,l,i)),p.push([Math.min(h.x,l.x),Math.min(h.y,l.y),Math.max(h.x,l.x),Math.max(h.y,l.y)]),h=l;d.push(this.insertItem_(l,a,i)),p.push([Math.min(h.x,l.x),Math.min(h.y,l.y),Math.max(h.x,l.x),Math.max(h.y,l.y)])}r.load(p,d)},t.prototype.getMaxCoords_=function(t){for(var e=t.firstItem(),i=e,r=[i.p0.x,i.p0.y];(i=t.nextItem()).p0.x>r[0]&&(r=[i.p0.x,i.p0.y]),i!==e;);return r},t.prototype.classifyPoints_=function(t,e,i){var r=t.firstItem(),n=r,o=t.nextItem(),s=!1;do{var a=i?Dc(o.p1.x,o.p1.y,n.p1.x,n.p1.y,n.p0.x,n.p0.y):Dc(n.p0.x,n.p0.y,n.p1.x,n.p1.y,o.p1.x,o.p1.y);void 0===a?(this.removeItem_(n,o,t,e),s=!0,o===r&&(r=t.getNextItem()),o=n,t.prevItem()):n.p1.reflex!==a&&(n.p1.reflex=a,s=!0),n=o,o=t.nextItem()}while(n!==r);return s},t.prototype.bridgeHole_=function(t,e,i,r,n){for(var o=t.firstItem();o.p1.x!==e;)o=t.nextItem();var s,a,h,l,u=o.p1,c={x:r,y:u.y,i:-1},p=1/0,d=this.getIntersections_({p0:u,p1:c},n,!0);for(s=0,a=d.length;s<a;++s){var f=d[s],_=this.calculateIntersection_(u,c,f.p0,f.p1,!0),g=Math.abs(u.x-_[0]);g<p&&void 0!==Dc(u.x,u.y,f.p0.x,f.p0.y,f.p1.x,f.p1.y)&&(p=g,l={x:_[0],y:_[1],i:-1},o=f)}if(p===1/0)return!1;if(h=o.p1,0<p){var y=this.getPointsInTriangle_(u,l,o.p1,n);if(y.length){var v=1/0;for(s=0,a=y.length;s<a;++s){var m=y[s],x=Math.atan2(u.y-m.y,c.x-m.x);(x<v||x===v&&m.x<h.x)&&(v=x,h=m)}}}for(o=i.firstItem();o.p1.x!==h.x||o.p1.y!==h.y;)o=i.nextItem();var S={x:u.x,y:u.y,i:u.i,reflex:void 0},C={x:o.p1.x,y:o.p1.y,i:o.p1.i,reflex:void 0};return t.getNextItem().p0=S,this.insertItem_(u,o.p1,t,n),this.insertItem_(C,S,t,n),o.p1=C,t.setFirstItem(),i.concat(t),!0},t.prototype.triangulate_=function(t,e){for(var i=this,r=!1,n=this.isSimple_(t,e);3<t.getLength();)if(n){if(!i.clipEars_(t,e,n,r)&&!i.classifyPoints_(t,e,r)&&!i.resolveSelfIntersections_(t,e,!0))break}else if(!i.clipEars_(t,e,n,r)&&!i.classifyPoints_(t,e,r)&&!i.resolveSelfIntersections_(t,e)){if(!(n=i.isSimple_(t,e))){i.splitPolygon_(t,e);break}r=!i.isClockwise_(t),i.classifyPoints_(t,e,r)}if(3===t.getLength()){var o=this.indices.length;this.indices[o++]=t.getPrevItem().p0.i,this.indices[o++]=t.getCurrItem().p0.i,this.indices[o++]=t.getNextItem().p0.i}},t.prototype.clipEars_=function(t,e,i,r){var n,o,s,a=this.indices.length,h=t.firstItem(),l=t.getPrevItem(),u=h,c=t.nextItem(),p=t.getNextItem(),d=!1;do{if(n=u.p0,o=u.p1,s=c.p1,!1===o.reflex){var f=void 0;f=i?0===this.getPointsInTriangle_(n,o,s,e,!0).length:r?this.diagonalIsInside_(p.p1,s,o,n,l.p0):this.diagonalIsInside_(l.p0,n,o,s,p.p1),(i||0===this.getIntersections_({p0:n,p1:s},e).length)&&f&&(i||!1===n.reflex||!1===s.reflex||Hr([l.p0.x,l.p0.y,n.x,n.y,o.x,o.y,s.x,s.y,p.p1.x,p.p1.y],0,10,2)===!r)&&(this.indices[a++]=n.i,this.indices[a++]=o.i,this.indices[a++]=s.i,this.removeItem_(u,c,t,e),c===h&&(h=p),d=!0)}l=t.getPrevItem(),u=t.getCurrItem(),c=t.nextItem(),p=t.getNextItem()}while(u!==h&&3<t.getLength());return d},t.prototype.resolveSelfIntersections_=function(t,e,i){var r=t.firstItem();t.nextItem();var n=r,o=t.nextItem(),s=!1;do{var a=this.calculateIntersection_(n.p0,n.p1,o.p0,o.p1,i);if(a){var h=!1,l=this.vertices.length,u=this.indices.length,c=l/2,p=t.prevItem();t.removeItem(),e.remove(p),h=p===r;var d=void 0;if(i?(a[0]===n.p0.x&&a[1]===n.p0.y?(t.prevItem(),d=n.p0,o.p0=d,e.remove(n),h=h||n===r):(d=o.p1,n.p1=d,e.remove(o),h=h||o===r),t.removeItem()):(d=this.createPoint_(a[0],a[1],c),n.p1=d,o.p0=d,e.update([Math.min(n.p0.x,n.p1.x),Math.min(n.p0.y,n.p1.y),Math.max(n.p0.x,n.p1.x),Math.max(n.p0.y,n.p1.y)],n),e.update([Math.min(o.p0.x,o.p1.x),Math.min(o.p0.y,o.p1.y),Math.max(o.p0.x,o.p1.x),Math.max(o.p0.y,o.p1.y)],o)),this.indices[u++]=p.p0.i,this.indices[u++]=p.p1.i,this.indices[u++]=d.i,s=!0,h)break}n=t.getPrevItem(),o=t.nextItem()}while(n!==r);return s},t.prototype.isSimple_=function(t,e){var i=t.firstItem(),r=i;do{if(this.getIntersections_(r,e).length)return!1;r=t.nextItem()}while(r!==i);return!0},t.prototype.isClockwise_=function(t){for(var e=2*t.getLength(),i=new Array(e),r=t.firstItem(),n=r,o=0;i[o++]=n.p0.x,i[o++]=n.p0.y,(n=t.nextItem())!==r;);return Hr(i,0,e,2)},t.prototype.splitPolygon_=function(t,e){var i=this,r=t.firstItem(),n=r;do{var o=i.getIntersections_(n,e);if(o.length){var s=o[0],a=i.vertices.length/2,h=i.calculateIntersection_(n.p0,n.p1,s.p0,s.p1),l=i.createPoint_(h[0],h[1],a),u=new _p,c=new Gh;i.insertItem_(l,n.p1,u,c),n.p1=l,e.update([Math.min(n.p0.x,l.x),Math.min(n.p0.y,l.y),Math.max(n.p0.x,l.x),Math.max(n.p0.y,l.y)],n);for(var p=t.nextItem();p!==s;)i.insertItem_(p.p0,p.p1,u,c),e.remove(p),t.removeItem(),p=t.getCurrItem();i.insertItem_(s.p0,l,u,c),s.p0=l,e.update([Math.min(s.p1.x,l.x),Math.min(s.p1.y,l.y),Math.max(s.p1.x,l.x),Math.max(s.p1.y,l.y)],s),i.classifyPoints_(t,e,!1),i.triangulate_(t,e),i.classifyPoints_(u,c,!1),i.triangulate_(u,c);break}n=t.nextItem()}while(n!==r)},t.prototype.createPoint_=function(t,e,i){var r=this.vertices.length;return{x:this.vertices[r++]=t,y:this.vertices[r++]=e,i:i,reflex:void 0}},t.prototype.insertItem_=function(t,e,i,r){var n={p0:t,p1:e};return i.insertItem(n),r&&r.insert([Math.min(t.x,e.x),Math.min(t.y,e.y),Math.max(t.x,e.x),Math.max(t.y,e.y)],n),n},t.prototype.removeItem_=function(t,e,i,r){i.getCurrItem()===e&&(i.removeItem(),t.p1=e.p1,r.remove(e),r.update([Math.min(t.p0.x,t.p1.x),Math.min(t.p0.y,t.p1.y),Math.max(t.p0.x,t.p1.x),Math.max(t.p0.y,t.p1.y)],t))},t.prototype.getPointsInTriangle_=function(t,e,i,r,n){for(var o=[],s=r.getInExtent([Math.min(t.x,e.x,i.x),Math.min(t.y,e.y,i.y),Math.max(t.x,e.x,i.x),Math.max(t.y,e.y,i.y)]),a=0,h=s.length;a<h;++a)for(var l in s[a]){var u=s[a][l];"object"!=typeof u||n&&!u.reflex||u.x===t.x&&u.y===t.y||u.x===e.x&&u.y===e.y||u.x===i.x&&u.y===i.y||-1!==o.indexOf(u)||!Ur([t.x,t.y,e.x,e.y,i.x,i.y],0,6,2,u.x,u.y)||o.push(u)}return o},t.prototype.getIntersections_=function(t,e,i){for(var r=t.p0,n=t.p1,o=e.getInExtent([Math.min(r.x,n.x),Math.min(r.y,n.y),Math.max(r.x,n.x),Math.max(r.y,n.y)]),s=[],a=0,h=o.length;a<h;++a){var l=o[a];t!==l&&(i||l.p0!==n||l.p1!==r)&&this.calculateIntersection_(r,n,l.p0,l.p1,i)&&s.push(l)}return s},t.prototype.calculateIntersection_=function(t,e,i,r,n){var o=(r.y-i.y)*(e.x-t.x)-(r.x-i.x)*(e.y-t.y);if(0!==o){var s=((r.x-i.x)*(t.y-i.y)-(r.y-i.y)*(t.x-i.x))/o,a=((e.x-t.x)*(t.y-i.y)-(e.y-t.y)*(t.x-i.x))/o;if(!n&&kc<s&&s<1-kc&&kc<a&&a<1-kc||n&&0<=s&&s<=1&&0<=a&&a<=1)return[t.x+s*(e.x-t.x),t.y+s*(e.y-t.y)]}},t.prototype.diagonalIsInside_=function(t,e,i,r,n){if(void 0===e.reflex||void 0===r.reflex)return!1;var o=(i.x-r.x)*(e.y-r.y)>(i.y-r.y)*(e.x-r.x),s=(n.x-r.x)*(e.y-r.y)<(n.y-r.y)*(e.x-r.x),a=(t.x-e.x)*(r.y-e.y)>(t.y-e.y)*(r.x-e.x),h=(i.x-e.x)*(r.y-e.y)<(i.y-e.y)*(r.x-e.x),l=r.reflex?s||o:s&&o,u=e.reflex?h||a:h&&a;return l&&u},t.prototype.drawMultiPolygon=function(t,e){var i,r,n,o,s=t.getEndss(),a=t.getStride(),h=this.indices.length,l=this.lineStringReplay.getCurrentIndex(),u=t.getFlatCoordinates(),c=0;for(i=0,r=s.length;i<r;++i){var p=s[i];if(0<p.length){var d=_t(u,c,p[0],a,-this.origin[0],-this.origin[1]);if(d.length){var f=[],_=void 0;for(n=1,o=p.length;n<o;++n)p[n]!==p[n-1]&&(_=_t(u,p[n-1],p[n],a,-this.origin[0],-this.origin[1]),f.push(_));this.lineStringReplay.drawPolygonCoordinates(d,f,a),this.drawCoordinates_(d,f,a)}}c=p[p.length-1]}this.indices.length>h&&(this.startIndices.push(h),this.startIndicesFeature.push(e),this.state_.changed&&(this.styleIndices_.push(h),this.state_.changed=!1)),this.lineStringReplay.getCurrentIndex()>l&&this.lineStringReplay.setPolygonStyle(e,l)},t.prototype.drawPolygon=function(t,e){var i=t.getEnds(),r=t.getStride();if(0<i.length){var n=t.getFlatCoordinates().map(Number),o=_t(n,0,i[0],r,-this.origin[0],-this.origin[1]);if(o.length){var s,a,h,l=[];for(s=1,a=i.length;s<a;++s)i[s]!==i[s-1]&&(h=_t(n,i[s-1],i[s],r,-this.origin[0],-this.origin[1]),l.push(h));this.startIndices.push(this.indices.length),this.startIndicesFeature.push(e),this.state_.changed&&(this.styleIndices_.push(this.indices.length),this.state_.changed=!1),this.lineStringReplay.setPolygonStyle(e),this.lineStringReplay.drawPolygonCoordinates(o,l,r),this.drawCoordinates_(o,l,r)}}},t.prototype.finish=function(t){this.verticesBuffer=new Uc(this.vertices),this.indicesBuffer=new Uc(this.indices),this.startIndices.push(this.indices.length),this.lineStringReplay.finish(t),0===this.styleIndices_.length&&0<this.styles_.length&&(this.styles_=[]),this.vertices=null,this.indices=null},t.prototype.getDeleteResourcesFunction=function(t){var e=this.verticesBuffer,i=this.indicesBuffer,r=this.lineStringReplay.getDeleteResourcesFunction(t);return function(){t.deleteBuffer(e),t.deleteBuffer(i),r()}},t.prototype.setUpProgram=function(t,e,i,r){var n,o=e.getProgram(pp,dp);return this.defaultLocations_?n=this.defaultLocations_:(n=new fp(t,o),this.defaultLocations_=n),e.useProgram(o),t.enableVertexAttribArray(n.a_position),t.vertexAttribPointer(n.a_position,2,Ve,!1,8,0),n},t.prototype.shutDownProgram=function(t,e){t.disableVertexAttribArray(e.a_position)},t.prototype.drawReplay=function(t,e,i,r){var n,o,s,a,h=t.getParameter(t.DEPTH_FUNC),l=t.getParameter(t.DEPTH_WRITEMASK);if(r||(t.enable(t.DEPTH_TEST),t.depthMask(!0),t.depthFunc(t.NOTEQUAL)),Tt(i))for(s=this.startIndices[this.startIndices.length-1],n=this.styleIndices_.length-1;0<=n;--n)o=this.styleIndices_[n],a=this.styles_[n],this.setFillStyle_(t,a),this.drawElements(t,e,o,s),s=o;else this.drawReplaySkipping_(t,e,i);r||(t.disable(t.DEPTH_TEST),t.clear(t.DEPTH_BUFFER_BIT),t.depthMask(l),t.depthFunc(h))},t.prototype.drawHitDetectionReplayOneByOne=function(t,e,i,r,n){var o,s,a,h,l,u,c;for(c=this.startIndices.length-2,a=this.startIndices[c+1],o=this.styleIndices_.length-1;0<=o;--o)for(h=this.styles_[o],this.setFillStyle_(t,h),l=this.styleIndices_[o];0<=c&&this.startIndices[c]>=l;){if(s=this.startIndices[c],void 0===i[Et(u=this.startIndicesFeature[c]).toString()]&&u.getGeometry()&&(void 0===n||wt(n,u.getGeometry().getExtent()))){t.clear(t.COLOR_BUFFER_BIT|t.DEPTH_BUFFER_BIT),this.drawElements(t,e,s,a);var p=r(u);if(p)return p}c--,a=s}},t.prototype.drawReplaySkipping_=function(t,e,i){var r,n,o,s,a,h,l;for(h=this.startIndices.length-2,o=n=this.startIndices[h+1],r=this.styleIndices_.length-1;0<=r;--r){for(s=this.styles_[r],this.setFillStyle_(t,s),a=this.styleIndices_[r];0<=h&&this.startIndices[h]>=a;)l=this.startIndices[h],i[Et(this.startIndicesFeature[h]).toString()]&&(n!==o&&(this.drawElements(t,e,n,o),t.clear(t.DEPTH_BUFFER_BIT)),o=l),h--,n=l;n!==o&&(this.drawElements(t,e,n,o),t.clear(t.DEPTH_BUFFER_BIT)),n=o=a}},t.prototype.setFillStyle_=function(t,e){t.uniform4fv(this.defaultLocations_.u_color,e)},t.prototype.setFillStrokeStyle=function(t,e){var i=t?t.getColor():[0,0,0,0];if(i=i instanceof CanvasGradient||i instanceof CanvasPattern?Nc:Ne(i).map(function(t,e){return 3!=e?t/255:t})||Nc,this.state_.fillColor&&fr(i,this.state_.fillColor)||(this.state_.fillColor=i,this.state_.changed=!0,this.styles_.push(i)),e)this.lineStringReplay.setFillStrokeStyle(null,e);else{var r=new Vi({color:[0,0,0,0],lineWidth:0});this.lineStringReplay.setFillStrokeStyle(null,r)}},t}(Oc),yp=function(t,e){this.space_=e,this.emptyBlocks_=[{x:0,y:0,width:t,height:t}],this.entries_={},this.context_=De(t,t),this.canvas_=this.context_.canvas};yp.prototype.get=function(t){return this.entries_[t]||null},yp.prototype.add=function(t,e,i,r,n){for(var o=this,s=0,a=this.emptyBlocks_.length;s<a;++s){var h=o.emptyBlocks_[s];if(h.width>=e+o.space_&&h.height>=i+o.space_){var l={offsetX:h.x+o.space_,offsetY:h.y+o.space_,image:o.canvas_};return o.entries_[t]=l,r.call(n,o.context_,h.x+o.space_,h.y+o.space_),o.split_(s,h,e+o.space_,i+o.space_),l}}return null},yp.prototype.split_=function(t,e,i,r){var n,o,s=e.width-i;e.height-r<s?(n={x:e.x+i,y:e.y,width:e.width-i,height:e.height},o={x:e.x,y:e.y+r,width:i,height:e.height-r}):(n={x:e.x+i,y:e.y,width:e.width-i,height:r},o={x:e.x,y:e.y+r,width:e.width,height:e.height-r}),this.updateBlocks_(t,n,o)},yp.prototype.updateBlocks_=function(t,e,i){var r=[t,1];0<e.width&&0<e.height&&r.push(e),0<i.width&&0<i.height&&r.push(i),this.emptyBlocks_.splice.apply(this.emptyBlocks_,r)};var vp=function(t){var e=t||{};this.currentSize_=void 0!==e.initialSize?e.initialSize:256,this.maxSize_=void 0!==e.maxSize?e.maxSize:void 0!==Be?Be:2048,this.space_=void 0!==e.space?e.space:1,this.atlases_=[new yp(this.currentSize_,this.space_)],this.currentHitSize_=this.currentSize_,this.hitAtlases_=[new yp(this.currentHitSize_,this.space_)]};vp.prototype.getInfo=function(t){var e=this.getInfo_(this.atlases_,t);if(!e)return null;var i=this.getInfo_(this.hitAtlases_,t);return this.mergeInfos_(e,i)},vp.prototype.getInfo_=function(t,e){for(var i=0,r=t.length;i<r;++i){var n=t[i].get(e);if(n)return n}return null},vp.prototype.mergeInfos_=function(t,e){return{offsetX:t.offsetX,offsetY:t.offsetY,image:t.image,hitImage:e.image}},vp.prototype.add=function(t,e,i,r,n,o){if(e+this.space_>this.maxSize_||i+this.space_>this.maxSize_)return null;var s=this.add_(!1,t,e,i,r,o);if(!s)return null;var a=void 0!==n?n:L,h=this.add_(!0,t,e,i,a,o);return this.mergeInfos_(s,h)},vp.prototype.add_=function(t,e,i,r,n,o){var s,a,h,l,u=t?this.hitAtlases_:this.atlases_;for(h=0,l=u.length;h<l;++h){if(a=(s=u[h]).add(e,i,r,n,o))return a;if(!a&&h===l-1){var c=void 0;t?(c=Math.min(2*this.currentHitSize_,this.maxSize_),this.currentHitSize_=c):(c=Math.min(2*this.currentSize_,this.maxSize_),this.currentSize_=c),s=new yp(c,this.space_),u.push(s),++l}}return null};var mp=function(i){function t(t,e){i.call(this,t,e),this.images_=[],this.textures_=[],this.measureCanvas_=De(0,0).canvas,this.state_={strokeColor:null,lineCap:void 0,lineDash:null,lineDashOffset:void 0,lineJoin:void 0,lineWidth:0,miterLimit:void 0,fillColor:null,font:void 0,scale:void 0},this.text_="",this.textAlign_=void 0,this.textBaseline_=void 0,this.offsetX_=void 0,this.offsetY_=void 0,this.atlases_={},this.currAtlas_=void 0,this.scale=1,this.opacity=1}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.drawText=function(t,e){var i=this;if(this.text_){var r=null,n=2,o=2;switch(t.getType()){case Lt.POINT:case Lt.MULTI_POINT:n=(r=t.getFlatCoordinates()).length,o=t.getStride();break;case Lt.CIRCLE:r=t.getCenter();break;case Lt.LINE_STRING:r=t.getFlatMidpoint();break;case Lt.MULTI_LINE_STRING:n=(r=t.getFlatMidpoints()).length;break;case Lt.POLYGON:r=t.getFlatInteriorPoint();break;case Lt.MULTI_POLYGON:n=(r=t.getFlatInteriorPoints()).length}this.startIndices.push(this.indices.length),this.startIndicesFeature.push(e);var s,a,h,l,u,c,p,d,f=this.currAtlas_,_=this.text_.split("\n"),g=this.getTextSize_(_),y=Math.round(g[0]*this.textAlign_-this.offsetX_),v=Math.round(g[1]*this.textBaseline_-this.offsetY_),m=this.state_.lineWidth/2*this.state_.scale;for(s=0,a=_.length;s<a;++s)for(u=0,c=f.height*s,h=0,l=(p=_[s].split("")).length;h<l;++h){if(d=f.atlas.getInfo(p[h])){var x=d.image;if(i.anchorX=y-u,i.anchorY=v-c,i.originX=0===h?d.offsetX-m:d.offsetX,i.originY=d.offsetY,i.height=f.height,i.width=0===h||h===p.length-1?f.width[p[h]]+m:f.width[p[h]],i.imageHeight=x.height,i.imageWidth=x.width,0===i.images_.length)i.images_.push(x);else Et(i.images_[i.images_.length-1])!=Et(x)&&(i.groupIndices.push(i.indices.length),i.images_.push(x));i.drawText_(r,0,n,o)}u+=i.width}}},t.prototype.getTextSize_=function(t){var o=this,s=this.currAtlas_,e=t.length*s.height;return[t.map(function(t){for(var e=0,i=0,r=t.length;i<r;++i){var n=t[i];s.width[n]||o.addCharToAtlas_(n),e+=s.width[n]?s.width[n]:0}return e}).reduce(function(t,e){return Math.max(t,e)}),e]},t.prototype.drawText_=function(t,e,i,r){for(var n=e,o=i;n<o;n+=r)this.drawCoordinates(t,e,i,r)},t.prototype.addCharToAtlas_=function(r){if(1===r.length){var t=this.currAtlas_,n=this.state_,e=this.measureCanvas_.getContext("2d");e.font=n.font;var i=Math.ceil(e.measureText(r).width*n.scale);t.atlas.add(r,i,t.height,function(t,e,i){t.font=n.font,t.fillStyle=n.fillColor,t.strokeStyle=n.strokeColor,t.lineWidth=n.lineWidth,t.lineCap=n.lineCap,t.lineJoin=n.lineJoin,t.miterLimit=n.miterLimit,t.textAlign="left",t.textBaseline="top",hi&&n.lineDash&&(t.setLineDash(n.lineDash),t.lineDashOffset=n.lineDashOffset),1!==n.scale&&t.setTransform(n.scale,0,0,n.scale,0,0),n.strokeColor&&t.strokeText(r,e,i),n.fillColor&&t.fillText(r,e,i)})&&(t.width[r]=i)}},t.prototype.finish=function(t){var e=t.getGL();this.groupIndices.push(this.indices.length),this.hitDetectionGroupIndices=this.groupIndices,this.verticesBuffer=new Uc(this.vertices),this.indicesBuffer=new Uc(this.indices);this.createTextures(this.textures_,this.images_,{},e),this.state_={strokeColor:null,lineCap:void 0,lineDash:null,lineDashOffset:void 0,lineJoin:void 0,lineWidth:0,miterLimit:void 0,fillColor:null,font:void 0,scale:void 0},this.text_="",this.textAlign_=void 0,this.textBaseline_=void 0,this.offsetX_=void 0,this.offsetY_=void 0,this.images_=null,this.atlases_={},this.currAtlas_=void 0,i.prototype.finish.call(this,t)},t.prototype.setTextStyle=function(t){var e=this.state_,i=t.getFill(),r=t.getStroke();if(t&&t.getText()&&(i||r)){if(i){var n=i.getColor();e.fillColor=ke(n||Nc)}else e.fillColor=null;if(r){var o=r.getColor();e.strokeColor=ke(o||Gc),e.lineWidth=r.getWidth()||1,e.lineCap=r.getLineCap()||"round",e.lineDashOffset=r.getLineDashOffset()||0,e.lineJoin=r.getLineJoin()||"round",e.miterLimit=r.getMiterLimit()||10;var s=r.getLineDash();e.lineDash=s?s.slice():Ac}else e.strokeColor=null,e.lineWidth=0;e.font=t.getFont()||"10px sans-serif",e.scale=t.getScale()||1,this.text_=t.getText();var a=_u[t.getTextAlign()],h=_u[t.getTextBaseline()];this.textAlign_=void 0===a?.5:a,this.textBaseline_=void 0===h?.5:h,this.offsetX_=t.getOffsetX()||0,this.offsetY_=t.getOffsetY()||0,this.rotateWithView=!!t.getRotateWithView(),this.rotation=t.getRotation()||0,this.currAtlas_=this.getAtlas_(e)}else this.text_=""},t.prototype.getAtlas_=function(t){var e=[];for(var i in t)(t[i]||0===t[i])&&(Array.isArray(t[i])?e=e.concat(t[i]):e.push(t[i]));var r=this.calculateHash_(e);if(!this.atlases_[r]){var n=this.measureCanvas_.getContext("2d");n.font=t.font;var o=Math.ceil((1.5*n.measureText("M").width+t.lineWidth/2)*t.scale);this.atlases_[r]={atlas:new vp({space:t.lineWidth+1}),width:{},height:o}}return this.atlases_[r]},t.prototype.calculateHash_=function(t){for(var e="",i=0,r=t.length;i<r;++i)e+=t[i];return e},t.prototype.getTextures=function(t){return this.textures_},t.prototype.getHitDetectionTextures=function(){return this.textures_},t}(Jc),xp=[1,1],Sp={Circle:Yc,Image:Qc,LineString:cp,Polygon:gp,Text:mp},Cp=function(r){function t(t,e,i){r.call(this),this.maxExtent_=e,this.tolerance_=t,this.renderBuffer_=i,this.replaysByZIndex_={}}return r&&(t.__proto__=r),((t.prototype=Object.create(r&&r.prototype)).constructor=t).prototype.addDeclutter=function(t,e){},t.prototype.getDeleteResourcesFunction=function(t){var e,n=[];for(e in this.replaysByZIndex_){var i=this.replaysByZIndex_[e];for(var r in i)n.push(i[r].getDeleteResourcesFunction(t))}return function(){for(var t,e=arguments,i=n.length,r=0;r<i;r++)t=n[r].apply(this,e);return t}},t.prototype.finish=function(t){var e;for(e in this.replaysByZIndex_){var i=this.replaysByZIndex_[e];for(var r in i)i[r].finish(t)}},t.prototype.getReplay=function(t,e){var i=void 0!==t?t.toString():"0",r=this.replaysByZIndex_[i];void 0===r&&(r={},this.replaysByZIndex_[i]=r);var n=r[e];void 0===n&&(n=new Sp[e](this.tolerance_,this.maxExtent_),r[e]=n);return n},t.prototype.isEmpty=function(){return Tt(this.replaysByZIndex_)},t.prototype.replay=function(t,e,i,r,n,o,s,a){var h,l,u,c,p,d,f=Object.keys(this.replaysByZIndex_).map(Number);for(f.sort(hr),h=0,l=f.length;h<l;++h)for(p=this.replaysByZIndex_[f[h].toString()],u=0,c=fu.length;u<c;++u)d=p[fu[u]],void 0!==d&&d.replay(t,e,i,r,n,o,s,a,void 0,!1)},t.prototype.replayHitDetection_=function(t,e,i,r,n,o,s,a,h,l,u){var c,p,d,f,_,g,y=Object.keys(this.replaysByZIndex_).map(Number);for(y.sort(function(t,e){return e-t}),c=0,p=y.length;c<p;++c)for(f=this.replaysByZIndex_[y[c].toString()],d=fu.length-1;0<=d;--d)if(void 0!==(_=f[fu[d]])&&(g=_.replay(t,e,i,r,n,o,s,a,h,l,u)))return g},t.prototype.forEachFeatureAtCoordinate=function(t,e,i,r,n,o,s,a,h,l){var u,c=e.getGL();return c.bindFramebuffer(c.FRAMEBUFFER,e.getHitDetectionFramebuffer()),void 0!==this.renderBuffer_&&(u=G(V(t),r*this.renderBuffer_)),this.replayHitDetection_(e,t,r,n,xp,s,a,h,function(t){var e=new Uint8Array(4);if(c.readPixels(0,0,1,1,c.RGBA,c.UNSIGNED_BYTE,e),0<e[3]){var i=l(t);if(i)return i}},!0,u)},t.prototype.hasFeatureAtCoordinate=function(t,e,i,r,n,o,s,a,h){var l=e.getGL();return l.bindFramebuffer(l.FRAMEBUFFER,e.getHitDetectionFramebuffer()),void 0!==this.replayHitDetection_(e,t,r,n,xp,s,a,h,function(t){var e=new Uint8Array(4);return l.readPixels(0,0,1,1,l.RGBA,l.UNSIGNED_BYTE,e),0<e[3]},!1)},t}(Hl),Ep=function(a){function t(t,e,i,r,n,o,s){a.call(this),this.context_=t,this.center_=e,this.extent_=o,this.pixelRatio_=s,this.size_=n,this.rotation_=r,this.resolution_=i,this.imageStyle_=null,this.fillStyle_=null,this.strokeStyle_=null,this.textStyle_=null}return a&&(t.__proto__=a),((t.prototype=Object.create(a&&a.prototype)).constructor=t).prototype.drawText_=function(t,e){var i=this.context_,r=t.getReplay(0,Zl.TEXT);r.setTextStyle(this.textStyle_),r.drawText(e,null),r.finish(i);r.replay(this.context_,this.center_,this.resolution_,this.rotation_,this.size_,this.pixelRatio_,1,{},void 0,!1),r.getDeleteResourcesFunction(i)()},t.prototype.setStyle=function(t){this.setFillStrokeStyle(t.getFill(),t.getStroke()),this.setImageStyle(t.getImage()),this.setTextStyle(t.getText())},t.prototype.drawGeometry=function(t){switch(t.getType()){case Lt.POINT:this.drawPoint(t,null);break;case Lt.LINE_STRING:this.drawLineString(t,null);break;case Lt.POLYGON:this.drawPolygon(t,null);break;case Lt.MULTI_POINT:this.drawMultiPoint(t,null);break;case Lt.MULTI_LINE_STRING:this.drawMultiLineString(t,null);break;case Lt.MULTI_POLYGON:this.drawMultiPolygon(t,null);break;case Lt.GEOMETRY_COLLECTION:this.drawGeometryCollection(t,null);break;case Lt.CIRCLE:this.drawCircle(t,null)}},t.prototype.drawFeature=function(t,e){var i=e.getGeometryFunction()(t);i&&wt(this.extent_,i.getExtent())&&(this.setStyle(e),this.drawGeometry(i))},t.prototype.drawGeometryCollection=function(t,e){var i,r,n=t.getGeometriesArray();for(i=0,r=n.length;i<r;++i)this.drawGeometry(n[i])},t.prototype.drawPoint=function(t,e){var i=this.context_,r=new Cp(1,this.extent_),n=r.getReplay(0,Zl.IMAGE);n.setImageStyle(this.imageStyle_),n.drawPoint(t,e),n.finish(i);n.replay(this.context_,this.center_,this.resolution_,this.rotation_,this.size_,this.pixelRatio_,1,{},void 0,!1),n.getDeleteResourcesFunction(i)(),this.textStyle_&&this.drawText_(r,t)},t.prototype.drawMultiPoint=function(t,e){var i=this.context_,r=new Cp(1,this.extent_),n=r.getReplay(0,Zl.IMAGE);n.setImageStyle(this.imageStyle_),n.drawMultiPoint(t,e),n.finish(i);n.replay(this.context_,this.center_,this.resolution_,this.rotation_,this.size_,this.pixelRatio_,1,{},void 0,!1),n.getDeleteResourcesFunction(i)(),this.textStyle_&&this.drawText_(r,t)},t.prototype.drawLineString=function(t,e){var i=this.context_,r=new Cp(1,this.extent_),n=r.getReplay(0,Zl.LINE_STRING);n.setFillStrokeStyle(null,this.strokeStyle_),n.drawLineString(t,e),n.finish(i);n.replay(this.context_,this.center_,this.resolution_,this.rotation_,this.size_,this.pixelRatio_,1,{},void 0,!1),n.getDeleteResourcesFunction(i)(),this.textStyle_&&this.drawText_(r,t)},t.prototype.drawMultiLineString=function(t,e){var i=this.context_,r=new Cp(1,this.extent_),n=r.getReplay(0,Zl.LINE_STRING);n.setFillStrokeStyle(null,this.strokeStyle_),n.drawMultiLineString(t,e),n.finish(i);n.replay(this.context_,this.center_,this.resolution_,this.rotation_,this.size_,this.pixelRatio_,1,{},void 0,!1),n.getDeleteResourcesFunction(i)(),this.textStyle_&&this.drawText_(r,t)},t.prototype.drawPolygon=function(t,e){var i=this.context_,r=new Cp(1,this.extent_),n=r.getReplay(0,Zl.POLYGON);n.setFillStrokeStyle(this.fillStyle_,this.strokeStyle_),n.drawPolygon(t,e),n.finish(i);n.replay(this.context_,this.center_,this.resolution_,this.rotation_,this.size_,this.pixelRatio_,1,{},void 0,!1),n.getDeleteResourcesFunction(i)(),this.textStyle_&&this.drawText_(r,t)},t.prototype.drawMultiPolygon=function(t,e){var i=this.context_,r=new Cp(1,this.extent_),n=r.getReplay(0,Zl.POLYGON);n.setFillStrokeStyle(this.fillStyle_,this.strokeStyle_),n.drawMultiPolygon(t,e),n.finish(i);n.replay(this.context_,this.center_,this.resolution_,this.rotation_,this.size_,this.pixelRatio_,1,{},void 0,!1),n.getDeleteResourcesFunction(i)(),this.textStyle_&&this.drawText_(r,t)},t.prototype.drawCircle=function(t,e){var i=this.context_,r=new Cp(1,this.extent_),n=r.getReplay(0,Zl.CIRCLE);n.setFillStrokeStyle(this.fillStyle_,this.strokeStyle_),n.drawCircle(t,e),n.finish(i);n.replay(this.context_,this.center_,this.resolution_,this.rotation_,this.size_,this.pixelRatio_,1,{},void 0,!1),n.getDeleteResourcesFunction(i)(),this.textStyle_&&this.drawText_(r,t)},t.prototype.setImageStyle=function(t){this.imageStyle_=t},t.prototype.setFillStrokeStyle=function(t,e){this.fillStyle_=t,this.strokeStyle_=e},t.prototype.setTextStyle=function(t){this.textStyle_=t},t}(Fl),Tp=new Ic("precision mediump float;\nvarying vec2 v_texCoord;\n\n\nuniform float u_opacity;\nuniform sampler2D u_texture;\n\nvoid main(void) {\n vec4 texColor = texture2D(u_texture, v_texCoord);\n gl_FragColor.rgb = texColor.rgb;\n gl_FragColor.a = texColor.a * u_opacity;\n}\n"),wp=new Lc("varying vec2 v_texCoord;\n\n\nattribute vec2 a_position;\nattribute vec2 a_texCoord;\n\nuniform mat4 u_texCoordMatrix;\nuniform mat4 u_projectionMatrix;\n\nvoid main(void) {\n gl_Position = u_projectionMatrix * vec4(a_position, 0., 1.);\n v_texCoord = (u_texCoordMatrix * vec4(a_texCoord, 0., 1.)).st;\n}\n\n\n"),Rp=function(t,e){this.u_texCoordMatrix=t.getUniformLocation(e,"u_texCoordMatrix"),this.u_projectionMatrix=t.getUniformLocation(e,"u_projectionMatrix"),this.u_opacity=t.getUniformLocation(e,"u_opacity"),this.u_texture=t.getUniformLocation(e,"u_texture"),this.a_position=t.getAttribLocation(e,"a_position"),this.a_texCoord=t.getAttribLocation(e,"a_texCoord")},Ip=function(i){function t(t,e){i.call(this,e),this.mapRenderer=t,this.arrayBuffer_=new Uc([-1,-1,0,0,1,-1,1,0,-1,1,0,1,1,1,1,1]),this.texture=null,this.framebuffer=null,this.framebufferDimension=void 0,this.texCoordMatrix=[1,0,0,1,0,0],this.projectionMatrix=[1,0,0,1,0,0],this.tmpMat4_=[1,0,0,0,0,1,0,0,0,0,1,0,0,0,0,1],this.defaultLocations_=null}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.bindFramebuffer=function(t,e){var i=this.mapRenderer.getGL();if(void 0===this.framebufferDimension||this.framebufferDimension!=e){var r=function(t,e,i){t.isContextLost()||(t.deleteFramebuffer(e),t.deleteTexture(i))}.bind(null,i,this.framebuffer,this.texture);t.postRenderFunctions.push(r);var n=Zc(i,e,e),o=i.createFramebuffer();i.bindFramebuffer(qe,o),i.framebufferTexture2D(qe,36064,He,n,0),this.texture=n,this.framebuffer=o,this.framebufferDimension=e}else i.bindFramebuffer(qe,this.framebuffer)},t.prototype.composeFrame=function(t,e,i){this.dispatchComposeEvent_(Tn,i,t),i.bindBuffer(ze,this.arrayBuffer_);var r,n=i.getGL(),o=i.getProgram(Tp,wp);this.defaultLocations_?r=this.defaultLocations_:(r=new Rp(n,o),this.defaultLocations_=r),i.useProgram(o)&&(n.enableVertexAttribArray(r.a_position),n.vertexAttribPointer(r.a_position,2,Ve,!1,16,0),n.enableVertexAttribArray(r.a_texCoord),n.vertexAttribPointer(r.a_texCoord,2,Ve,!1,16,8),n.uniform1i(r.u_texture,0)),n.uniformMatrix4fv(r.u_texCoordMatrix,!1,Mc(this.tmpMat4_,this.getTexCoordMatrix())),n.uniformMatrix4fv(r.u_projectionMatrix,!1,Mc(this.tmpMat4_,this.getProjectionMatrix())),n.uniform1f(r.u_opacity,e.opacity),n.bindTexture(He,this.getTexture()),n.drawArrays(5,0,4),this.dispatchComposeEvent_(En,i,t)},t.prototype.dispatchComposeEvent_=function(t,e,i){var r=this.getLayer();if(r.hasListener(t)){var n=i.viewState,o=n.resolution,s=i.pixelRatio,a=i.extent,h=n.center,l=n.rotation,u=i.size,c=new Ep(e,h,o,l,u,a,s),p=new Pl(t,c,i,null,e);r.dispatchEvent(p)}},t.prototype.getTexCoordMatrix=function(){return this.texCoordMatrix},t.prototype.getTexture=function(){return this.texture},t.prototype.getProjectionMatrix=function(){return this.projectionMatrix},t.prototype.handleWebGLContextLost=function(){this.texture=null,this.framebuffer=null,this.framebufferDimension=void 0},t.prototype.prepareFrame=function(t,e,i){},t.prototype.forEachLayerAtPixel=function(t,e,i,r){},t}(Yl),Lp=function(i){function t(t,e){i.call(this,t,e),this.image_=null,this.hitCanvasContext_=null,this.hitTransformationMatrix_=null}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.createTexture_=function(t){var e=t.getImage();return qc(this.mapRenderer.getGL(),e,Ze,Ze)},t.prototype.forEachFeatureAtCoordinate=function(t,e,i,r,n){var o=this.getLayer(),s=o.getSource(),a=e.viewState.resolution,h=e.viewState.rotation,l=e.skippedFeatureUids;return s.forEachFeatureAtCoordinate(t,a,h,i,l,function(t){return r.call(n,t,o)})},t.prototype.prepareFrame=function(t,e,i){var r=this.mapRenderer.getGL(),n=t.pixelRatio,o=t.viewState,s=o.center,a=o.resolution,h=o.rotation,l=this.image_,u=this.texture,c=this.getLayer().getSource(),p=t.viewHints,d=t.extent;if(void 0!==e.extent&&(d=ht(d,e.extent)),!p[rs.ANIMATING]&&!p[rs.INTERACTING]&&!pt(d)){var f=o.projection,_=c.getImage(d,a,n,f);if(_)if(this.loadImage(_)&&(l=_,u=this.createTexture_(_),this.texture)){var g=function(t,e){t.isContextLost()||t.deleteTexture(e)}.bind(null,r,this.texture);t.postRenderFunctions.push(g)}}if(l){var y=this.mapRenderer.getContext().getCanvas();this.updateProjectionMatrix_(y.width,y.height,n,s,a,h,l.getExtent()),this.hitTransformationMatrix_=null;var v=this.texCoordMatrix;ge(v),Ce(v,1,-1),Ee(v,0,-1),this.image_=l,this.texture=u}return!!l},t.prototype.updateProjectionMatrix_=function(t,e,i,r,n,o,s){var a=t*n,h=e*n,l=this.projectionMatrix;ge(l),Ce(l,2*i/a,2*i/h),Se(l,-o),Ee(l,s[0]-r[0],s[1]-r[1]),Ce(l,(s[2]-s[0])/2,(s[3]-s[1])/2),Ee(l,1,1)},t.prototype.hasFeatureAtCoordinate=function(t,e){return void 0!==this.forEachFeatureAtCoordinate(t,e,0,y,this)},t.prototype.forEachLayerAtPixel=function(t,e,i,r){if(this.image_&&this.image_.getImage()){if(this.getLayer().getSource().forEachFeatureAtCoordinate!==L){var n=xe(e.pixelToCoordinateTransform,t.slice());return this.forEachFeatureAtCoordinate(n,e,0,y,this)?i.call(r,this.getLayer(),null):void 0}var o=[this.image_.getImage().width,this.image_.getImage().height];this.hitTransformationMatrix_||(this.hitTransformationMatrix_=this.getHitTransformationMatrix_(e.size,o));var s=xe(this.hitTransformationMatrix_,t.slice());if(!(s[0]<0||s[0]>o[0]||s[1]<0||s[1]>o[1])){this.hitCanvasContext_||(this.hitCanvasContext_=De(1,1)),this.hitCanvasContext_.clearRect(0,0,1,1),this.hitCanvasContext_.drawImage(this.image_.getImage(),s[0],s[1],1,1,0,0,1,1);var a=this.hitCanvasContext_.getImageData(0,0,1,1).data;return 0<a[3]?i.call(r,this.getLayer(),a):void 0}}},t.prototype.getHitTransformationMatrix_=function(t,e){var i=[1,0,0,1,0,0];Ee(i,-1,-1),Ce(i,2/t[0],2/t[1]),Ee(i,0,t[1]),Ce(i,1,-1);var r=we(this.projectionMatrix.slice()),n=[1,0,0,1,0,0];return Ee(n,0,e[1]),Ce(n,1,-1),Ce(n,e[0]/2,e[1]/2),Ee(n,1,1),ye(n,r),ye(n,i),n},t}(Ip);Lp.handles=function(t){return t.getType()===oh.IMAGE},Lp.create=function(t,e){return new Lp(t,e)};var bp=function(i){function t(t){i.call(this,t);var e=t.getViewport();this.canvas_=document.createElement("CANVAS"),this.canvas_.style.width="100%",this.canvas_.style.height="100%",this.canvas_.style.display="block",this.canvas_.className=_i,e.insertBefore(this.canvas_,e.childNodes[0]||null),this.clipTileCanvasWidth_=0,this.clipTileCanvasHeight_=0,this.clipTileContext_=De(),this.renderedVisible_=!0,this.gl_=Qe(this.canvas_,{antialias:!0,depth:!0,failIfMajorPerformanceCaveat:!0,preserveDrawingBuffer:!1,stencil:!0}),this.context_=new Kc(this.canvas_,this.gl_),E(this.canvas_,Vc,this.handleWebGLContextLost,this),E(this.canvas_,Wc,this.handleWebGLContextRestored,this),this.textureCache_=new mi,this.focus_=null,this.tileTextureQueue_=new qo(function(t){var e=t[1],i=t[2],r=e[0]-this.focus_[0],n=e[1]-this.focus_[1];return 65536*Math.log(i)+Math.sqrt(r*r+n*n)/i}.bind(this),function(t){return t[0].getKey()}),this.loadNextTileTexture_=function(t,e){if(!this.tileTextureQueue_.isEmpty()){this.tileTextureQueue_.reprioritize();var i=this.tileTextureQueue_.dequeue(),r=i[0],n=i[3],o=i[4];this.bindTileTexture(r,n,o,9729,9729)}return!1}.bind(this),this.textureCacheFrameMarkerCount_=0,this.initializeGL_()}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.bindTileTexture=function(t,e,i,r,n){var o=this.getGL(),s=t.getKey();if(this.textureCache_.containsKey(s)){var a=this.textureCache_.get(s);o.bindTexture(He,a.texture),a.magFilter!=r&&(o.texParameteri(He,10240,r),a.magFilter=r),a.minFilter!=n&&(o.texParameteri(He,10241,n),a.minFilter=n)}else{var h=o.createTexture();if(o.bindTexture(He,h),0<i){var l=this.clipTileContext_.canvas,u=this.clipTileContext_;this.clipTileCanvasWidth_!==e[0]||this.clipTileCanvasHeight_!==e[1]?(l.width=e[0],l.height=e[1],this.clipTileCanvasWidth_=e[0],this.clipTileCanvasHeight_=e[1]):u.clearRect(0,0,e[0],e[1]),u.drawImage(t.getImage(),i,i,e[0],e[1],0,0,e[0],e[1]),o.texImage2D(He,0,6408,6408,5121,l)}else o.texImage2D(He,0,6408,6408,5121,t.getImage());o.texParameteri(He,10240,r),o.texParameteri(He,10241,n),o.texParameteri(He,We,Ze),o.texParameteri(He,Ke,Ze),this.textureCache_.set(s,{texture:h,magFilter:r,minFilter:n})}},t.prototype.dispatchComposeEvent_=function(t,e){var i=this.getMap();if(i.hasListener(t)){var r=this.context_,n=e.extent,o=e.size,s=e.viewState,a=e.pixelRatio,h=s.resolution,l=s.center,u=s.rotation,c=new Ep(r,l,h,u,o,n,a),p=new Pl(t,c,e,null,r);i.dispatchEvent(p)}},t.prototype.disposeInternal=function(){var e=this.getGL();e.isContextLost()||this.textureCache_.forEach(function(t){t&&e.deleteTexture(t.texture)}),this.context_.dispose(),i.prototype.disposeInternal.call(this)},t.prototype.expireCache_=function(t,e){for(var i,r=this.getGL();1024<this.textureCache_.getCount()-this.textureCacheFrameMarkerCount_;){if(i=this.textureCache_.peekLast())r.deleteTexture(i.texture);else{if(+this.textureCache_.peekLastKey()==e.index)break;--this.textureCacheFrameMarkerCount_}this.textureCache_.pop()}},t.prototype.getContext=function(){return this.context_},t.prototype.getGL=function(){return this.gl_},t.prototype.getTileTextureQueue=function(){return this.tileTextureQueue_},t.prototype.handleWebGLContextLost=function(t){t.preventDefault(),this.textureCache_.clear(),this.textureCacheFrameMarkerCount_=0;var e=this.getLayerRenderers();for(var i in e){e[i].handleWebGLContextLost()}},t.prototype.handleWebGLContextRestored=function(){this.initializeGL_(),this.getMap().render()},t.prototype.initializeGL_=function(){var t=this.gl_;t.activeTexture(33984),t.blendFuncSeparate(770,771,1,771),t.disable(2884),t.disable(2929),t.disable(3089),t.disable(2960)},t.prototype.isTileTextureLoaded=function(t){return this.textureCache_.containsKey(t.getKey())},t.prototype.renderFrame=function(t){var e=this.getContext(),i=this.getGL();if(i.isContextLost())return!1;if(!t)return this.renderedVisible_&&(this.canvas_.style.display="none",this.renderedVisible_=!1),!1;this.focus_=t.focus,this.textureCache_.set((-t.index).toString(),null),++this.textureCacheFrameMarkerCount_,this.dispatchComposeEvent_(Tn,t);var r=[],n=t.layerStatesArray;_r(n,Dl);var o,s,a,h=t.viewState.resolution;for(o=0,s=n.length;o<s;++o)bs(a=n[o],h)&&a.sourceState==ms&&this.getLayerRenderer(a.layer).prepareFrame(t,a,e)&&r.push(a);var l=t.size[0]*t.pixelRatio,u=t.size[1]*t.pixelRatio;for(this.canvas_.width==l&&this.canvas_.height==u||(this.canvas_.width=l,this.canvas_.height=u),i.bindFramebuffer(qe,null),i.clearColor(0,0,0,0),i.clear(16384),i.enable(3042),i.viewport(0,0,this.canvas_.width,this.canvas_.height),o=0,s=r.length;o<s;++o)a=r[o],this.getLayerRenderer(a.layer).composeFrame(t,a,e);this.renderedVisible_||(this.canvas_.style.display="",this.renderedVisible_=!0),this.calculateMatrices2D(t),1024<this.textureCache_.getCount()-this.textureCacheFrameMarkerCount_&&t.postRenderFunctions.push(this.expireCache_.bind(this)),this.tileTextureQueue_.isEmpty()||(t.postRenderFunctions.push(this.loadNextTileTexture_),t.animate=!0),this.dispatchComposeEvent_(En,t),this.scheduleRemoveUnusedLayerRenderers(t),this.scheduleExpireIconCache(t)},t.prototype.forEachFeatureAtCoordinate=function(t,e,i,r,n,o,s){var a;if(this.getGL().isContextLost())return!1;var h,l=e.viewState,u=e.layerStatesArray;for(h=u.length-1;0<=h;--h){var c=u[h],p=c.layer;if(bs(c,l.resolution)&&o.call(s,p))if(a=this.getLayerRenderer(p).forEachFeatureAtCoordinate(t,e,i,r,n))return a}},t.prototype.hasFeatureAtCoordinate=function(t,e,i,r,n){var o=!1;if(this.getGL().isContextLost())return!1;var s,a=e.viewState,h=e.layerStatesArray;for(s=h.length-1;0<=s;--s){var l=h[s],u=l.layer;if(bs(l,a.resolution)&&r.call(n,u))if(o=this.getLayerRenderer(u).hasFeatureAtCoordinate(t,e))return!0}return o},t.prototype.forEachLayerAtPixel=function(t,e,i,r,n,o,s){if(this.getGL().isContextLost())return!1;var a,h,l=e.viewState,u=e.layerStatesArray;for(h=u.length-1;0<=h;--h){var c=u[h],p=c.layer;if(bs(c,l.resolution)&&o.call(n,p))if(a=this.getLayerRenderer(p).forEachLayerAtPixel(t,e,r,n))return a}},t}(Gl),Pp=new Ic("precision mediump float;\nvarying vec2 v_texCoord;\n\n\nuniform sampler2D u_texture;\n\nvoid main(void) {\n gl_FragColor = texture2D(u_texture, v_texCoord);\n}\n"),Fp=new Lc("varying vec2 v_texCoord;\n\n\nattribute vec2 a_position;\nattribute vec2 a_texCoord;\nuniform vec4 u_tileOffset;\n\nvoid main(void) {\n gl_Position = vec4(a_position * u_tileOffset.xy + u_tileOffset.zw, 0., 1.);\n v_texCoord = a_texCoord;\n}\n\n\n"),Mp=function(t,e){this.u_tileOffset=t.getUniformLocation(e,"u_tileOffset"),this.u_texture=t.getUniformLocation(e,"u_texture"),this.a_position=t.getAttribLocation(e,"a_position"),this.a_texCoord=t.getAttribLocation(e,"a_texCoord")},Op=function(i){function t(t,e){i.call(this,t,e),this.fragmentShader_=Pp,this.vertexShader_=Fp,this.locations_=null,this.renderArrayBuffer_=new Uc([0,0,0,1,1,0,1,1,0,1,0,0,1,1,1,0]),this.renderedTileRange_=null,this.renderedFramebufferExtent_=null,this.renderedRevision_=-1,this.tmpSize_=[0,0]}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.disposeInternal=function(){this.mapRenderer.getContext().deleteBuffer(this.renderArrayBuffer_),i.prototype.disposeInternal.call(this)},t.prototype.createLoadedTileFinder=function(e,r,n){var o=this.mapRenderer;return function(i,t){return e.forEachLoadedTile(r,i,t,function(t){var e=o.isTileTextureLoaded(t);return e&&(n[i]||(n[i]={}),n[i][t.tileCoord.toString()]=t),e})}},t.prototype.handleWebGLContextLost=function(){i.prototype.handleWebGLContextLost.call(this),this.locations_=null},t.prototype.prepareFrame=function(t,e,i){var r,n,o=this.mapRenderer,s=i.getGL(),a=t.viewState,h=a.projection,l=this.getLayer(),u=l.getSource(),c=u.getTileGridForProjection(h),p=c.getZForResolution(a.resolution),d=c.getResolution(p),f=u.getTilePixelSize(p,t.pixelRatio,h),_=f[0]/ws(c.getTileSize(p),this.tmpSize_)[0],g=d/_,y=u.getTilePixelRatio(_)*u.getGutter(h),v=a.center,m=t.extent,x=c.getTileRangeForExtentAndZ(m,p);if(this.renderedTileRange_&&this.renderedTileRange_.equals(x)&&this.renderedRevision_==u.getRevision())r=this.renderedFramebufferExtent_;else{var S=x.getSize(),C=Math.max(S[0]*f[0],S[1]*f[1]),E=(Z(0<(n=C),29),Math.pow(2,Math.ceil(Math.log(n)/Math.LN2))),T=g*E,w=c.getOrigin(p),R=w[0]+x.minX*f[0]*g,I=w[1]+x.minY*f[1]*g;r=[R,I,R+T,I+T],this.bindFramebuffer(t,E),s.viewport(0,0,E,E),s.clearColor(0,0,0,0),s.clear(16384),s.disable(3042);var L=i.getProgram(this.fragmentShader_,this.vertexShader_);i.useProgram(L),this.locations_||(this.locations_=new Mp(s,L)),i.bindBuffer(ze,this.renderArrayBuffer_),s.enableVertexAttribArray(this.locations_.a_position),s.vertexAttribPointer(this.locations_.a_position,2,Ve,!1,16,0),s.enableVertexAttribArray(this.locations_.a_texCoord),s.vertexAttribPointer(this.locations_.a_texCoord,2,Ve,!1,16,8),s.uniform1i(this.locations_.u_texture,0);var b={};b[p]={};var P,F,M,O,N,A,G=this.createLoadedTileFinder(u,h,b),k=l.getUseInterimTilesOnError(),D=!0,j=[1/0,1/0,-1/0,-1/0],U=new Vl(0,0,0,0);for(O=x.minX;O<=x.maxX;++O)for(N=x.minY;N<=x.maxY;++N)if(F=u.getTile(p,O,N,_,h),void 0===e.extent||wt(A=c.getTileCoordExtent(F.tileCoord,j),e.extent)){if((M=F.getState())==Gn||M==Dn||M==kn&&!k||(F=F.getInterimTile()),(M=F.getState())==Gn){if(o.isTileTextureLoaded(F)){b[p][F.tileCoord.toString()]=F;continue}}else if(M==Dn||M==kn&&!k)continue;D=!1,c.forEachTileCoordParentTileRange(F.tileCoord,G,null,U,j)||(P=c.getTileCoordChildTileRange(F.tileCoord,U,j))&&G(p+1,P)}var Y=Object.keys(b).map(Number);Y.sort(hr);for(var B=new Float32Array(4),X=0,z=Y.length;X<z;++X){var V=b[Y[X]];for(var W in V)F=V[W],A=c.getTileCoordExtent(F.tileCoord,j),B[0]=2*(A[2]-A[0])/T,B[1]=2*(A[3]-A[1])/T,B[2]=2*(A[0]-r[0])/T-1,B[3]=2*(A[1]-r[1])/T-1,s.uniform4fv(this.locations_.u_tileOffset,B),o.bindTileTexture(F,f,y*_,9729,9729),s.drawArrays(5,0,4)}D?(this.renderedTileRange_=x,this.renderedFramebufferExtent_=r,this.renderedRevision_=u.getRevision()):(this.renderedTileRange_=null,this.renderedFramebufferExtent_=null,this.renderedRevision_=-1,t.animate=!0)}this.updateUsedTiles(t.usedTiles,u,p,x);var K=o.getTileTextureQueue();this.manageTilePyramid(t,u,c,_,h,m,p,l.getPreload(),function(t){t.getState()!=Gn||o.isTileTextureLoaded(t)||K.isKeyQueued(t.getKey())||K.enqueue([t,c.getTileCoordCenter(t.tileCoord),c.getResolution(t.tileCoord[0]),f,y*_])},this),this.scheduleExpireCache(t,u);var H=this.texCoordMatrix;return ge(H),Ee(H,(Math.round(v[0]/d)*d-r[0])/(r[2]-r[0]),(Math.round(v[1]/d)*d-r[1])/(r[3]-r[1])),0!==a.rotation&&Se(H,a.rotation),Ce(H,t.size[0]*a.resolution/(r[2]-r[0]),t.size[1]*a.resolution/(r[3]-r[1])),Ee(H,-.5,-.5),!0},t.prototype.forEachLayerAtPixel=function(t,e,i,r){if(this.framebuffer){var n=[t[0]/e.size[0],(e.size[1]-t[1])/e.size[1]],o=xe(this.texCoordMatrix,n.slice()),s=[o[0]*this.framebufferDimension,o[1]*this.framebufferDimension],a=this.mapRenderer.getContext().getGL();a.bindFramebuffer(a.FRAMEBUFFER,this.framebuffer);var h=new Uint8Array(4);return a.readPixels(s[0],s[1],1,1,a.RGBA,a.UNSIGNED_BYTE,h),0<h[3]?i.call(r,this.getLayer(),h):void 0}},t}(Ip);Op.handles=function(t){return t.getType()===oh.TILE},Op.create=function(t,e){return new Op(t,e)};var Np=function(i){function t(t,e){i.call(this,t,e),this.dirty_=!1,this.renderedRevision_=-1,this.renderedResolution_=NaN,this.renderedExtent_=[1/0,1/0,-1/0,-1/0],this.renderedRenderOrder_=null,this.replayGroup_=null,this.layerState_=null}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.composeFrame=function(t,e,i){this.layerState_=e;var r=t.viewState,n=this.replayGroup_,o=t.size,s=t.pixelRatio,a=this.mapRenderer.getGL();n&&!n.isEmpty()&&(a.enable(a.SCISSOR_TEST),a.scissor(0,0,o[0]*s,o[1]*s),n.replay(i,r.center,r.resolution,r.rotation,o,s,e.opacity,e.managed?t.skippedFeatureUids:{}),a.disable(a.SCISSOR_TEST))},t.prototype.disposeInternal=function(){var t=this.replayGroup_;if(t){var e=this.mapRenderer.getContext();t.getDeleteResourcesFunction(e)(),this.replayGroup_=null}i.prototype.disposeInternal.call(this)},t.prototype.forEachFeatureAtCoordinate=function(t,e,i,r,n){if(this.replayGroup_&&this.layerState_){var o=this.mapRenderer.getContext(),s=e.viewState,a=this.getLayer(),h=this.layerState_,l={};return this.replayGroup_.forEachFeatureAtCoordinate(t,o,s.center,s.resolution,s.rotation,e.size,e.pixelRatio,h.opacity,{},function(t){var e=Et(t).toString();if(!(e in l))return l[e]=!0,r.call(n,t,a)})}},t.prototype.hasFeatureAtCoordinate=function(t,e){if(this.replayGroup_&&this.layerState_){var i=this.mapRenderer.getContext(),r=e.viewState,n=this.layerState_;return this.replayGroup_.hasFeatureAtCoordinate(t,i,r.center,r.resolution,r.rotation,e.size,e.pixelRatio,n.opacity,e.skippedFeatureUids)}return!1},t.prototype.forEachLayerAtPixel=function(t,e,i,r){var n=xe(e.pixelToCoordinateTransform,t.slice());return this.hasFeatureAtCoordinate(n,e)?i.call(r,this.getLayer(),null):void 0},t.prototype.handleStyleImageChange_=function(t){this.renderIfReadyAndVisible()},t.prototype.prepareFrame=function(t,e,i){var n=this.getLayer(),r=n.getSource(),o=t.viewHints[rs.ANIMATING],s=t.viewHints[rs.INTERACTING],a=n.getUpdateWhileAnimating(),h=n.getUpdateWhileInteracting();if(!this.dirty_&&!a&&o||!h&&s)return!0;var l=t.extent,u=t.viewState,c=u.projection,p=u.resolution,d=t.pixelRatio,f=n.getRevision(),_=n.getRenderBuffer(),g=n.getRenderOrder();void 0===g&&(g=bu);var y=G(l,_*p);if(!this.dirty_&&this.renderedResolution_==p&&this.renderedRevision_==f&&this.renderedRenderOrder_==g&&Q(this.renderedExtent_,y))return!0;this.replayGroup_&&t.postRenderFunctions.push(this.replayGroup_.getDeleteResourcesFunction(i)),this.dirty_=!1;var v=new Cp(Fu(p,d),y,n.getRenderBuffer());r.loadFeatures(y,p,c);var m=function(t){var e,i=t.getStyleFunction()||n.getStyleFunction();if(i&&(e=i(t,p)),e){var r=this.renderFeature(t,p,d,e,v);this.dirty_=this.dirty_||r}};if(g){var x=[];r.forEachFeatureInExtent(y,function(t){x.push(t)},this),x.sort(g),x.forEach(m.bind(this))}else r.forEachFeatureInExtent(y,m,this);return v.finish(i),this.renderedResolution_=p,this.renderedRevision_=f,this.renderedRenderOrder_=g,this.renderedExtent_=y,this.replayGroup_=v,!0},t.prototype.renderFeature=function(t,e,i,r,n){if(!r)return!1;var o=!1;if(Array.isArray(r))for(var s=r.length-1;0<=s;--s)o=Mu(n,t,r[s],Pu(e,i),this.handleStyleImageChange_,this)||o;else o=Mu(n,t,r,Pu(e,i),this.handleStyleImageChange_,this)||o;return o},t}(Ip);Np.handles=function(t){return t.getType()===oh.VECTOR},Np.create=function(t,e){return new Np(t,e)};var Ap=function(e){function t(t){(t=C({},t)).controls||(t.controls=As()),t.interactions||(t.interactions=Ll()),e.call(this,t)}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.createRenderer=function(){var t=new bp(this);return t.registerLayerRenderers([Lp,Op,Np]),t},t}(Rs),Gp="projection",kp="coordinateFormat",Dp=function(r){function t(t){var e=t||{},i=document.createElement("DIV");i.className=void 0!==e.className?e.className:"ol-mouse-position",r.call(this,{element:i,render:e.render||jp,target:e.target}),E(this,b(Gp),this.handleProjectionChanged_,this),e.coordinateFormat&&this.setCoordinateFormat(e.coordinateFormat),e.projection&&this.setProjection(e.projection),this.undefinedHTML_="undefinedHTML"in e?e.undefinedHTML:" ",this.renderOnMouseOut_=!!this.undefinedHTML_,this.renderedHTML_=i.innerHTML,this.mapProjection_=null,this.transform_=null,this.lastMouseMovePixel_=null}return r&&(t.__proto__=r),((t.prototype=Object.create(r&&r.prototype)).constructor=t).prototype.handleProjectionChanged_=function(){this.transform_=null},t.prototype.getCoordinateFormat=function(){return this.get(kp)},t.prototype.getProjection=function(){return this.get(Gp)},t.prototype.handleMouseMove=function(t){var e=this.getMap();this.lastMouseMovePixel_=e.getEventPixel(t),this.updateHTML_(this.lastMouseMovePixel_)},t.prototype.handleMouseOut=function(t){this.updateHTML_(null),this.lastMouseMovePixel_=null},t.prototype.setMap=function(t){if(r.prototype.setMap.call(this,t),t){var e=t.getViewport();this.listenerKeys.push(E(e,w.MOUSEMOVE,this.handleMouseMove,this)),this.renderOnMouseOut_&&this.listenerKeys.push(E(e,w.MOUSEOUT,this.handleMouseOut,this))}},t.prototype.setCoordinateFormat=function(t){this.set(kp,t)},t.prototype.setProjection=function(t){this.set(Gp,ne(t))},t.prototype.updateHTML_=function(t){var e=this.undefinedHTML_;if(t&&this.mapProjection_){if(!this.transform_){var i=this.getProjection();this.transform_=i?ce(this.mapProjection_,i):ie}var r=this.getMap().getCoordinateFromPixel(t);if(r){this.transform_(r,r);var n=this.getCoordinateFormat();e=n?n(r):r.toString()}}this.renderedHTML_&&e===this.renderedHTML_||(this.element.innerHTML=e,this.renderedHTML_=e)},t}(Is);function jp(t){var e=t.frameState;e?this.mapProjection_!=e.viewState.projection&&(this.mapProjection_=e.viewState.projection,this.transform_=null):this.mapProjection_=null,this.updateHTML_(this.lastMouseMovePixel_)}var Up=function(){this.dataProjection=null,this.defaultFeatureProjection=null};function Yp(t,e,i){var r,n=i?ne(i.featureProjection):null,o=i?ne(i.dataProjection):null;if(r=n&&o&&!ue(n,o)?t instanceof Ie?(e?t.clone():t).transform(e?n:o,e?o:n):fe(t,o,n):t,e&&i&&void 0!==i.decimals){var s=Math.pow(10,i.decimals);r===t&&(r=r.clone()),r.applyTransform(function(t){for(var e=0,i=t.length;e<i;++e)t[e]=Math.round(t[e]*s)/s;return t})}return r}Up.prototype.getReadOptions=function(t,e){var i;return e&&(i={dataProjection:e.dataProjection?e.dataProjection:this.readProjection(t),featureProjection:e.featureProjection}),this.adaptOptions(i)},Up.prototype.adaptOptions=function(t){return C({dataProjection:this.dataProjection,featureProjection:this.defaultFeatureProjection},t)},Up.prototype.getLastExtent=function(){return null},Up.prototype.getType=function(){},Up.prototype.readFeature=function(t,e){},Up.prototype.readFeatures=function(t,e){},Up.prototype.readGeometry=function(t,e){},Up.prototype.readProjection=function(t){},Up.prototype.writeFeature=function(t,e){},Up.prototype.writeFeatures=function(t,e){},Up.prototype.writeGeometry=function(t,e){};var Bp=function(t){function e(){t.call(this)}return t&&(e.__proto__=t),((e.prototype=Object.create(t&&t.prototype)).constructor=e).prototype.getType=function(){return uh.JSON},e.prototype.readFeature=function(t,e){return this.readFeatureFromObject(Xp(t),this.getReadOptions(t,e))},e.prototype.readFeatures=function(t,e){return this.readFeaturesFromObject(Xp(t),this.getReadOptions(t,e))},e.prototype.readFeatureFromObject=function(t,e){},e.prototype.readFeaturesFromObject=function(t,e){},e.prototype.readGeometry=function(t,e){return this.readGeometryFromObject(Xp(t),this.getReadOptions(t,e))},e.prototype.readGeometryFromObject=function(t,e){},e.prototype.readProjection=function(t){return this.readProjectionFromObject(Xp(t))},e.prototype.readProjectionFromObject=function(t){},e.prototype.writeFeature=function(t,e){return JSON.stringify(this.writeFeatureObject(t,e))},e.prototype.writeFeatureObject=function(t,e){},e.prototype.writeFeatures=function(t,e){return JSON.stringify(this.writeFeaturesObject(t,e))},e.prototype.writeFeaturesObject=function(t,e){},e.prototype.writeGeometry=function(t,e){return JSON.stringify(this.writeGeometryObject(t,e))},e.prototype.writeGeometryObject=function(t,e){},e}(Up);function Xp(t){if("string"==typeof t){var e=JSON.parse(t);return e||null}return null!==t?t:null}var zp={};zp[Lt.POINT]=function(t){var e;e=void 0!==t.m&&void 0!==t.z?new Dr([t.x,t.y,t.z,t.m],yr.XYZM):void 0!==t.z?new Dr([t.x,t.y,t.z],yr.XYZ):void 0!==t.m?new Dr([t.x,t.y,t.m],yr.XYM):new Dr([t.x,t.y]);return e},zp[Lt.LINE_STRING]=function(t){var e=Hp(t);return new Sn(t.paths[0],e)},zp[Lt.POLYGON]=function(t){var e=Hp(t);return new Qr(t.rings,e)},zp[Lt.MULTI_POINT]=function(t){var e=Hp(t);return new ih(t.points,e)},zp[Lt.MULTI_LINE_STRING]=function(t){var e=Hp(t);return new eh(t.paths,e)},zp[Lt.MULTI_POLYGON]=function(t){var e=Hp(t);return new nh(t.rings,e)};var Vp={};Vp[Lt.POINT]=function(t,e){var i,r=t.getCoordinates(),n=t.getLayout();n===yr.XYZ?i={x:r[0],y:r[1],z:r[2]}:n===yr.XYM?i={x:r[0],y:r[1],m:r[2]}:n===yr.XYZM?i={x:r[0],y:r[1],z:r[2],m:r[3]}:n===yr.XY?i={x:r[0],y:r[1]}:Z(!1,34);return i},Vp[Lt.LINE_STRING]=function(t,e){var i=Zp(t);return{hasZ:i.hasZ,hasM:i.hasM,paths:[t.getCoordinates()]}},Vp[Lt.POLYGON]=function(t,e){var i=Zp(t);return{hasZ:i.hasZ,hasM:i.hasM,rings:t.getCoordinates(!1)}},Vp[Lt.MULTI_POINT]=function(t,e){var i=Zp(t);return{hasZ:i.hasZ,hasM:i.hasM,points:t.getCoordinates()}},Vp[Lt.MULTI_LINE_STRING]=function(t,e){var i=Zp(t);return{hasZ:i.hasZ,hasM:i.hasM,paths:t.getCoordinates()}},Vp[Lt.MULTI_POLYGON]=function(t,e){for(var i=Zp(t),r=t.getCoordinates(!1),n=[],o=0;o<r.length;o++)for(var s=r[o].length-1;0<=s;s--)n.push(r[o][s]);return{hasZ:i.hasZ,hasM:i.hasM,rings:n}};var Wp=function(i){function t(t){var e=t||{};i.call(this),this.geometryName_=e.geometryName}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.readFeatureFromObject=function(t,e){var i=t,r=Kp(i.geometry,e),n=new Ji;return this.geometryName_&&n.setGeometryName(this.geometryName_),n.setGeometry(r),e&&e.idField&&i.attributes[e.idField]&&n.setId(i.attributes[e.idField]),i.attributes&&n.setProperties(i.attributes),n},t.prototype.readFeaturesFromObject=function(t,e){var i=e||{};if(t.features){var r=[],n=t.features;i.idField=t.objectIdFieldName;for(var o=0,s=n.length;o<s;++o)r.push(this.readFeatureFromObject(n[o],i));return r}return[this.readFeatureFromObject(t,i)]},t.prototype.readGeometryFromObject=function(t,e){return Kp(t,e)},t.prototype.readProjectionFromObject=function(t){var e=t;return e.spatialReference&&e.spatialReference.wkid?ne("EPSG:"+e.spatialReference.wkid):null},t.prototype.writeGeometryObject=function(t,e){return qp(t,this.adaptOptions(e))},t.prototype.writeFeatureObject=function(t,e){e=this.adaptOptions(e);var i={},r=t.getGeometry();r&&(i.geometry=qp(r,e),e&&e.featureProjection&&(i.geometry.spatialReference={wkid:ne(e.featureProjection).getCode().split(":").pop()}));var n=t.getProperties();return delete n[t.getGeometryName()],Tt(n)?i.attributes={}:i.attributes=n,i},t.prototype.writeFeaturesObject=function(t,e){e=this.adaptOptions(e);for(var i=[],r=0,n=t.length;r<n;++r)i.push(this.writeFeatureObject(t[r],e));return{features:i}},t}(Bp);function Kp(t,e){if(!t)return null;var i;if("number"==typeof t.x&&"number"==typeof t.y)i=Lt.POINT;else if(t.points)i=Lt.MULTI_POINT;else if(t.paths)i=1===t.paths.length?Lt.LINE_STRING:Lt.MULTI_LINE_STRING;else if(t.rings){var r=Hp(t),n=function(t,e){var i,r,n=[],o=[],s=[];for(i=0,r=t.length;i<r;++i){n.length=0,Lr(n,0,t[i],e.length);var a=Hr(n,0,n.length,e.length);a?o.push([t[i]]):s.push(t[i])}for(;s.length;){var h=s.shift(),l=!1;for(i=o.length-1;0<=i;i--){var u=o[i][0],c=Q(new kr(u).getExtent(),new kr(h).getExtent());if(c){o[i].push(h),l=!0;break}}l||o.push([h.reverse()])}return o}(t.rings,r);t=C({},t),1===n.length?(i=Lt.POLYGON,t.rings=n[0]):(i=Lt.MULTI_POLYGON,t.rings=n)}return Yp((0,zp[i])(t),!1,e)}function Hp(t){var e=yr.XY;return!0===t.hasZ&&!0===t.hasM?e=yr.XYZM:!0===t.hasZ?e=yr.XYZ:!0===t.hasM&&(e=yr.XYM),e}function Zp(t){var e=t.getLayout();return{hasZ:e===yr.XYZ||e===yr.XYZM,hasM:e===yr.XYM||e===yr.XYZM}}function qp(t,e){return(0,Vp[t.getType()])(Yp(t,!0,e),e)}var Jp=document.implementation.createDocument("","",null),Qp="http://www.w3.org/2001/XMLSchema-instance";function $p(t,e){return Jp.createElementNS(t,e)}function td(t,e){return function t(e,i,r){if(e.nodeType==Node.CDATA_SECTION_NODE||e.nodeType==Node.TEXT_NODE)i?r.push(String(e.nodeValue).replace(/(\r\n|\r|\n)/g,"")):r.push(e.nodeValue);else{var n;for(n=e.firstChild;n;n=n.nextSibling)t(n,i,r)}return r}(t,e,[]).join("")}function ed(t){return t instanceof Document}function id(t){return t instanceof Node}function rd(t){return(new DOMParser).parseFromString(t,"application/xml")}function nd(r,n){return function(t,e){var i=r.call(void 0!==n?n:this,t,e);void 0!==i&&pr(e[e.length-1],i)}}function od(r,n){return function(t,e){var i=r.call(void 0!==n?n:this,t,e);void 0!==i&&e[e.length-1].push(i)}}function sd(r,n){return function(t,e){var i=r.call(void 0!==n?n:this,t,e);void 0!==i&&(e[e.length-1]=i)}}function ad(o,s,a){return function(t,e){var i=o.call(void 0!==a?a:this,t,e);if(void 0!==i){var r=e[e.length-1],n=void 0!==s?s:t.localName;(n in r?r[n]:r[n]=[]).push(i)}}}function hd(r,n,o){return function(t,e){var i=r.call(void 0!==o?o:this,t,e);void 0!==i&&(e[e.length-1][void 0!==n?n:t.localName]=i)}}function ld(r,n){return function(t,e,i){r.call(void 0!==n?n:this,t,e,i),i[i.length-1].node.appendChild(t)}}function ud(n,t){var o,s;return function(t,e,i){if(void 0===o){o={};var r={};r[t.localName]=n,o[t.namespaceURI]=r,s=cd(t.localName)}yd(o,s,e,i)}}function cd(t,o){var s=t;return function(t,e,i){var r=e[e.length-1].node,n=s;return void 0===n&&(n=i),$p(void 0!==o?o:r.namespaceURI,n)}}var pd=cd();function dd(t,e){for(var i=e.length,r=new Array(i),n=0;n<i;++n)r[n]=t[e[n]];return r}function fd(t,e,i){var r,n,o=void 0!==i?i:{};for(r=0,n=t.length;r<n;++r)o[t[r]]=e;return o}function _d(t,e,i,r){var n;for(n=e.firstElementChild;n;n=n.nextElementSibling){var o=t[n.namespaceURI];if(void 0!==o){var s=o[n.localName];void 0!==s&&s.call(r,n,i)}}}function gd(t,e,i,r,n){return r.push(t),_d(e,i,r,n),r.pop()}function yd(t,e,i,r,n,o){for(var s,a,h=(void 0!==n?n:i).length,l=0;l<h;++l)void 0!==(s=i[l])&&void 0!==(a=e.call(void 0!==o?o:this,s,r,void 0!==n?n[l]:void 0))&&t[a.namespaceURI][a.localName].call(o,a,s,r)}function vd(t,e,i,r,n,o,s){return n.push(t),yd(e,i,r,n,o,s),n.pop()}var md=function(t){function e(){t.call(this),this.xmlSerializer_=new XMLSerializer}return t&&(e.__proto__=t),((e.prototype=Object.create(t&&t.prototype)).constructor=e).prototype.getType=function(){return uh.XML},e.prototype.readFeature=function(t,e){if(ed(t))return this.readFeatureFromDocument(t,e);if(id(t))return this.readFeatureFromNode(t,e);if("string"==typeof t){var i=rd(t);return this.readFeatureFromDocument(i,e)}return null},e.prototype.readFeatureFromDocument=function(t,e){var i=this.readFeaturesFromDocument(t,e);return 0<i.length?i[0]:null},e.prototype.readFeatureFromNode=function(t,e){return null},e.prototype.readFeatures=function(t,e){if(ed(t))return this.readFeaturesFromDocument(t,e);if(id(t))return this.readFeaturesFromNode(t,e);if("string"==typeof t){var i=rd(t);return this.readFeaturesFromDocument(i,e)}return[]},e.prototype.readFeaturesFromDocument=function(t,e){for(var i=[],r=t.firstChild;r;r=r.nextSibling)r.nodeType==Node.ELEMENT_NODE&&pr(i,this.readFeaturesFromNode(r,e));return i},e.prototype.readFeaturesFromNode=function(t,e){},e.prototype.readGeometry=function(t,e){if(ed(t))return this.readGeometryFromDocument(t,e);if(id(t))return this.readGeometryFromNode(t,e);if("string"==typeof t){var i=rd(t);return this.readGeometryFromDocument(i,e)}return null},e.prototype.readGeometryFromDocument=function(t,e){return null},e.prototype.readGeometryFromNode=function(t,e){return null},e.prototype.readProjection=function(t){if(ed(t))return this.readProjectionFromDocument(t);if(id(t))return this.readProjectionFromNode(t);if("string"==typeof t){var e=rd(t);return this.readProjectionFromDocument(e)}return null},e.prototype.readProjectionFromDocument=function(t){return this.dataProjection},e.prototype.readProjectionFromNode=function(t){return this.dataProjection},e.prototype.writeFeature=function(t,e){var i=this.writeFeatureNode(t,e);return this.xmlSerializer_.serializeToString(i)},e.prototype.writeFeatureNode=function(t,e){return null},e.prototype.writeFeatures=function(t,e){var i=this.writeFeaturesNode(t,e);return this.xmlSerializer_.serializeToString(i)},e.prototype.writeFeaturesNode=function(t,e){return null},e.prototype.writeGeometry=function(t,e){var i=this.writeGeometryNode(t,e);return this.xmlSerializer_.serializeToString(i)},e.prototype.writeGeometryNode=function(t,e){return null},e}(Up),xd="http://www.opengis.net/gml",Sd=/^[\s\xa0]*$/,Cd=function(i){function t(t){i.call(this);var e=t||{};this.featureType=e.featureType,this.featureNS=e.featureNS,this.srsName=e.srsName,this.schemaLocation="",this.FEATURE_COLLECTION_PARSERS={},this.FEATURE_COLLECTION_PARSERS[xd]={featureMember:sd(this.readFeaturesInternal),featureMembers:sd(this.readFeaturesInternal)}}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.readFeaturesInternal=function(t,e){var i=t.localName,r=null;if("FeatureCollection"==i)r="http://www.opengis.net/wfs"===t.namespaceURI?gd([],this.FEATURE_COLLECTION_PARSERS,t,e,this):gd(null,this.FEATURE_COLLECTION_PARSERS,t,e,this);else if("featureMembers"==i||"featureMember"==i){var n=e[0],o=n.featureType,s=n.featureNS;if(!o&&t.childNodes){o=[],s={};for(var a=0,h=t.childNodes.length;a<h;++a){var l=t.childNodes[a];if(1===l.nodeType){var u=l.nodeName.split(":").pop();if(-1===o.indexOf(u)){var c="",p=0,d=l.namespaceURI;for(var f in s){if(s[f]===d){c=f;break}++p}c||(s[c="p"+p]=d),o.push(c+":"+u)}}}"featureMember"!=i&&(n.featureType=o,n.featureNS=s)}if("string"==typeof s){var _=s;(s={}).p0=_}var g={},y=Array.isArray(o)?o:[o];for(var v in s){for(var m={},x=0,S=y.length;x<S;++x){(-1===y[x].indexOf(":")?"p0":y[x].split(":")[0])===v&&(m[y[x].split(":").pop()]="featureMembers"==i?od(this.readFeatureElement,this):sd(this.readFeatureElement,this))}g[s[v]]=m}r=gd("featureMember"==i?void 0:[],g,t,e)}return null===r&&(r=[]),r},t.prototype.readGeometryElement=function(t,e){var i=e[0];i.srsName=t.firstElementChild.getAttribute("srsName"),i.srsDimension=t.firstElementChild.getAttribute("srsDimension");var r=gd(null,this.GEOMETRY_PARSERS_,t,e,this);return r?Yp(r,!1,i):void 0},t.prototype.readFeatureElement=function(t,e){var i,r,n,o,s=t.getAttribute("fid")||(r=xd,n="id",t.getAttributeNS(r,n)||""),a={};for(i=t.firstElementChild;i;i=i.nextElementSibling){var h=i.localName;if(0===i.childNodes.length||1===i.childNodes.length&&(3===i.firstChild.nodeType||4===i.firstChild.nodeType)){var l=td(i,!1);Sd.test(l)&&(l=void 0),a[h]=l}else"boundedBy"!==h&&(o=h),a[h]=this.readGeometryElement(i,e)}var u=new Ji(a);return o&&u.setGeometryName(o),s&&u.setId(s),u},t.prototype.readPoint=function(t,e){var i=this.readFlatCoordinatesFromNode_(t,e);if(i)return new Dr(i,yr.XYZ)},t.prototype.readMultiPoint=function(t,e){var i=gd([],this.MULTIPOINT_PARSERS_,t,e,this);return i?new ih(i):void 0},t.prototype.readMultiLineString=function(t,e){var i=gd([],this.MULTILINESTRING_PARSERS_,t,e,this);if(i)return new eh(i)},t.prototype.readMultiPolygon=function(t,e){var i=gd([],this.MULTIPOLYGON_PARSERS_,t,e,this);if(i)return new nh(i)},t.prototype.pointMemberParser_=function(t,e){_d(this.POINTMEMBER_PARSERS_,t,e,this)},t.prototype.lineStringMemberParser_=function(t,e){_d(this.LINESTRINGMEMBER_PARSERS_,t,e,this)},t.prototype.polygonMemberParser_=function(t,e){_d(this.POLYGONMEMBER_PARSERS_,t,e,this)},t.prototype.readLineString=function(t,e){var i=this.readFlatCoordinatesFromNode_(t,e);return i?new Sn(i,yr.XYZ):void 0},t.prototype.readFlatLinearRing_=function(t,e){var i=gd(null,this.GEOMETRY_FLAT_COORDINATES_PARSERS_,t,e,this);return i||void 0},t.prototype.readLinearRing=function(t,e){var i=this.readFlatCoordinatesFromNode_(t,e);if(i)return new kr(i,yr.XYZ)},t.prototype.readPolygon=function(t,e){var i=gd([null],this.FLAT_LINEAR_RINGS_PARSERS_,t,e,this);if(i&&i[0]){var r,n,o=i[0],s=[o.length];for(r=1,n=i.length;r<n;++r)pr(o,i[r]),s.push(o.length);return new Qr(o,yr.XYZ,s)}},t.prototype.readFlatCoordinatesFromNode_=function(t,e){return gd(null,this.GEOMETRY_FLAT_COORDINATES_PARSERS_,t,e,this)},t.prototype.readGeometryFromNode=function(t,e){var i=this.readGeometryElement(t,[this.getReadOptions(t,e||{})]);return i||null},t.prototype.readFeaturesFromNode=function(t,e){var i={featureType:this.featureType,featureNS:this.featureNS};return e&&C(i,this.getReadOptions(t,e)),this.readFeaturesInternal(t,[i])||[]},t.prototype.readProjectionFromNode=function(t){return ne(this.srsName?this.srsName:t.firstElementChild.getAttribute("srsName"))},t}(md);function Ed(t){return Td(td(t,!1))}function Td(t){var e=/^\s*(true|1)|(false|0)\s*$/.exec(t);return e?void 0!==e[1]||!1:void 0}function wd(t){var e=td(t,!1),i=Date.parse(e);return isNaN(i)?void 0:i/1e3}function Rd(t){return Id(td(t,!1))}function Id(t){var e=/^\s*([+\-]?\d*\.?\d+(?:e[+\-]?\d+)?)\s*$/i.exec(t);return e?parseFloat(e[1]):void 0}function Ld(t){return bd(td(t,!1))}function bd(t){var e=/^\s*(\d+)\s*$/.exec(t);return e?parseInt(e[1],10):void 0}function Pd(t){return td(t,!1).trim()}function Fd(t,e){Nd(t,e?"1":"0")}function Md(t,e){var i=e.toPrecision();t.appendChild(Jp.createTextNode(i))}function Od(t,e){var i=e.toString();t.appendChild(Jp.createTextNode(i))}function Nd(t,e){t.appendChild(Jp.createTextNode(e))}Cd.prototype.MULTIPOINT_PARSERS_={"http://www.opengis.net/gml":{pointMember:od(Cd.prototype.pointMemberParser_),pointMembers:od(Cd.prototype.pointMemberParser_)}},Cd.prototype.MULTILINESTRING_PARSERS_={"http://www.opengis.net/gml":{lineStringMember:od(Cd.prototype.lineStringMemberParser_),lineStringMembers:od(Cd.prototype.lineStringMemberParser_)}},Cd.prototype.MULTIPOLYGON_PARSERS_={"http://www.opengis.net/gml":{polygonMember:od(Cd.prototype.polygonMemberParser_),polygonMembers:od(Cd.prototype.polygonMemberParser_)}},Cd.prototype.POINTMEMBER_PARSERS_={"http://www.opengis.net/gml":{Point:od(Cd.prototype.readFlatCoordinatesFromNode_)}},Cd.prototype.LINESTRINGMEMBER_PARSERS_={"http://www.opengis.net/gml":{LineString:od(Cd.prototype.readLineString)}},Cd.prototype.POLYGONMEMBER_PARSERS_={"http://www.opengis.net/gml":{Polygon:od(Cd.prototype.readPolygon)}},Cd.prototype.RING_PARSERS={"http://www.opengis.net/gml":{LinearRing:sd(Cd.prototype.readFlatLinearRing_)}};var Ad=xd+" http://schemas.opengis.net/gml/3.1.1/profiles/gmlsfProfile/1.0.0/gmlsf.xsd",Gd={MultiLineString:"lineStringMember",MultiCurve:"curveMember",MultiPolygon:"polygonMember",MultiSurface:"surfaceMember"},kd=function(i){function t(t){var e=t||{};i.call(this,e),this.surface_=void 0!==e.surface&&e.surface,this.curve_=void 0!==e.curve&&e.curve,this.multiCurve_=void 0===e.multiCurve||e.multiCurve,this.multiSurface_=void 0===e.multiSurface||e.multiSurface,this.schemaLocation=e.schemaLocation?e.schemaLocation:Ad,this.hasZ=void 0!==e.hasZ&&e.hasZ}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.readMultiCurve_=function(t,e){var i=gd([],this.MULTICURVE_PARSERS_,t,e,this);return i?new eh(i):void 0},t.prototype.readMultiSurface_=function(t,e){var i=gd([],this.MULTISURFACE_PARSERS_,t,e,this);if(i)return new nh(i)},t.prototype.curveMemberParser_=function(t,e){_d(this.CURVEMEMBER_PARSERS_,t,e,this)},t.prototype.surfaceMemberParser_=function(t,e){_d(this.SURFACEMEMBER_PARSERS_,t,e,this)},t.prototype.readPatch_=function(t,e){return gd([null],this.PATCHES_PARSERS_,t,e,this)},t.prototype.readSegment_=function(t,e){return gd([null],this.SEGMENTS_PARSERS_,t,e,this)},t.prototype.readPolygonPatch_=function(t,e){return gd([null],this.FLAT_LINEAR_RINGS_PARSERS_,t,e,this)},t.prototype.readLineStringSegment_=function(t,e){return gd([null],this.GEOMETRY_FLAT_COORDINATES_PARSERS_,t,e,this)},t.prototype.interiorParser_=function(t,e){var i=gd(void 0,this.RING_PARSERS,t,e,this);i&&e[e.length-1].push(i)},t.prototype.exteriorParser_=function(t,e){var i=gd(void 0,this.RING_PARSERS,t,e,this);i&&(e[e.length-1][0]=i)},t.prototype.readSurface_=function(t,e){var i=gd([null],this.SURFACE_PARSERS_,t,e,this);if(i&&i[0]){var r,n,o=i[0],s=[o.length];for(r=1,n=i.length;r<n;++r)pr(o,i[r]),s.push(o.length);return new Qr(o,yr.XYZ,s)}},t.prototype.readCurve_=function(t,e){var i=gd([null],this.CURVE_PARSERS_,t,e,this);return i?new Sn(i,yr.XYZ):void 0},t.prototype.readEnvelope_=function(t,e){var i=gd([null],this.ENVELOPE_PARSERS_,t,e,this);return X(i[1][0],i[1][1],i[2][0],i[2][1])},t.prototype.readFlatPos_=function(t,e){for(var i,r=td(t,!1),n=/^\s*([+\-]?\d*\.?\d+(?:[eE][+\-]?\d+)?)\s*/,o=[];i=n.exec(r);)o.push(parseFloat(i[1])),r=r.substr(i[0].length);if(""===r){var s,a,h=e[0].srsName,l="enu";if(h)l=ne(h).getAxisOrientation();if("neu"===l)for(s=0,a=o.length;s<a;s+=3){var u=o[s],c=o[s+1];o[s]=c,o[s+1]=u}var p=o.length;if(2==p&&o.push(0),0!==p)return o}},t.prototype.readFlatPosList_=function(t,e){var i=td(t,!1).replace(/^\s*|\s*$/g,""),r=e[0],n=r.srsName,o=r.srsDimension,s="enu";n&&(s=ne(n).getAxisOrientation());var a,h,l,u=i.split(/\s+/),c=2;t.getAttribute("srsDimension")?c=bd(t.getAttribute("srsDimension")):t.getAttribute("dimension")?c=bd(t.getAttribute("dimension")):t.parentNode.getAttribute("srsDimension")?c=bd(t.parentNode.getAttribute("srsDimension")):o&&(c=bd(o));for(var p=[],d=0,f=u.length;d<f;d+=c)a=parseFloat(u[d]),h=parseFloat(u[d+1]),l=3===c?parseFloat(u[d+2]):0,"en"===s.substr(0,2)?p.push(a,h,l):p.push(h,a,l);return p},t.prototype.writePos_=function(t,e,i){var r=i[i.length-1],n=r.hasZ,o=n?3:2;t.setAttribute("srsDimension",o);var s=r.srsName,a="enu";s&&(a=ne(s).getAxisOrientation());var h,l=e.getCoordinates();(h="en"===a.substr(0,2)?l[0]+" "+l[1]:l[1]+" "+l[0],n)&&(h+=" "+(l[2]||0));Nd(t,h)},t.prototype.getCoords_=function(t,e,i){var r="enu";e&&(r=ne(e).getAxisOrientation());var n="en"===r.substr(0,2)?t[0]+" "+t[1]:t[1]+" "+t[0];i&&(n+=" "+(t[2]||0));return n},t.prototype.writePosList_=function(t,e,i){var r=i[i.length-1],n=r.hasZ,o=n?3:2;t.setAttribute("srsDimension",o);for(var s,a=r.srsName,h=e.getCoordinates(),l=h.length,u=new Array(l),c=0;c<l;++c)s=h[c],u[c]=this.getCoords_(s,a,n);Nd(t,u.join(" "))},t.prototype.writePoint_=function(t,e,i){var r=i[i.length-1].srsName;r&&t.setAttribute("srsName",r);var n=$p(t.namespaceURI,"pos");t.appendChild(n),this.writePos_(n,e,i)},t.prototype.writeEnvelope=function(t,e,i){var r=i[i.length-1].srsName;r&&t.setAttribute("srsName",r);var n=[e[0]+" "+e[1],e[2]+" "+e[3]];vd({node:t},this.ENVELOPE_SERIALIZERS_,pd,n,i,["lowerCorner","upperCorner"],this)},t.prototype.writeLinearRing_=function(t,e,i){var r=i[i.length-1].srsName;r&&t.setAttribute("srsName",r);var n=$p(t.namespaceURI,"posList");t.appendChild(n),this.writePosList_(n,e,i)},t.prototype.RING_NODE_FACTORY_=function(t,e,i){var r=e[e.length-1],n=r.node,o=r.exteriorWritten;return void 0===o&&(r.exteriorWritten=!0),$p(n.namespaceURI,void 0!==o?"interior":"exterior")},t.prototype.writeSurfaceOrPolygon_=function(t,e,i){var r=i[i.length-1],n=r.hasZ,o=r.srsName;if("PolygonPatch"!==t.nodeName&&o&&t.setAttribute("srsName",o),"Polygon"===t.nodeName||"PolygonPatch"===t.nodeName){var s=e.getLinearRings();vd({node:t,hasZ:n,srsName:o},this.RING_SERIALIZERS_,this.RING_NODE_FACTORY_,s,i,void 0,this)}else if("Surface"===t.nodeName){var a=$p(t.namespaceURI,"patches");t.appendChild(a),this.writeSurfacePatches_(a,e,i)}},t.prototype.writeCurveOrLineString_=function(t,e,i){var r=i[i.length-1].srsName;if("LineStringSegment"!==t.nodeName&&r&&t.setAttribute("srsName",r),"LineString"===t.nodeName||"LineStringSegment"===t.nodeName){var n=$p(t.namespaceURI,"posList");t.appendChild(n),this.writePosList_(n,e,i)}else if("Curve"===t.nodeName){var o=$p(t.namespaceURI,"segments");t.appendChild(o),this.writeCurveSegments_(o,e,i)}},t.prototype.writeMultiSurfaceOrPolygon_=function(t,e,i){var r=i[i.length-1],n=r.hasZ,o=r.srsName,s=r.surface;o&&t.setAttribute("srsName",o);var a=e.getPolygons();vd({node:t,hasZ:n,srsName:o,surface:s},this.SURFACEORPOLYGONMEMBER_SERIALIZERS_,this.MULTIGEOMETRY_MEMBER_NODE_FACTORY_,a,i,void 0,this)},t.prototype.writeMultiPoint_=function(t,e,i){var r=i[i.length-1],n=r.srsName,o=r.hasZ;n&&t.setAttribute("srsName",n);var s=e.getPoints();vd({node:t,hasZ:o,srsName:n},this.POINTMEMBER_SERIALIZERS_,cd("pointMember"),s,i,void 0,this)},t.prototype.writeMultiCurveOrLineString_=function(t,e,i){var r=i[i.length-1],n=r.hasZ,o=r.srsName,s=r.curve;o&&t.setAttribute("srsName",o);var a=e.getLineStrings();vd({node:t,hasZ:n,srsName:o,curve:s},this.LINESTRINGORCURVEMEMBER_SERIALIZERS_,this.MULTIGEOMETRY_MEMBER_NODE_FACTORY_,a,i,void 0,this)},t.prototype.writeRing_=function(t,e,i){var r=$p(t.namespaceURI,"LinearRing");t.appendChild(r),this.writeLinearRing_(r,e,i)},t.prototype.writeSurfaceOrPolygonMember_=function(t,e,i){var r=this.GEOMETRY_NODE_FACTORY_(e,i);r&&(t.appendChild(r),this.writeSurfaceOrPolygon_(r,e,i))},t.prototype.writePointMember_=function(t,e,i){var r=$p(t.namespaceURI,"Point");t.appendChild(r),this.writePoint_(r,e,i)},t.prototype.writeLineStringOrCurveMember_=function(t,e,i){var r=this.GEOMETRY_NODE_FACTORY_(e,i);r&&(t.appendChild(r),this.writeCurveOrLineString_(r,e,i))},t.prototype.writeSurfacePatches_=function(t,e,i){var r=$p(t.namespaceURI,"PolygonPatch");t.appendChild(r),this.writeSurfaceOrPolygon_(r,e,i)},t.prototype.writeCurveSegments_=function(t,e,i){var r=$p(t.namespaceURI,"LineStringSegment");t.appendChild(r),this.writeCurveOrLineString_(r,e,i)},t.prototype.writeGeometryElement=function(t,e,i){var r,n=i[i.length-1],o=C({},n);o.node=t,r=Array.isArray(e)?n.dataProjection?fe(e,n.featureProjection,n.dataProjection):e:Yp(e,!0,n),vd(o,this.GEOMETRY_SERIALIZERS_,this.GEOMETRY_NODE_FACTORY_,[r],i,void 0,this)},t.prototype.writeFeatureElement=function(t,e,i){var r=e.getId();r&&t.setAttribute("fid",r);var n=i[i.length-1],o=n.featureNS,s=e.getGeometryName();n.serializers||(n.serializers={},n.serializers[o]={});var a=e.getProperties(),h=[],l=[];for(var u in a){var c=a[u];null!==c&&(h.push(u),l.push(c),u==s||c instanceof Ie?u in n.serializers[o]||(n.serializers[o][u]=ld(this.writeGeometryElement,this)):u in n.serializers[o]||(n.serializers[o][u]=ld(Nd)))}var p=C({},n);p.node=t,vd(p,n.serializers,cd(void 0,o),l,i,h)},t.prototype.writeFeatureMembers_=function(t,e,i){var r=i[i.length-1],n=r.featureType,o=r.featureNS,s={};s[o]={},s[o][n]=ld(this.writeFeatureElement,this);var a=C({},r);a.node=t,vd(a,s,cd(n,o),e,i)},t.prototype.MULTIGEOMETRY_MEMBER_NODE_FACTORY_=function(t,e,i){var r=e[e.length-1].node;return $p("http://www.opengis.net/gml",Gd[r.nodeName])},t.prototype.GEOMETRY_NODE_FACTORY_=function(t,e,i){var r,n=e[e.length-1],o=n.multiSurface,s=n.surface,a=n.curve,h=n.multiCurve;return Array.isArray(t)?r="Envelope":"MultiPolygon"===(r=t.getType())&&!0===o?r="MultiSurface":"Polygon"===r&&!0===s?r="Surface":"LineString"===r&&!0===a?r="Curve":"MultiLineString"===r&&!0===h&&(r="MultiCurve"),$p("http://www.opengis.net/gml",r)},t.prototype.writeGeometryNode=function(t,e){e=this.adaptOptions(e);var i=$p("http://www.opengis.net/gml","geom"),r={node:i,hasZ:this.hasZ,srsName:this.srsName,curve:this.curve_,surface:this.surface_,multiSurface:this.multiSurface_,multiCurve:this.multiCurve_};return e&&C(r,e),this.writeGeometryElement(i,t,[r]),i},t.prototype.writeFeaturesNode=function(t,e){e=this.adaptOptions(e);var i=$p("http://www.opengis.net/gml","featureMembers");i.setAttributeNS(Qp,"xsi:schemaLocation",this.schemaLocation);var r={srsName:this.srsName,hasZ:this.hasZ,curve:this.curve_,surface:this.surface_,multiSurface:this.multiSurface_,multiCurve:this.multiCurve_,featureNS:this.featureNS,featureType:this.featureType};return e&&C(r,e),this.writeFeatureMembers_(i,t,[r]),i},t}(Cd);kd.prototype.GEOMETRY_FLAT_COORDINATES_PARSERS_={"http://www.opengis.net/gml":{pos:sd(kd.prototype.readFlatPos_),posList:sd(kd.prototype.readFlatPosList_)}},kd.prototype.FLAT_LINEAR_RINGS_PARSERS_={"http://www.opengis.net/gml":{interior:kd.prototype.interiorParser_,exterior:kd.prototype.exteriorParser_}},kd.prototype.GEOMETRY_PARSERS_={"http://www.opengis.net/gml":{Point:sd(Cd.prototype.readPoint),MultiPoint:sd(Cd.prototype.readMultiPoint),LineString:sd(Cd.prototype.readLineString),MultiLineString:sd(Cd.prototype.readMultiLineString),LinearRing:sd(Cd.prototype.readLinearRing),Polygon:sd(Cd.prototype.readPolygon),MultiPolygon:sd(Cd.prototype.readMultiPolygon),Surface:sd(kd.prototype.readSurface_),MultiSurface:sd(kd.prototype.readMultiSurface_),Curve:sd(kd.prototype.readCurve_),MultiCurve:sd(kd.prototype.readMultiCurve_),Envelope:sd(kd.prototype.readEnvelope_)}},kd.prototype.MULTICURVE_PARSERS_={"http://www.opengis.net/gml":{curveMember:od(kd.prototype.curveMemberParser_),curveMembers:od(kd.prototype.curveMemberParser_)}},kd.prototype.MULTISURFACE_PARSERS_={"http://www.opengis.net/gml":{surfaceMember:od(kd.prototype.surfaceMemberParser_),surfaceMembers:od(kd.prototype.surfaceMemberParser_)}},kd.prototype.CURVEMEMBER_PARSERS_={"http://www.opengis.net/gml":{LineString:od(Cd.prototype.readLineString),Curve:od(kd.prototype.readCurve_)}},kd.prototype.SURFACEMEMBER_PARSERS_={"http://www.opengis.net/gml":{Polygon:od(Cd.prototype.readPolygon),Surface:od(kd.prototype.readSurface_)}},kd.prototype.SURFACE_PARSERS_={"http://www.opengis.net/gml":{patches:sd(kd.prototype.readPatch_)}},kd.prototype.CURVE_PARSERS_={"http://www.opengis.net/gml":{segments:sd(kd.prototype.readSegment_)}},kd.prototype.ENVELOPE_PARSERS_={"http://www.opengis.net/gml":{lowerCorner:od(kd.prototype.readFlatPosList_),upperCorner:od(kd.prototype.readFlatPosList_)}},kd.prototype.PATCHES_PARSERS_={"http://www.opengis.net/gml":{PolygonPatch:sd(kd.prototype.readPolygonPatch_)}},kd.prototype.SEGMENTS_PARSERS_={"http://www.opengis.net/gml":{LineStringSegment:sd(kd.prototype.readLineStringSegment_)}},kd.prototype.writeFeatures,kd.prototype.RING_SERIALIZERS_={"http://www.opengis.net/gml":{exterior:ld(kd.prototype.writeRing_),interior:ld(kd.prototype.writeRing_)}},kd.prototype.ENVELOPE_SERIALIZERS_={"http://www.opengis.net/gml":{lowerCorner:ld(Nd),upperCorner:ld(Nd)}},kd.prototype.SURFACEORPOLYGONMEMBER_SERIALIZERS_={"http://www.opengis.net/gml":{surfaceMember:ld(kd.prototype.writeSurfaceOrPolygonMember_),polygonMember:ld(kd.prototype.writeSurfaceOrPolygonMember_)}},kd.prototype.POINTMEMBER_SERIALIZERS_={"http://www.opengis.net/gml":{pointMember:ld(kd.prototype.writePointMember_)}},kd.prototype.LINESTRINGORCURVEMEMBER_SERIALIZERS_={"http://www.opengis.net/gml":{lineStringMember:ld(kd.prototype.writeLineStringOrCurveMember_),curveMember:ld(kd.prototype.writeLineStringOrCurveMember_)}},kd.prototype.GEOMETRY_SERIALIZERS_={"http://www.opengis.net/gml":{Curve:ld(kd.prototype.writeCurveOrLineString_),MultiCurve:ld(kd.prototype.writeMultiCurveOrLineString_),Point:ld(kd.prototype.writePoint_),MultiPoint:ld(kd.prototype.writeMultiPoint_),LineString:ld(kd.prototype.writeCurveOrLineString_),MultiLineString:ld(kd.prototype.writeMultiCurveOrLineString_),LinearRing:ld(kd.prototype.writeLinearRing_),Polygon:ld(kd.prototype.writeSurfaceOrPolygon_),MultiPolygon:ld(kd.prototype.writeMultiSurfaceOrPolygon_),Surface:ld(kd.prototype.writeSurfaceOrPolygon_),MultiSurface:ld(kd.prototype.writeMultiSurfaceOrPolygon_),Envelope:ld(kd.prototype.writeEnvelope)}};var Dd=kd;Dd.prototype.writeFeatures,Dd.prototype.writeFeaturesNode;var jd=xd+" http://schemas.opengis.net/gml/2.1.2/feature.xsd",Ud={MultiLineString:"lineStringMember",MultiCurve:"curveMember",MultiPolygon:"polygonMember",MultiSurface:"surfaceMember"},Yd=function(i){function t(t){var e=t||{};i.call(this,e),this.FEATURE_COLLECTION_PARSERS[xd].featureMember=od(this.readFeaturesInternal),this.schemaLocation=e.schemaLocation?e.schemaLocation:jd}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.readFlatCoordinates_=function(t,e){var i=td(t,!1).replace(/^\s*|\s*$/g,""),r=e[0].srsName,n="enu";if(r){var o=ne(r);o&&(n=o.getAxisOrientation())}for(var s=i.trim().split(/\s+/),a=[],h=0,l=s.length;h<l;h++){var u=s[h].split(/,+/),c=parseFloat(u[0]),p=parseFloat(u[1]),d=3===u.length?parseFloat(u[2]):0;"en"===n.substr(0,2)?a.push(c,p,d):a.push(p,c,d)}return a},t.prototype.readBox_=function(t,e){var i=gd([null],this.BOX_PARSERS_,t,e,this);return X(i[1][0],i[1][1],i[1][3],i[1][4])},t.prototype.innerBoundaryIsParser_=function(t,e){var i=gd(void 0,this.RING_PARSERS,t,e,this);i&&e[e.length-1].push(i)},t.prototype.outerBoundaryIsParser_=function(t,e){var i=gd(void 0,this.RING_PARSERS,t,e,this);i&&(e[e.length-1][0]=i)},t.prototype.GEOMETRY_NODE_FACTORY_=function(t,e,i){var r,n=e[e.length-1],o=n.multiSurface,s=n.surface,a=n.multiCurve;return Array.isArray(t)?r="Envelope":"MultiPolygon"===(r=t.getType())&&!0===o?r="MultiSurface":"Polygon"===r&&!0===s?r="Surface":"MultiLineString"===r&&!0===a&&(r="MultiCurve"),$p("http://www.opengis.net/gml",r)},t.prototype.writeFeatureElement=function(t,e,i){var r=e.getId();r&&t.setAttribute("fid",r);var n=i[i.length-1],o=n.featureNS,s=e.getGeometryName();n.serializers||(n.serializers={},n.serializers[o]={});var a=e.getProperties(),h=[],l=[];for(var u in a){var c=a[u];null!==c&&(h.push(u),l.push(c),u==s||c instanceof Ie?u in n.serializers[o]||(n.serializers[o][u]=ld(this.writeGeometryElement,this)):u in n.serializers[o]||(n.serializers[o][u]=ld(Nd)))}var p=C({},n);p.node=t,vd(p,n.serializers,cd(void 0,o),l,i,h)},t.prototype.writeCurveOrLineString_=function(t,e,i){var r=i[i.length-1].srsName;if("LineStringSegment"!==t.nodeName&&r&&t.setAttribute("srsName",r),"LineString"===t.nodeName||"LineStringSegment"===t.nodeName){var n=this.createCoordinatesNode_(t.namespaceURI);t.appendChild(n),this.writeCoordinates_(n,e,i)}else if("Curve"===t.nodeName){var o=$p(t.namespaceURI,"segments");t.appendChild(o),this.writeCurveSegments_(o,e,i)}},t.prototype.writeLineStringOrCurveMember_=function(t,e,i){var r=this.GEOMETRY_NODE_FACTORY_(e,i);r&&(t.appendChild(r),this.writeCurveOrLineString_(r,e,i))},t.prototype.writeMultiCurveOrLineString_=function(t,e,i){var r=i[i.length-1],n=r.hasZ,o=r.srsName,s=r.curve;o&&t.setAttribute("srsName",o);var a=e.getLineStrings();vd({node:t,hasZ:n,srsName:o,curve:s},this.LINESTRINGORCURVEMEMBER_SERIALIZERS_,this.MULTIGEOMETRY_MEMBER_NODE_FACTORY_,a,i,void 0,this)},t.prototype.writeGeometryElement=function(t,e,i){var r,n=i[i.length-1],o=C({},n);o.node=t,r=Array.isArray(e)?n.dataProjection?fe(e,n.featureProjection,n.dataProjection):e:Yp(e,!0,n),vd(o,this.GEOMETRY_SERIALIZERS_,this.GEOMETRY_NODE_FACTORY_,[r],i,void 0,this)},t.prototype.createCoordinatesNode_=function(t){var e=$p(t,"coordinates");return e.setAttribute("decimal","."),e.setAttribute("cs",","),e.setAttribute("ts"," "),e},t.prototype.writeCoordinates_=function(t,e,i){for(var r=i[i.length-1],n=r.hasZ,o=r.srsName,s=e.getCoordinates(),a=s.length,h=new Array(a),l=0;l<a;++l){var u=s[l];h[l]=this.getCoords_(u,o,n)}Nd(t,h.join(" "))},t.prototype.writeCurveSegments_=function(t,e,i){var r=$p(t.namespaceURI,"LineStringSegment");t.appendChild(r),this.writeCurveOrLineString_(r,e,i)},t.prototype.writeSurfaceOrPolygon_=function(t,e,i){var r=i[i.length-1],n=r.hasZ,o=r.srsName;if("PolygonPatch"!==t.nodeName&&o&&t.setAttribute("srsName",o),"Polygon"===t.nodeName||"PolygonPatch"===t.nodeName){var s=e.getLinearRings();vd({node:t,hasZ:n,srsName:o},this.RING_SERIALIZERS_,this.RING_NODE_FACTORY_,s,i,void 0,this)}else if("Surface"===t.nodeName){var a=$p(t.namespaceURI,"patches");t.appendChild(a),this.writeSurfacePatches_(a,e,i)}},t.prototype.RING_NODE_FACTORY_=function(t,e,i){var r=e[e.length-1],n=r.node,o=r.exteriorWritten;return void 0===o&&(r.exteriorWritten=!0),$p(n.namespaceURI,void 0!==o?"innerBoundaryIs":"outerBoundaryIs")},t.prototype.writeSurfacePatches_=function(t,e,i){var r=$p(t.namespaceURI,"PolygonPatch");t.appendChild(r),this.writeSurfaceOrPolygon_(r,e,i)},t.prototype.writeRing_=function(t,e,i){var r=$p(t.namespaceURI,"LinearRing");t.appendChild(r),this.writeLinearRing_(r,e,i)},t.prototype.getCoords_=function(t,e,i){var r="enu";e&&(r=ne(e).getAxisOrientation());var n="en"===r.substr(0,2)?t[0]+","+t[1]:t[1]+","+t[0];i&&(n+=","+(t[2]||0));return n},t.prototype.writePoint_=function(t,e,i){var r=i[i.length-1],n=r.hasZ,o=r.srsName;o&&t.setAttribute("srsName",o);var s=this.createCoordinatesNode_(t.namespaceURI);t.appendChild(s);var a=e.getCoordinates();Nd(s,this.getCoords_(a,o,n))},t.prototype.writeMultiPoint_=function(t,e,i){var r=i[i.length-1],n=r.hasZ,o=r.srsName;o&&t.setAttribute("srsName",o);var s=e.getPoints();vd({node:t,hasZ:n,srsName:o},this.POINTMEMBER_SERIALIZERS_,cd("pointMember"),s,i,void 0,this)},t.prototype.writePointMember_=function(t,e,i){var r=$p(t.namespaceURI,"Point");t.appendChild(r),this.writePoint_(r,e,i)},t.prototype.writeLinearRing_=function(t,e,i){var r=i[i.length-1].srsName;r&&t.setAttribute("srsName",r);var n=this.createCoordinatesNode_(t.namespaceURI);t.appendChild(n),this.writeCoordinates_(n,e,i)},t.prototype.writeMultiSurfaceOrPolygon_=function(t,e,i){var r=i[i.length-1],n=r.hasZ,o=r.srsName,s=r.surface;o&&t.setAttribute("srsName",o);var a=e.getPolygons();vd({node:t,hasZ:n,srsName:o,surface:s},this.SURFACEORPOLYGONMEMBER_SERIALIZERS_,this.MULTIGEOMETRY_MEMBER_NODE_FACTORY_,a,i,void 0,this)},t.prototype.writeSurfaceOrPolygonMember_=function(t,e,i){var r=this.GEOMETRY_NODE_FACTORY_(e,i);r&&(t.appendChild(r),this.writeSurfaceOrPolygon_(r,e,i))},t.prototype.writeEnvelope=function(t,e,i){var r=i[i.length-1].srsName;r&&t.setAttribute("srsName",r);var n=[e[0]+" "+e[1],e[2]+" "+e[3]];vd({node:t},this.ENVELOPE_SERIALIZERS_,pd,n,i,["lowerCorner","upperCorner"],this)},t.prototype.MULTIGEOMETRY_MEMBER_NODE_FACTORY_=function(t,e,i){var r=e[e.length-1].node;return $p("http://www.opengis.net/gml",Ud[r.nodeName])},t}(Cd);Yd.prototype.GEOMETRY_FLAT_COORDINATES_PARSERS_={"http://www.opengis.net/gml":{coordinates:sd(Yd.prototype.readFlatCoordinates_)}},Yd.prototype.FLAT_LINEAR_RINGS_PARSERS_={"http://www.opengis.net/gml":{innerBoundaryIs:Yd.prototype.innerBoundaryIsParser_,outerBoundaryIs:Yd.prototype.outerBoundaryIsParser_}},Yd.prototype.BOX_PARSERS_={"http://www.opengis.net/gml":{coordinates:od(Yd.prototype.readFlatCoordinates_)}},Yd.prototype.GEOMETRY_PARSERS_={"http://www.opengis.net/gml":{Point:sd(Cd.prototype.readPoint),MultiPoint:sd(Cd.prototype.readMultiPoint),LineString:sd(Cd.prototype.readLineString),MultiLineString:sd(Cd.prototype.readMultiLineString),LinearRing:sd(Cd.prototype.readLinearRing),Polygon:sd(Cd.prototype.readPolygon),MultiPolygon:sd(Cd.prototype.readMultiPolygon),Box:sd(Yd.prototype.readBox_)}},Yd.prototype.GEOMETRY_SERIALIZERS_={"http://www.opengis.net/gml":{Curve:ld(Yd.prototype.writeCurveOrLineString_),MultiCurve:ld(Yd.prototype.writeMultiCurveOrLineString_),Point:ld(Yd.prototype.writePoint_),MultiPoint:ld(Yd.prototype.writeMultiPoint_),LineString:ld(Yd.prototype.writeCurveOrLineString_),MultiLineString:ld(Yd.prototype.writeMultiCurveOrLineString_),LinearRing:ld(Yd.prototype.writeLinearRing_),Polygon:ld(Yd.prototype.writeSurfaceOrPolygon_),MultiPolygon:ld(Yd.prototype.writeMultiSurfaceOrPolygon_),Surface:ld(Yd.prototype.writeSurfaceOrPolygon_),MultiSurface:ld(Yd.prototype.writeMultiSurfaceOrPolygon_),Envelope:ld(Yd.prototype.writeEnvelope)}},Yd.prototype.LINESTRINGORCURVEMEMBER_SERIALIZERS_={"http://www.opengis.net/gml":{lineStringMember:ld(Yd.prototype.writeLineStringOrCurveMember_),curveMember:ld(Yd.prototype.writeLineStringOrCurveMember_)}},Yd.prototype.RING_SERIALIZERS_={"http://www.opengis.net/gml":{outerBoundaryIs:ld(Yd.prototype.writeRing_),innerBoundaryIs:ld(Yd.prototype.writeRing_)}},Yd.prototype.POINTMEMBER_SERIALIZERS_={"http://www.opengis.net/gml":{pointMember:ld(Yd.prototype.writePointMember_)}},Yd.prototype.SURFACEORPOLYGONMEMBER_SERIALIZERS_={"http://www.opengis.net/gml":{surfaceMember:ld(Yd.prototype.writeSurfaceOrPolygonMember_),polygonMember:ld(Yd.prototype.writeSurfaceOrPolygonMember_)}},Yd.prototype.ENVELOPE_SERIALIZERS_={"http://www.opengis.net/gml":{lowerCorner:ld(Nd),upperCorner:ld(Nd)}};var Bd=[null,"http://www.topografix.com/GPX/1/0","http://www.topografix.com/GPX/1/1"],Xd={rte:vf,trk:mf,wpt:xf},zd=fd(Bd,{rte:od(vf),trk:od(mf),wpt:od(xf)}),Vd=fd(Bd,{text:hd(Pd,"linkText"),type:hd(Pd,"linkType")}),Wd=fd(Bd,{rte:ld(function(t,e,i){var r=i[0],n=e.getProperties(),o={node:t,properties:n},s=e.getGeometry();s&&(s=Yp(s,!0,r),o.geometryLayout=s.getLayout(),n.rtept=s.getCoordinates());var a=i[i.length-1].node,h=rf[a.namespaceURI],l=dd(n,h);vd(o,nf,pd,l,i,h)}),trk:ld(function(t,e,i){var r=i[0],n=e.getProperties(),o={node:t,properties:n},s=e.getGeometry();s&&(s=Yp(s,!0,r),n.trkseg=s.getLineStrings());var a=i[i.length-1].node,h=sf[a.namespaceURI],l=dd(n,h);vd(o,af,pd,l,i,h)}),wpt:ld(function(t,e,i){var r=i[0],n=i[i.length-1];n.properties=e.getProperties();var o=e.getGeometry();o&&(o=Yp(o,!0,r),n.geometryLayout=o.getLayout(),Cf(t,o.getCoordinates(),i))})}),Kd=function(i){function t(t){i.call(this);var e=t||{};this.dataProjection=ne("EPSG:4326"),this.readExtensions_=e.readExtensions}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.handleReadExtensions_=function(t){t||(t=[]);for(var e=0,i=t.length;e<i;++e){var r=t[e];if(this.readExtensions_){var n=r.get("extensionsNode_")||null;this.readExtensions_(r,n)}r.set("extensionsNode_",void 0)}},t.prototype.readFeatureFromNode=function(t,e){if(!lr(Bd,t.namespaceURI))return null;var i=Xd[t.localName];if(!i)return null;var r=i(t,[this.getReadOptions(t,e)]);return r?(this.handleReadExtensions_([r]),r):null},t.prototype.readFeaturesFromNode=function(t,e){if(!lr(Bd,t.namespaceURI))return[];if("gpx"==t.localName){var i=gd([],zd,t,[this.getReadOptions(t,e)]);return i?(this.handleReadExtensions_(i),i):[]}return[]},t.prototype.writeFeaturesNode=function(t,e){e=this.adaptOptions(e);var i=$p("http://www.topografix.com/GPX/1/1","gpx");return i.setAttributeNS("http://www.w3.org/2000/xmlns/","xmlns:xsi",Qp),i.setAttributeNS(Qp,"xsi:schemaLocation","http://www.topografix.com/GPX/1/1 http://www.topografix.com/GPX/1/1/gpx.xsd"),i.setAttribute("version","1.1"),i.setAttribute("creator","OpenLayers"),vd({node:i},Wd,df,t,[e]),i},t}(md),Hd=fd(Bd,{name:hd(Pd),cmt:hd(Pd),desc:hd(Pd),src:hd(Pd),link:gf,number:hd(Ld),extensions:yf,type:hd(Pd),rtept:function(t,e){var i=gd({},Zd,t,e);if(i){var r=e[e.length-1],n=r.flatCoordinates,o=r.layoutOptions;ff(n,o,t,i)}}}),Zd=fd(Bd,{ele:hd(Rd),time:hd(wd)}),qd=fd(Bd,{name:hd(Pd),cmt:hd(Pd),desc:hd(Pd),src:hd(Pd),link:gf,number:hd(Ld),type:hd(Pd),extensions:yf,trkseg:function(t,e){var i=e[e.length-1];_d(Jd,t,e);var r=i.flatCoordinates;i.ends.push(r.length)}}),Jd=fd(Bd,{trkpt:function(t,e){var i=gd({},Qd,t,e);if(i){var r=e[e.length-1],n=r.flatCoordinates,o=r.layoutOptions;ff(n,o,t,i)}}}),Qd=fd(Bd,{ele:hd(Rd),time:hd(wd)}),$d=fd(Bd,{ele:hd(Rd),time:hd(wd),magvar:hd(Rd),geoidheight:hd(Rd),name:hd(Pd),cmt:hd(Pd),desc:hd(Pd),src:hd(Pd),link:gf,sym:hd(Pd),type:hd(Pd),fix:hd(Pd),sat:hd(Ld),hdop:hd(Rd),vdop:hd(Rd),pdop:hd(Rd),ageofdgpsdata:hd(Rd),dgpsid:hd(Ld),extensions:yf}),tf=["text","type"],ef=fd(Bd,{text:ld(Nd),type:ld(Nd)}),rf=fd(Bd,["name","cmt","desc","src","link","number","type","rtept"]),nf=fd(Bd,{name:ld(Nd),cmt:ld(Nd),desc:ld(Nd),src:ld(Nd),link:ld(Sf),number:ld(Od),type:ld(Nd),rtept:ud(ld(Cf))}),of=fd(Bd,["ele","time"]),sf=fd(Bd,["name","cmt","desc","src","link","number","type","trkseg"]),af=fd(Bd,{name:ld(Nd),cmt:ld(Nd),desc:ld(Nd),src:ld(Nd),link:ld(Sf),number:ld(Od),type:ld(Nd),trkseg:ud(ld(function(t,e,i){vd({node:t,geometryLayout:e.getLayout(),properties:{}},lf,hf,e.getCoordinates(),i)}))}),hf=cd("trkpt"),lf=fd(Bd,{trkpt:ld(Cf)}),uf=fd(Bd,["ele","time","magvar","geoidheight","name","cmt","desc","src","link","sym","type","fix","sat","hdop","vdop","pdop","ageofdgpsdata","dgpsid"]),cf=fd(Bd,{ele:ld(Md),time:ld(function(t,e){var i=new Date(1e3*e),r=i.getUTCFullYear()+"-"+on(i.getUTCMonth()+1,2)+"-"+on(i.getUTCDate(),2)+"T"+on(i.getUTCHours(),2)+":"+on(i.getUTCMinutes(),2)+":"+on(i.getUTCSeconds(),2)+"Z";t.appendChild(Jp.createTextNode(r))}),magvar:ld(Md),geoidheight:ld(Md),name:ld(Nd),cmt:ld(Nd),desc:ld(Nd),src:ld(Nd),link:ld(Sf),sym:ld(Nd),type:ld(Nd),fix:ld(Nd),sat:ld(Od),hdop:ld(Md),vdop:ld(Md),pdop:ld(Md),ageofdgpsdata:ld(Md),dgpsid:ld(Od)}),pf={Point:"wpt",LineString:"rte",MultiLineString:"trk"};function df(t,e,i){var r=t.getGeometry();if(r){var n=pf[r.getType()];if(n)return $p(e[e.length-1].node.namespaceURI,n)}}function ff(t,e,i,r){return t.push(parseFloat(i.getAttribute("lon")),parseFloat(i.getAttribute("lat"))),"ele"in r?(t.push(r.ele),delete r.ele,e.hasZ=!0):t.push(0),"time"in r?(t.push(r.time),delete r.time,e.hasM=!0):t.push(0),t}function _f(t,e,i){var r=yr.XY,n=2;if(t.hasZ&&t.hasM?(r=yr.XYZM,n=4):t.hasZ?(r=yr.XYZ,n=3):t.hasM&&(r=yr.XYM,n=3),4!==n){for(var o=0,s=e.length/4;o<s;o++)e[o*n]=e[4*o],e[o*n+1]=e[4*o+1],t.hasZ&&(e[o*n+2]=e[4*o+2]),t.hasM&&(e[o*n+2]=e[4*o+3]);if(e.length=e.length/4*n,i)for(var a=0,h=i.length;a<h;a++)i[a]=i[a]/4*n}return r}function gf(t,e){var i=e[e.length-1],r=t.getAttribute("href");null!==r&&(i.link=r),_d(Vd,t,e)}function yf(t,e){e[e.length-1].extensionsNode_=t}function vf(t,e){var i=e[0],r=gd({flatCoordinates:[],layoutOptions:{}},Hd,t,e);if(r){var n=r.flatCoordinates;delete r.flatCoordinates;var o=r.layoutOptions;delete r.layoutOptions;var s=_f(o,n),a=new Sn(n,s);Yp(a,!1,i);var h=new Ji(a);return h.setProperties(r),h}}function mf(t,e){var i=e[0],r=gd({flatCoordinates:[],ends:[],layoutOptions:{}},qd,t,e);if(r){var n=r.flatCoordinates;delete r.flatCoordinates;var o=r.ends;delete r.ends;var s=r.layoutOptions;delete r.layoutOptions;var a=_f(s,n,o),h=new eh(n,a,o);Yp(h,!1,i);var l=new Ji(h);return l.setProperties(r),l}}function xf(t,e){var i=e[0],r=gd({},$d,t,e);if(r){var n={},o=ff([],n,t,r),s=_f(n,o),a=new Dr(o,s);Yp(a,!1,i);var h=new Ji(a);return h.setProperties(r),h}}function Sf(t,e,i){t.setAttribute("href",e);var r=i[i.length-1].properties,n=[r.linkText,r.linkType];vd({node:t},ef,pd,n,i,tf)}function Cf(t,e,i){var r=i[i.length-1],n=r.node.namespaceURI,o=r.properties;switch(t.setAttributeNS(null,"lat",e[1]),t.setAttributeNS(null,"lon",e[0]),r.geometryLayout){case yr.XYZM:0!==e[3]&&(o.time=e[3]);case yr.XYZ:0!==e[2]&&(o.ele=e[2]);break;case yr.XYM:0!==e[2]&&(o.time=e[2])}var s="rtept"==t.nodeName?of[n]:uf[n],a=dd(o,s);vd({node:t,properties:o},cf,pd,a,i,s)}var Ef=function(e){function u(t){e.call(this),this.geometries_=t||null,this.listenGeometriesChange_()}return e&&(u.__proto__=e),((u.prototype=Object.create(e&&e.prototype)).constructor=u).prototype.unlistenGeometriesChange_=function(){if(this.geometries_)for(var t=0,e=this.geometries_.length;t<e;++t)d(this.geometries_[t],w.CHANGE,this.changed,this)},u.prototype.listenGeometriesChange_=function(){if(this.geometries_)for(var t=0,e=this.geometries_.length;t<e;++t)E(this.geometries_[t],w.CHANGE,this.changed,this)},u.prototype.clone=function(){var t=new u(null);return t.setGeometries(this.geometries_),t},u.prototype.closestPointXY=function(t,e,i,r){if(r<D(this.getExtent(),t,e))return r;for(var n=this.geometries_,o=0,s=n.length;o<s;++o)r=n[o].closestPointXY(t,e,i,r);return r},u.prototype.containsXY=function(t,e){for(var i=this.geometries_,r=0,n=i.length;r<n;++r)if(i[r].containsXY(t,e))return!0;return!1},u.prototype.computeExtent=function(t){z(t);for(var e=this.geometries_,i=0,r=e.length;i<r;++i)H(t,e[i].getExtent());return t},u.prototype.getGeometries=function(){return Tf(this.geometries_)},u.prototype.getGeometriesArray=function(){return this.geometries_},u.prototype.getSimplifiedGeometry=function(t){if(this.simplifiedGeometryRevision!=this.getRevision()&&(_(this.simplifiedGeometryCache),this.simplifiedGeometryMaxMinSquaredTolerance=0,this.simplifiedGeometryRevision=this.getRevision()),t<0||0!==this.simplifiedGeometryMaxMinSquaredTolerance&&t<this.simplifiedGeometryMaxMinSquaredTolerance)return this;var e=t.toString();if(this.simplifiedGeometryCache.hasOwnProperty(e))return this.simplifiedGeometryCache[e];for(var i=[],r=this.geometries_,n=!1,o=0,s=r.length;o<s;++o){var a=r[o],h=a.getSimplifiedGeometry(t);i.push(h),h!==a&&(n=!0)}if(n){var l=new u(null);return l.setGeometriesArray(i),this.simplifiedGeometryCache[e]=l}return this.simplifiedGeometryMaxMinSquaredTolerance=t,this},u.prototype.getType=function(){return Lt.GEOMETRY_COLLECTION},u.prototype.intersectsExtent=function(t){for(var e=this.geometries_,i=0,r=e.length;i<r;++i)if(e[i].intersectsExtent(t))return!0;return!1},u.prototype.isEmpty=function(){return 0===this.geometries_.length},u.prototype.rotate=function(t,e){for(var i=this.geometries_,r=0,n=i.length;r<n;++r)i[r].rotate(t,e);this.changed()},u.prototype.scale=function(t,e,i){var r=i;r||(r=ot(this.getExtent()));for(var n=this.geometries_,o=0,s=n.length;o<s;++o)n[o].scale(t,e,r);this.changed()},u.prototype.setGeometries=function(t){this.setGeometriesArray(Tf(t))},u.prototype.setGeometriesArray=function(t){this.unlistenGeometriesChange_(),this.geometries_=t,this.listenGeometriesChange_(),this.changed()},u.prototype.applyTransform=function(t){for(var e=this.geometries_,i=0,r=e.length;i<r;++i)e[i].applyTransform(t);this.changed()},u.prototype.translate=function(t,e){for(var i=this.geometries_,r=0,n=i.length;r<n;++r)i[r].translate(t,e);this.changed()},u.prototype.disposeInternal=function(){this.unlistenGeometriesChange_(),e.prototype.disposeInternal.call(this)},u}(Ie);function Tf(t){for(var e=[],i=0,r=t.length;i<r;++i)e.push(t[i].clone());return e}var wf=function(i){function t(t){var e=t||{};i.call(this),this.dataProjection=ne(e.dataProjection?e.dataProjection:"EPSG:4326"),e.featureProjection&&(this.defaultFeatureProjection=ne(e.featureProjection)),this.geometryName_=e.geometryName,this.extractGeometryName_=e.extractGeometryName}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.readFeatureFromObject=function(t,e){var i=null,r=Lf((i="Feature"===t.type?t:{type:"Feature",geometry:t}).geometry,e),n=new Ji;return this.geometryName_?n.setGeometryName(this.geometryName_):this.extractGeometryName_&&void 0!==i.geometry_name&&n.setGeometryName(i.geometry_name),n.setGeometry(r),void 0!==i.id&&n.setId(i.id),i.properties&&n.setProperties(i.properties),n},t.prototype.readFeaturesFromObject=function(t,e){var i=null;if("FeatureCollection"===t.type){i=[];for(var r=t.features,n=0,o=r.length;n<o;++n)i.push(this.readFeatureFromObject(r[n],e))}else i=[this.readFeatureFromObject(t,e)];return i},t.prototype.readGeometryFromObject=function(t,e){return Lf(t,e)},t.prototype.readProjectionFromObject=function(t){var e,i=t.crs;return i?"name"==i.type?e=ne(i.properties.name):Z(!1,36):e=this.dataProjection,e},t.prototype.writeFeatureObject=function(t,e){e=this.adaptOptions(e);var i={type:"Feature"},r=t.getId();void 0!==r&&(i.id=r);var n=t.getGeometry();i.geometry=n?bf(n,e):null;var o=t.getProperties();return delete o[t.getGeometryName()],Tt(o)?i.properties=null:i.properties=o,i},t.prototype.writeFeaturesObject=function(t,e){e=this.adaptOptions(e);for(var i=[],r=0,n=t.length;r<n;++r)i.push(this.writeFeatureObject(t[r],e));return{type:"FeatureCollection",features:i}},t.prototype.writeGeometryObject=function(t,e){return bf(t,this.adaptOptions(e))},t}(Bp),Rf={Point:function(t){return new Dr(t.coordinates)},LineString:function(t){return new Sn(t.coordinates)},Polygon:function(t){return new Qr(t.coordinates)},MultiPoint:function(t){return new ih(t.coordinates)},MultiLineString:function(t){return new eh(t.coordinates)},MultiPolygon:function(t){return new nh(t.coordinates)},GeometryCollection:function(t,e){var i=t.geometries.map(function(t){return Lf(t,e)});return new Ef(i)}},If={Point:function(t,e){return{type:"Point",coordinates:t.getCoordinates()}},LineString:function(t,e){return{type:"LineString",coordinates:t.getCoordinates()}},Polygon:function(t,e){var i;e&&(i=e.rightHanded);return{type:"Polygon",coordinates:t.getCoordinates(i)}},MultiPoint:function(t,e){return{type:"MultiPoint",coordinates:t.getCoordinates()}},MultiLineString:function(t,e){return{type:"MultiLineString",coordinates:t.getCoordinates()}},MultiPolygon:function(t,e){var i;e&&(i=e.rightHanded);return{type:"MultiPolygon",coordinates:t.getCoordinates(i)}},GeometryCollection:function(t,i){return{type:"GeometryCollection",geometries:t.getGeometriesArray().map(function(t){var e=C({},i);return delete e.featureProjection,bf(t,e)})}},Circle:function(t){return{type:"GeometryCollection",geometries:[]}}};function Lf(t,e){return t?Yp((0,Rf[t.type])(t),!1,e):null}function bf(t,e){return(0,If[t.getType()])(Yp(t,!0,e),e)}var Pf=function(t){function e(){t.call(this)}return t&&(e.__proto__=t),((e.prototype=Object.create(t&&t.prototype)).constructor=e).prototype.getType=function(){return uh.TEXT},e.prototype.readFeature=function(t,e){return this.readFeatureFromText(Ff(t),this.adaptOptions(e))},e.prototype.readFeatureFromText=function(t,e){},e.prototype.readFeatures=function(t,e){return this.readFeaturesFromText(Ff(t),this.adaptOptions(e))},e.prototype.readFeaturesFromText=function(t,e){},e.prototype.readGeometry=function(t,e){return this.readGeometryFromText(Ff(t),this.adaptOptions(e))},e.prototype.readGeometryFromText=function(t,e){},e.prototype.readProjection=function(t){return this.readProjectionFromText(Ff(t))},e.prototype.readProjectionFromText=function(t){return this.dataProjection},e.prototype.writeFeature=function(t,e){return this.writeFeatureText(t,this.adaptOptions(e))},e.prototype.writeFeatureText=function(t,e){},e.prototype.writeFeatures=function(t,e){return this.writeFeaturesText(t,this.adaptOptions(e))},e.prototype.writeFeaturesText=function(t,e){},e.prototype.writeGeometry=function(t,e){return this.writeGeometryText(t,this.adaptOptions(e))},e.prototype.writeGeometryText=function(t,e){},e}(Up);function Ff(t){return"string"==typeof t?t:""}var Mf="barometric",Of="gps",Nf="none",Af=/^B(\d{2})(\d{2})(\d{2})(\d{2})(\d{5})([NS])(\d{3})(\d{5})([EW])([AV])(\d{5})(\d{5})/,Gf=/^H.([A-Z]{3}).*?:(.*)/,kf=/^HFDTE(\d{2})(\d{2})(\d{2})/,Df=/\r\n|\r|\n/,jf=function(i){function t(t){i.call(this);var e=t||{};this.dataProjection=ne("EPSG:4326"),this.altitudeMode_=e.altitudeMode?e.altitudeMode:Nf}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.readFeatureFromText=function(t,e){var i,r,n=this.altitudeMode_,o=t.split(Df),s={},a=[],h=2e3,l=0,u=1,c=-1;for(i=0,r=o.length;i<r;++i){var p=o[i],d=void 0;if("B"==p.charAt(0)){if(d=Af.exec(p)){var f=parseInt(d[1],10),_=parseInt(d[2],10),g=parseInt(d[3],10),y=parseInt(d[4],10)+parseInt(d[5],10)/6e4;"S"==d[6]&&(y=-y);var v=parseInt(d[7],10)+parseInt(d[8],10)/6e4;if("W"==d[9]&&(v=-v),a.push(v,y),n!=Nf){var m=void 0;m=n==Of?parseInt(d[11],10):n==Mf?parseInt(d[12],10):0,a.push(m)}var x=Date.UTC(h,l,u,f,_,g);x<c&&(x=Date.UTC(h,l,u+1,f,_,g)),a.push(x/1e3),c=x}}else"H"==p.charAt(0)&&((d=kf.exec(p))?(u=parseInt(d[1],10),l=parseInt(d[2],10)-1,h=2e3+parseInt(d[3],10)):(d=Gf.exec(p))&&(s[d[1]]=d[2].trim()))}if(0===a.length)return null;var S=n==Nf?yr.XYM:yr.XYZM,C=new Sn(a,S),E=new Ji(Yp(C,!1,e));return E.setProperties(s),E},t.prototype.readFeaturesFromText=function(t,e){var i=this.readFeatureFromText(t,e);return i?[i]:[]},t.prototype.writeFeatureText=function(t,e){},t.prototype.writeFeaturesText=function(t,e){},t.prototype.writeGeometryText=function(t,e){},t.prototype.readGeometryFromText=function(t,e){},t}(Pf),Uf={FRACTION:"fraction",PIXELS:"pixels"},Yf=function(s){function t(t,e,i,r,n,o){s.call(this),this.hitDetectionImage_=null,this.image_=t||new Image,null!==r&&(this.image_.crossOrigin=r),this.canvas_=o?document.createElement("CANVAS"):null,this.color_=o,this.imageListenerKeys_=null,this.imageState_=n,this.size_=i,this.src_=e,this.tainting_=!1,this.imageState_==di.LOADED&&this.determineTainting_()}return s&&(t.__proto__=s),((t.prototype=Object.create(s&&s.prototype)).constructor=t).prototype.determineTainting_=function(){var t=De(1,1);try{t.drawImage(this.image_,0,0),t.getImageData(0,0,1,1)}catch(t){this.tainting_=!0}},t.prototype.dispatchChangeEvent_=function(){this.dispatchEvent(w.CHANGE)},t.prototype.handleImageError_=function(){this.imageState_=di.ERROR,this.unlistenImage_(),this.dispatchChangeEvent_()},t.prototype.handleImageLoad_=function(){this.imageState_=di.LOADED,this.size_&&(this.image_.width=this.size_[0],this.image_.height=this.size_[1]),this.size_=[this.image_.width,this.image_.height],this.unlistenImage_(),this.determineTainting_(),this.replaceColor_(),this.dispatchChangeEvent_()},t.prototype.getImage=function(t){return this.canvas_?this.canvas_:this.image_},t.prototype.getImageState=function(){return this.imageState_},t.prototype.getHitDetectionImage=function(t){if(!this.hitDetectionImage_)if(this.tainting_){var e=this.size_[0],i=this.size_[1],r=De(e,i);r.fillRect(0,0,e,i),this.hitDetectionImage_=r.canvas}else this.hitDetectionImage_=this.image_;return this.hitDetectionImage_},t.prototype.getSize=function(){return this.size_},t.prototype.getSrc=function(){return this.src_},t.prototype.load=function(){if(this.imageState_==di.IDLE){this.imageState_=di.LOADING,this.imageListenerKeys_=[p(this.image_,w.ERROR,this.handleImageError_,this),p(this.image_,w.LOAD,this.handleImageLoad_,this)];try{this.image_.src=this.src_}catch(t){this.handleImageError_()}}},t.prototype.replaceColor_=function(){if(!this.tainting_&&null!==this.color_){this.canvas_.width=this.image_.width,this.canvas_.height=this.image_.height;var t=this.canvas_.getContext("2d");t.drawImage(this.image_,0,0);for(var e=t.getImageData(0,0,this.image_.width,this.image_.height),i=e.data,r=this.color_[0]/255,n=this.color_[1]/255,o=this.color_[2]/255,s=0,a=i.length;s<a;s+=4)i[s]*=r,i[s+1]*=n,i[s+2]*=o;t.putImageData(e,0,0)}},t.prototype.unlistenImage_=function(){this.imageListenerKeys_.forEach(g),this.imageListenerKeys_=null},t}(i);var Bf,Xf,zf,Vf,Wf,Kf,Hf,Zf,qf,Jf={BOTTOM_LEFT:"bottom-left",BOTTOM_RIGHT:"bottom-right",TOP_LEFT:"top-left",TOP_RIGHT:"top-right"},Qf=function(v){function t(t){var e=t||{},i=void 0!==e.opacity?e.opacity:1,r=void 0!==e.rotation?e.rotation:0,n=void 0!==e.scale?e.scale:1,o=void 0!==e.rotateWithView&&e.rotateWithView,s=void 0===e.snapToPixel||e.snapToPixel;v.call(this,{opacity:i,rotation:r,scale:n,snapToPixel:s,rotateWithView:o}),this.anchor_=void 0!==e.anchor?e.anchor:[.5,.5],this.normalizedAnchor_=null,this.anchorOrigin_=void 0!==e.anchorOrigin?e.anchorOrigin:Jf.TOP_LEFT,this.anchorXUnits_=void 0!==e.anchorXUnits?e.anchorXUnits:Uf.FRACTION,this.anchorYUnits_=void 0!==e.anchorYUnits?e.anchorYUnits:Uf.FRACTION,this.crossOrigin_=void 0!==e.crossOrigin?e.crossOrigin:null;var a=void 0!==e.img?e.img:null,h=void 0!==e.imgSize?e.imgSize:null,l=e.src;Z(!(void 0!==l&&a),4),Z(!a||a&&h,5),void 0!==l&&0!==l.length||!a||(l=a.src||Et(a).toString()),Z(void 0!==l&&0<l.length,6);var u,c,p,d,f,_,g,y=void 0!==e.src?di.IDLE:di.LOADED;this.color_=void 0!==e.color?Ne(e.color):null,this.iconImage_=(u=a,c=l,p=h,d=this.crossOrigin_,f=y,_=this.color_,(g=Al.get(c,d,_))||(g=new Yf(u,c,p,d,f,_),Al.set(c,d,_,g)),g),this.offset_=void 0!==e.offset?e.offset:[0,0],this.offsetOrigin_=void 0!==e.offsetOrigin?e.offsetOrigin:Jf.TOP_LEFT,this.origin_=null,this.size_=void 0!==e.size?e.size:null}return v&&(t.__proto__=v),((t.prototype=Object.create(v&&v.prototype)).constructor=t).prototype.clone=function(){return new t({anchor:this.anchor_.slice(),anchorOrigin:this.anchorOrigin_,anchorXUnits:this.anchorXUnits_,anchorYUnits:this.anchorYUnits_,crossOrigin:this.crossOrigin_,color:this.color_&&this.color_.slice?this.color_.slice():this.color_||void 0,src:this.getSrc(),offset:this.offset_.slice(),offsetOrigin:this.offsetOrigin_,size:null!==this.size_?this.size_.slice():void 0,opacity:this.getOpacity(),scale:this.getScale(),snapToPixel:this.getSnapToPixel(),rotation:this.getRotation(),rotateWithView:this.getRotateWithView()})},t.prototype.getAnchor=function(){if(this.normalizedAnchor_)return this.normalizedAnchor_;var t=this.anchor_,e=this.getSize();if(this.anchorXUnits_==Uf.FRACTION||this.anchorYUnits_==Uf.FRACTION){if(!e)return null;t=this.anchor_.slice(),this.anchorXUnits_==Uf.FRACTION&&(t[0]*=e[0]),this.anchorYUnits_==Uf.FRACTION&&(t[1]*=e[1])}if(this.anchorOrigin_!=Jf.TOP_LEFT){if(!e)return null;t===this.anchor_&&(t=this.anchor_.slice()),this.anchorOrigin_!=Jf.TOP_RIGHT&&this.anchorOrigin_!=Jf.BOTTOM_RIGHT||(t[0]=-t[0]+e[0]),this.anchorOrigin_!=Jf.BOTTOM_LEFT&&this.anchorOrigin_!=Jf.BOTTOM_RIGHT||(t[1]=-t[1]+e[1])}return this.normalizedAnchor_=t,this.normalizedAnchor_},t.prototype.setAnchor=function(t){this.anchor_=t,this.normalizedAnchor_=null},t.prototype.getColor=function(){return this.color_},t.prototype.getImage=function(t){return this.iconImage_.getImage(t)},t.prototype.getImageSize=function(){return this.iconImage_.getSize()},t.prototype.getHitDetectionImageSize=function(){return this.getImageSize()},t.prototype.getImageState=function(){return this.iconImage_.getImageState()},t.prototype.getHitDetectionImage=function(t){return this.iconImage_.getHitDetectionImage(t)},t.prototype.getOrigin=function(){if(this.origin_)return this.origin_;var t=this.offset_;if(this.offsetOrigin_!=Jf.TOP_LEFT){var e=this.getSize(),i=this.iconImage_.getSize();if(!e||!i)return null;t=t.slice(),this.offsetOrigin_!=Jf.TOP_RIGHT&&this.offsetOrigin_!=Jf.BOTTOM_RIGHT||(t[0]=i[0]-e[0]-t[0]),this.offsetOrigin_!=Jf.BOTTOM_LEFT&&this.offsetOrigin_!=Jf.BOTTOM_RIGHT||(t[1]=i[1]-e[1]-t[1])}return this.origin_=t,this.origin_},t.prototype.getSrc=function(){return this.iconImage_.getSrc()},t.prototype.getSize=function(){return this.size_?this.size_:this.iconImage_.getSize()},t.prototype.listenImageChange=function(t,e){return E(this.iconImage_,w.CHANGE,t,e)},t.prototype.load=function(){this.iconImage_.load()},t.prototype.unlistenImageChange=function(t,e){d(this.iconImage_,w.CHANGE,t,e)},t}(Yi),$f=["http://www.google.com/kml/ext/2.2"],t_=[null,"http://earth.google.com/kml/2.0","http://earth.google.com/kml/2.1","http://earth.google.com/kml/2.2","http://www.opengis.net/kml/2.2"],e_={fraction:Uf.FRACTION,pixels:Uf.PIXELS,insetPixels:Uf.PIXELS},i_=fd(t_,{ExtendedData:K_,Region:H_,MultiGeometry:hd(D_,"geometry"),LineString:hd(A_,"geometry"),LinearRing:hd(G_,"geometry"),Point:hd(j_,"geometry"),Polygon:hd(Y_,"geometry"),Style:hd(X_),StyleMap:function(t,e){var i=S_(t,e);if(!i)return;var r=e[e.length-1];Array.isArray(i)?r.Style=i:"string"==typeof i?r.styleUrl=i:Z(!1,38)},address:hd(Pd),description:hd(Pd),name:hd(Pd),open:hd(Ed),phoneNumber:hd(Pd),styleUrl:hd(v_),visibility:hd(Ed)},fd($f,{MultiTrack:hd(function(t,e){var i=gd([],L_,t,e);if(!i)return;return new eh(i)},"geometry"),Track:hd(P_,"geometry")})),r_=fd(t_,{ExtendedData:K_,Region:H_,Link:function(t,e){_d(n_,t,e)},address:hd(Pd),description:hd(Pd),name:hd(Pd),open:hd(Ed),phoneNumber:hd(Pd),visibility:hd(Ed)}),n_=fd(t_,{href:hd(v_)}),o_=fd(t_,{LatLonAltBox:function(t,e){var i=gd({},J_,t,e);if(!i)return;var r=e[e.length-1],n=[parseFloat(i.west),parseFloat(i.south),parseFloat(i.east),parseFloat(i.north)];r.extent=n,r.altitudeMode=i.altitudeMode,r.minAltitude=parseFloat(i.minAltitude),r.maxAltitude=parseFloat(i.maxAltitude)},Lod:function(t,e){var i=gd({},Q_,t,e);if(!i)return;var r=e[e.length-1];r.minLodPixels=parseFloat(i.minLodPixels),r.maxLodPixels=parseFloat(i.maxLodPixels),r.minFadeExtent=parseFloat(i.minFadeExtent),r.maxFadeExtent=parseFloat(i.maxFadeExtent)}}),s_=fd(t_,["Document","Placemark"]),a_=fd(t_,{Document:ld(function(t,e,i){vd({node:t},rg,ng,e,i,void 0,this)}),Placemark:ld(Lg)}),h_=null,l_=null,u_=null,c_=null,p_=null,d_=null;var f_=function(i){function t(t){i.call(this);var e=t||{};d_||(h_=new zi({color:Bf=[255,255,255,1]}),Xf=[20,2],zf=Uf.PIXELS,Vf=Uf.PIXELS,Wf=[64,64],Kf="https://maps.google.com/mapfiles/kml/pushpin/ylw-pushpin.png",Hf=.5,l_=new Qf({anchor:Xf,anchorOrigin:Jf.BOTTOM_LEFT,anchorXUnits:zf,anchorYUnits:Vf,crossOrigin:"anonymous",rotation:0,scale:Hf,size:Wf,src:Kf}),Zf="NO_IMAGE",u_=new Vi({color:Bf,width:1}),qf=new Vi({color:[51,51,51,1],width:2}),c_=new Ln({font:"bold 16px Helvetica",fill:h_,stroke:qf,scale:.8}),p_=new Wi({fill:h_,image:l_,text:c_,stroke:u_,zIndex:0}),d_=[p_]),this.dataProjection=ne("EPSG:4326"),this.defaultStyle_=e.defaultStyle?e.defaultStyle:d_,this.extractStyles_=void 0===e.extractStyles||e.extractStyles,this.writeStyles_=void 0===e.writeStyles||e.writeStyles,this.sharedStyles_={},this.showPointNames_=void 0===e.showPointNames||e.showPointNames}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.readDocumentOrFolder_=function(t,e){var i=gd([],fd(t_,{Document:nd(this.readDocumentOrFolder_,this),Folder:nd(this.readDocumentOrFolder_,this),Placemark:od(this.readPlacemark_,this),Style:this.readSharedStyle_.bind(this),StyleMap:this.readSharedStyleMap_.bind(this)}),t,e,this);return i||void 0},t.prototype.readPlacemark_=function(t,e){var i=gd({geometry:null},i_,t,e);if(i){var r=new Ji,n=t.getAttribute("id");null!==n&&r.setId(n);var a,h,l,u,c,o=e[0],s=i.geometry;if(s&&Yp(s,!1,o),r.setGeometry(s),delete i.geometry,this.extractStyles_){var p=i.Style,d=i.styleUrl,f=(a=p,h=d,l=this.defaultStyle_,u=this.sharedStyles_,c=this.showPointNames_,function(t,e){var i,r=c,n="";if(r){var o=t.getGeometry();o&&(r=o.getType()===Lt.POINT)}if(r&&(n=t.get("name"),r=r&&n),a)return r?(i=__(a[0],n),a.concat(i)):a;if(h){var s=function t(e,i,r){return Array.isArray(e)?e:"string"==typeof e?(!(e in r)&&"#"+e in r&&(e="#"+e),t(r[e],i,r)):i}(h,l,u);return r?(i=__(s[0],n),s.concat(i)):s}return r?(i=__(l[0],n),l.concat(i)):l});r.setStyle(f)}return delete i.Style,r.setProperties(i),r}},t.prototype.readSharedStyle_=function(t,e){var i=t.getAttribute("id");if(null!==i){var r=X_(t,e);if(r){var n,o=t.baseURI;if(o&&"about:blank"!=o||(o=window.location.href),o)n=new URL("#"+i,o).href;else n="#"+i;this.sharedStyles_[n]=r}}},t.prototype.readSharedStyleMap_=function(t,e){var i=t.getAttribute("id");if(null!==i){var r=S_(t,e);if(r){var n,o=t.baseURI;if(o&&"about:blank"!=o||(o=window.location.href),o)n=new URL("#"+i,o).href;else n="#"+i;this.sharedStyles_[n]=r}}},t.prototype.readFeatureFromNode=function(t,e){if(!lr(t_,t.namespaceURI))return null;var i=this.readPlacemark_(t,[this.getReadOptions(t,e)]);return i||null},t.prototype.readFeaturesFromNode=function(t,e){var i;if(!lr(t_,t.namespaceURI))return[];var r=t.localName;if("Document"==r||"Folder"==r)return(i=this.readDocumentOrFolder_(t,[this.getReadOptions(t,e)]))||[];if("Placemark"==r){var n=this.readPlacemark_(t,[this.getReadOptions(t,e)]);return n?[n]:[]}if("kml"==r){i=[];for(var o=t.firstElementChild;o;o=o.nextElementSibling){var s=this.readFeaturesFromNode(o,e);s&&pr(i,s)}return i}return[]},t.prototype.readName=function(t){if(ed(t))return this.readNameFromDocument(t);if(id(t))return this.readNameFromNode(t);if("string"==typeof t){var e=rd(t);return this.readNameFromDocument(e)}},t.prototype.readNameFromDocument=function(t){for(var e=t.firstChild;e;e=e.nextSibling)if(e.nodeType==Node.ELEMENT_NODE){var i=this.readNameFromNode(e);if(i)return i}},t.prototype.readNameFromNode=function(t){for(var e=t.firstElementChild;e;e=e.nextElementSibling)if(lr(t_,e.namespaceURI)&&"name"==e.localName)return Pd(e);for(var i=t.firstElementChild;i;i=i.nextElementSibling){var r=i.localName;if(lr(t_,i.namespaceURI)&&("Document"==r||"Folder"==r||"Placemark"==r||"kml"==r)){var n=this.readNameFromNode(i);if(n)return n}}},t.prototype.readNetworkLinks=function(t){var e=[];if(ed(t))pr(e,this.readNetworkLinksFromDocument(t));else if(id(t))pr(e,this.readNetworkLinksFromNode(t));else if("string"==typeof t){var i=rd(t);pr(e,this.readNetworkLinksFromDocument(i))}return e},t.prototype.readNetworkLinksFromDocument=function(t){for(var e=[],i=t.firstChild;i;i=i.nextSibling)i.nodeType==Node.ELEMENT_NODE&&pr(e,this.readNetworkLinksFromNode(i));return e},t.prototype.readNetworkLinksFromNode=function(t){for(var e=[],i=t.firstElementChild;i;i=i.nextElementSibling)if(lr(t_,i.namespaceURI)&&"NetworkLink"==i.localName){var r=gd({},r_,i,[]);e.push(r)}for(var n=t.firstElementChild;n;n=n.nextElementSibling){var o=n.localName;!lr(t_,n.namespaceURI)||"Document"!=o&&"Folder"!=o&&"kml"!=o||pr(e,this.readNetworkLinksFromNode(n))}return e},t.prototype.readRegion=function(t){var e=[];if(ed(t))pr(e,this.readRegionFromDocument(t));else if(id(t))pr(e,this.readRegionFromNode(t));else if("string"==typeof t){var i=rd(t);pr(e,this.readRegionFromDocument(i))}return e},t.prototype.readRegionFromDocument=function(t){for(var e=[],i=t.firstChild;i;i=i.nextSibling)i.nodeType==Node.ELEMENT_NODE&&pr(e,this.readRegionFromNode(i));return e},t.prototype.readRegionFromNode=function(t){for(var e=[],i=t.firstElementChild;i;i=i.nextElementSibling)if(lr(t_,i.namespaceURI)&&"Region"==i.localName){var r=gd({},o_,i,[]);e.push(r)}for(var n=t.firstElementChild;n;n=n.nextElementSibling){var o=n.localName;!lr(t_,n.namespaceURI)||"Document"!=o&&"Folder"!=o&&"kml"!=o||pr(e,this.readRegionFromNode(n))}return e},t.prototype.writeFeaturesNode=function(t,e){e=this.adaptOptions(e);var i=$p(t_[4],"kml"),r="http://www.w3.org/2000/xmlns/";i.setAttributeNS(r,"xmlns:gx",$f[0]),i.setAttributeNS(r,"xmlns:xsi",Qp),i.setAttributeNS(Qp,"xsi:schemaLocation","http://www.opengis.net/kml/2.2 https://developers.google.com/kml/schema/kml22gx.xsd");var n={node:i},o={};1<t.length?o.Document=t:1==t.length&&(o.Placemark=t[0]);var s=s_[i.namespaceURI],a=dd(o,s);return vd(n,a_,pd,a,[e],s,this),i},t}(md);function __(t,e){var i=null,r=[0,0],n="start";if(t.getImage()){var o=t.getImage().getImageSize();if(null===o&&(o=Wf),2==o.length){var s=t.getImage().getScale();r[0]=s*o[0]/2,r[1]=-s*o[1]/2,n="left"}}if(null!==t.getText()){var a=t.getText();(i=a.clone()).setFont(a.getFont()||c_.getFont()),i.setScale(a.getScale()||c_.getScale()),i.setFill(a.getFill()||c_.getFill()),i.setStroke(a.getStroke()||qf)}else i=c_.clone();return i.setText(e),i.setOffsetX(r[0]),i.setOffsetY(r[1]),i.setTextAlign(n),new Wi({text:i})}function g_(t){var e=td(t,!1),i=/^\s*#?\s*([0-9A-Fa-f]{8})\s*$/.exec(e);if(i){var r=i[1];return[parseInt(r.substr(6,2),16),parseInt(r.substr(4,2),16),parseInt(r.substr(2,2),16),parseInt(r.substr(0,2),16)/255]}}function y_(t){for(var e,i=td(t,!1),r=[],n=/^\s*([+\-]?\d*\.?\d+(?:e[+\-]?\d+)?)\s*,\s*([+\-]?\d*\.?\d+(?:e[+\-]?\d+)?)(?:\s*,\s*([+\-]?\d*\.?\d+(?:e[+\-]?\d+)?))?\s*/i;e=n.exec(i);){var o=parseFloat(e[1]),s=parseFloat(e[2]),a=e[3]?parseFloat(e[3]):0;r.push(o,s,a),i=i.substr(e[0].length)}if(""===i)return r}function v_(t){var e=td(t,!1).trim(),i=t.baseURI;return i&&"about:blank"!=i||(i=window.location.href),i?new URL(e,i).href:e}function m_(t){return Rd(t)}var x_=fd(t_,{Pair:function(t,e){var i=gd({},Z_,t,e);if(!i)return;var r=i.key;if(r&&"normal"==r){var n=i.styleUrl;n&&(e[e.length-1]=n);var o=i.Style;o&&(e[e.length-1]=o)}}});function S_(t,e){return gd(void 0,x_,t,e)}var C_=fd(t_,{Icon:hd(function(t,e){var i=gd({},F_,t,e);return i||null}),heading:hd(Rd),hotSpot:hd(function(t){var e,i=t.getAttribute("xunits"),r=t.getAttribute("yunits");return e="insetPixels"!==i?"insetPixels"!==r?Jf.BOTTOM_LEFT:Jf.TOP_LEFT:"insetPixels"!==r?Jf.BOTTOM_RIGHT:Jf.TOP_RIGHT,{x:parseFloat(t.getAttribute("x")),xunits:e_[i],y:parseFloat(t.getAttribute("y")),yunits:e_[r],origin:e}}),scale:hd(m_)});var E_=fd(t_,{color:hd(g_),scale:hd(m_)});var T_=fd(t_,{color:hd(g_),width:hd(Rd)});var w_=fd(t_,{color:hd(g_),fill:hd(Ed),outline:hd(Ed)});var R_=fd(t_,{coordinates:sd(y_)});function I_(t,e){return gd(null,R_,t,e)}var L_=fd($f,{Track:od(P_)});var b_=fd(t_,{when:function(t,e){var i=e[e.length-1].whens,r=td(t,!1),n=Date.parse(r);i.push(isNaN(n)?0:n)}},fd($f,{coord:function(t,e){var i=e[e.length-1].flatCoordinates,r=td(t,!1),n=/^\s*([+\-]?\d+(?:\.\d*)?(?:e[+\-]?\d*)?)\s+([+\-]?\d+(?:\.\d*)?(?:e[+\-]?\d*)?)\s+([+\-]?\d+(?:\.\d*)?(?:e[+\-]?\d*)?)\s*$/i.exec(r);if(n){var o=parseFloat(n[1]),s=parseFloat(n[2]),a=parseFloat(n[3]);i.push(o,s,a,0)}else i.push(0,0,0,0)}}));function P_(t,e){var i=gd({flatCoordinates:[],whens:[]},b_,t,e);if(i){for(var r=i.flatCoordinates,n=i.whens,o=0,s=Math.min(r.length,n.length);o<s;++o)r[4*o+3]=n[o];return new Sn(r,yr.XYZM)}}var F_=fd(t_,{href:hd(v_)},fd($f,{x:hd(Rd),y:hd(Rd),w:hd(Rd),h:hd(Rd)}));var M_=fd(t_,{coordinates:sd(y_)});function O_(t,e){return gd(null,M_,t,e)}var N_=fd(t_,{extrude:hd(Ed),tessellate:hd(Ed),altitudeMode:hd(Pd)});function A_(t,e){var i=gd({},N_,t,e),r=O_(t,e);if(r){var n=new Sn(r,yr.XYZ);return n.setProperties(i),n}}function G_(t,e){var i=gd({},N_,t,e),r=O_(t,e);if(r){var n=new Qr(r,yr.XYZ,[r.length]);return n.setProperties(i),n}}var k_=fd(t_,{LineString:od(A_),LinearRing:od(G_),MultiGeometry:od(D_),Point:od(j_),Polygon:od(Y_)});function D_(t,e){var i,r=gd([],k_,t,e);if(!r)return null;if(0===r.length)return new Ef(r);for(var n,o,s=!0,a=r[0].getType(),h=1,l=r.length;h<l;++h)if(r[h].getType()!=a){s=!1;break}if(s)if(a==Lt.POINT){var u=r[0];n=u.getLayout(),o=u.getFlatCoordinates();for(var c=1,p=r.length;c<p;++c)pr(o,r[c].getFlatCoordinates());z_(i=new ih(o,n),r)}else a==Lt.LINE_STRING?z_(i=new eh(r),r):a==Lt.POLYGON?z_(i=new nh(r),r):a==Lt.GEOMETRY_COLLECTION?i=new Ef(r):Z(!1,37);else i=new Ef(r);return i}function j_(t,e){var i=gd({},N_,t,e),r=O_(t,e);if(r){var n=new Dr(r,yr.XYZ);return n.setProperties(i),n}}var U_=fd(t_,{innerBoundaryIs:function(t,e){var i=gd(void 0,$_,t,e);if(i){var r=e[e.length-1];r.push(i)}},outerBoundaryIs:function(t,e){var i=gd(void 0,tg,t,e);if(i){var r=e[e.length-1];r[0]=i}}});function Y_(t,e){var i=gd({},N_,t,e),r=gd([null],U_,t,e);if(r&&r[0]){for(var n=r[0],o=[n.length],s=1,a=r.length;s<a;++s)pr(n,r[s]),o.push(n.length);var h=new Qr(n,yr.XYZ,o);return h.setProperties(i),h}}var B_=fd(t_,{IconStyle:function(t,e){var i=gd({},C_,t,e);if(i){var r,n,o,s,a=e[e.length-1],h="Icon"in i?i.Icon:{},l=!("Icon"in i)||0<Object.keys(h).length,u=h.href;u?r=u:l&&(r=Kf);var c,p=Jf.BOTTOM_LEFT,d=i.hotSpot;d?(n=[d.x,d.y],o=d.xunits,s=d.yunits,p=d.origin):r===Kf?(n=Xf,o=zf,s=Vf):/^http:\/\/maps\.(?:google|gstatic)\.com\//.test(r)&&(n=[.5,0],o=Uf.FRACTION,s=Uf.FRACTION);var f,_=h.x,g=h.y;void 0!==_&&void 0!==g&&(c=[_,g]);var y,v=h.w,m=h.h;void 0!==v&&void 0!==m&&(f=[v,m]);var x=i.heading;void 0!==x&&(y=St(x));var S=i.scale;if(l){r==Kf&&(f=Wf,void 0===S&&(S=Hf));var C=new Qf({anchor:n,anchorOrigin:p,anchorXUnits:o,anchorYUnits:s,crossOrigin:"anonymous",offset:c,offsetOrigin:Jf.BOTTOM_LEFT,rotation:y,scale:S,size:f,src:r});a.imageStyle=C}else a.imageStyle=Zf}},LabelStyle:function(t,e){var i=gd({},E_,t,e);if(i){var r=e[e.length-1],n=new Ln({fill:new zi({color:"color"in i?i.color:Bf}),scale:i.scale});r.textStyle=n}},LineStyle:function(t,e){var i=gd({},T_,t,e);if(i){var r=e[e.length-1],n=new Vi({color:"color"in i?i.color:Bf,width:"width"in i?i.width:1});r.strokeStyle=n}},PolyStyle:function(t,e){var i=gd({},w_,t,e);if(i){var r=e[e.length-1],n=new zi({color:"color"in i?i.color:Bf});r.fillStyle=n;var o=i.fill;void 0!==o&&(r.fill=o);var s=i.outline;void 0!==s&&(r.outline=s)}}});function X_(t,e){var i=gd({},B_,t,e);if(!i)return null;var r="fillStyle"in i?i.fillStyle:h_,n=i.fill;void 0===n||n||(r=null);var o="imageStyle"in i?i.imageStyle:l_;o==Zf&&(o=void 0);var s="textStyle"in i?i.textStyle:c_,a="strokeStyle"in i?i.strokeStyle:u_,h=i.outline;return void 0===h||h||(a=null),[new Wi({fill:r,image:o,stroke:a,text:s,zIndex:void 0})]}function z_(t,e){var i,r,n,o=e.length,s=new Array(e.length),a=new Array(e.length),h=new Array(e.length);i=r=n=!1;for(var l=0;l<o;++l){var u=e[l];s[l]=u.get("extrude"),a[l]=u.get("tessellate"),h[l]=u.get("altitudeMode"),i=i||void 0!==s[l],r=r||void 0!==a[l],n=n||h[l]}i&&t.set("extrude",s),r&&t.set("tessellate",a),n&&t.set("altitudeMode",h)}var V_=fd(t_,{displayName:hd(Pd),value:hd(Pd)});var W_=fd(t_,{Data:function(t,e){var i=t.getAttribute("name");_d(V_,t,e);var r=e[e.length-1];null!==i?r[i]=r.value:null!==r.displayName&&(r[r.displayName]=r.value),delete r.value},SchemaData:function(t,e){_d(q_,t,e)}});function K_(t,e){_d(W_,t,e)}function H_(t,e){_d(o_,t,e)}var Z_=fd(t_,{Style:hd(X_),key:hd(Pd),styleUrl:hd(v_)});var q_=fd(t_,{SimpleData:function(t,e){var i=t.getAttribute("name");if(null!==i){var r=Pd(t),n=e[e.length-1];n[i]=r}}});var J_=fd(t_,{altitudeMode:hd(Pd),minAltitude:hd(Rd),maxAltitude:hd(Rd),north:hd(Rd),south:hd(Rd),east:hd(Rd),west:hd(Rd)});var Q_=fd(t_,{minLodPixels:hd(Rd),maxLodPixels:hd(Rd),minFadeExtent:hd(Rd),maxFadeExtent:hd(Rd)});var $_=fd(t_,{LinearRing:sd(I_)});var tg=fd(t_,{LinearRing:sd(I_)});function eg(t,e){for(var i=Ne(e),r=[255*(4==i.length?i[3]:1),i[2],i[1],i[0]],n=0;n<4;++n){var o=parseInt(r[n],10).toString(16);r[n]=1==o.length?"0"+o:o}Nd(t,r.join(""))}var ig=fd(t_,{Data:ld(function(t,e,i){t.setAttribute("name",e.name);var r={node:t},n=e.value;"object"==typeof n?(null!==n&&n.displayName&&vd(r,ig,pd,[n.displayName],i,["displayName"]),null!==n&&n.value&&vd(r,ig,pd,[n.value],i,["value"])):vd(r,ig,pd,[n],i,["value"])}),value:ld(function(t,e){Nd(t,e)}),displayName:ld(function(t,e){i=t,r=e,i.appendChild(Jp.createCDATASection(r));var i,r})});var rg=fd(t_,{Placemark:ld(Lg)}),ng=function(t,e,i){return $p(e[e.length-1].node.namespaceURI,"Placemark")};var og=cd("Data");var sg=fd(t_,["href"],fd($f,["x","y","w","h"])),ag=fd(t_,{href:ld(Nd)},fd($f,{x:ld(Md),y:ld(Md),w:ld(Md),h:ld(Md)})),hg=function(t,e,i){return $p($f[0],"gx:"+i)};var lg=fd(t_,["scale","heading","Icon","hotSpot"]),ug=fd(t_,{Icon:ld(function(t,e,i){var r={node:t},n=i[i.length-1].node,o=sg[n.namespaceURI],s=dd(e,o);vd(r,ag,pd,s,i,o),s=dd(e,o=sg[$f[0]]),vd(r,ag,hg,s,i,o)}),heading:ld(Md),hotSpot:ld(function(t,e){t.setAttribute("x",e.x),t.setAttribute("y",e.y),t.setAttribute("xunits",e.xunits),t.setAttribute("yunits",e.yunits)}),scale:ld(Dg)});var cg=fd(t_,["color","scale"]),pg=fd(t_,{color:ld(eg),scale:ld(Dg)});var dg=fd(t_,["color","width"]),fg=fd(t_,{color:ld(eg),width:ld(Md)});var _g={Point:"Point",LineString:"LineString",LinearRing:"LinearRing",Polygon:"Polygon",MultiPoint:"MultiGeometry",MultiLineString:"MultiGeometry",MultiPolygon:"MultiGeometry",GeometryCollection:"MultiGeometry"},gg=function(t,e,i){if(t)return $p(e[e.length-1].node.namespaceURI,_g[t.getType()])},yg=cd("Point"),vg=cd("LineString"),mg=cd("LinearRing"),xg=cd("Polygon"),Sg=fd(t_,{LineString:ld(Fg),Point:ld(Fg),Polygon:ld(Ag),GeometryCollection:ld(Cg)});function Cg(t,e,i){var r,n,o={node:t},s=e.getType();s==Lt.GEOMETRY_COLLECTION?(r=e.getGeometries(),n=gg):s==Lt.MULTI_POINT?(r=e.getPoints(),n=yg):s==Lt.MULTI_LINE_STRING?(r=e.getLineStrings(),n=vg):s==Lt.MULTI_POLYGON?(r=e.getPolygons(),n=xg):Z(!1,39),vd(o,Sg,n,r,i)}var Eg=fd(t_,{LinearRing:ld(Fg)});function Tg(t,e,i){vd({node:t},Eg,mg,[e],i)}var wg=fd(t_,{ExtendedData:ld(function(t,e,i){for(var r={node:t},n=e.names,o=e.values,s=n.length,a=0;a<s;a++)vd(r,ig,og,[{name:n[a],value:o[a]}],i)}),MultiGeometry:ld(Cg),LineString:ld(Fg),LinearRing:ld(Fg),Point:ld(Fg),Polygon:ld(Ag),Style:ld(function(t,e,i){var r={node:t},n={},o=e.getFill(),s=e.getStroke(),a=e.getImage(),h=e.getText();a instanceof Qf&&(n.IconStyle=a);h&&(n.LabelStyle=h);s&&(n.LineStyle=s);o&&(n.PolyStyle=o);var l=i[i.length-1].node,u=jg[l.namespaceURI],c=dd(n,u);vd(r,Ug,pd,c,i,u)}),address:ld(Nd),description:ld(Nd),name:ld(Nd),open:ld(Fd),phoneNumber:ld(Nd),styleUrl:ld(Nd),visibility:ld(Fd)}),Rg=fd(t_,["name","open","visibility","address","phoneNumber","description","styleUrl","Style"]),Ig=cd("ExtendedData");function Lg(t,e,i){var r={node:t};e.getId()&&t.setAttribute("id",e.getId());var n=e.getProperties(),o={address:1,description:1,name:1,open:1,phoneNumber:1,styleUrl:1,visibility:1};o[e.getGeometryName()]=1;var s=Object.keys(n||{}).sort().filter(function(t){return!o[t]});if(0<s.length){var a=dd(n,s);vd(r,wg,Ig,[{names:s,values:a}],i)}var h=e.getStyleFunction();if(h){var l=h(e,0);if(l){var u=Array.isArray(l)?l[0]:l;this.writeStyles_&&(n.Style=u);var c=u.getText();c&&(n.name=c.getText())}}var p=i[i.length-1].node,d=Rg[p.namespaceURI],f=dd(n,d);vd(r,wg,pd,f,i,d);var _=i[0],g=e.getGeometry();g&&(g=Yp(g,!0,_)),vd(r,wg,gg,[g],i)}var bg=fd(t_,["extrude","tessellate","altitudeMode","coordinates"]),Pg=fd(t_,{extrude:ld(Fd),tessellate:ld(Fd),altitudeMode:ld(Nd),coordinates:ld(function(t,e,i){var r,n=i[i.length-1],o=n.layout,s=n.stride;o==yr.XY||o==yr.XYM?r=2:o==yr.XYZ||o==yr.XYZM?r=3:Z(!1,34);var a=e.length,h="";if(0<a){h+=e[0];for(var l=1;l<r;++l)h+=","+e[l];for(var u=s;u<a;u+=s){h+=" "+e[u];for(var c=1;c<r;++c)h+=","+e[u+c]}}Nd(t,h)})});function Fg(t,e,i){var r=e.getFlatCoordinates(),n={node:t};n.layout=e.getLayout(),n.stride=e.getStride();var o=e.getProperties();o.coordinates=r;var s=i[i.length-1].node,a=bg[s.namespaceURI],h=dd(o,a);vd(n,Pg,pd,h,i,a)}var Mg=fd(t_,{outerBoundaryIs:ld(Tg),innerBoundaryIs:ld(Tg)}),Og=cd("innerBoundaryIs"),Ng=cd("outerBoundaryIs");function Ag(t,e,i){var r=e.getLinearRings(),n=r.shift(),o={node:t};vd(o,Mg,Og,r,i),vd(o,Mg,Ng,[n],i)}var Gg=fd(t_,{color:ld(eg)}),kg=cd("color");function Dg(t,e){Md(t,Math.round(1e6*e)/1e6)}var jg=fd(t_,["IconStyle","LabelStyle","LineStyle","PolyStyle"]),Ug=fd(t_,{IconStyle:ld(function(t,e,i){var r={node:t},n={},o=e.getSrc(),s=e.getSize(),a=e.getImageSize(),h={href:o};if(s){h.w=s[0],h.h=s[1];var l=e.getAnchor(),u=e.getOrigin();if(u&&a&&0!==u[0]&&u[1]!==s[1]&&(h.x=u[0],h.y=a[1]-(u[1]+s[1])),l&&(l[0]!==s[0]/2||l[1]!==s[1]/2)){var c={x:l[0],xunits:Uf.PIXELS,y:s[1]-l[1],yunits:Uf.PIXELS};n.hotSpot=c}}n.Icon=h;var p=e.getScale();1!==p&&(n.scale=p);var d=e.getRotation();0!==d&&(n.heading=d);var f=i[i.length-1].node,_=lg[f.namespaceURI],g=dd(n,_);vd(r,ug,pd,g,i,_)}),LabelStyle:ld(function(t,e,i){var r={node:t},n={},o=e.getFill();o&&(n.color=o.getColor());var s=e.getScale();s&&1!==s&&(n.scale=s);var a=i[i.length-1].node,h=cg[a.namespaceURI],l=dd(n,h);vd(r,pg,pd,l,i,h)}),LineStyle:ld(function(t,e,i){var r={node:t},n={color:e.getColor(),width:e.getWidth()},o=i[i.length-1].node,s=dg[o.namespaceURI],a=dd(n,s);vd(r,fg,pd,a,i,s)}),PolyStyle:ld(function(t,e,i){vd({node:t},Gg,kg,[e.getColor()],i)})});var Yg=function(t,e,i,r,n){var o,s,a=8*n-r-1,h=(1<<a)-1,l=h>>1,u=-7,c=i?n-1:0,p=i?-1:1,d=t[e+c];for(c+=p,o=d&(1<<-u)-1,d>>=-u,u+=a;0<u;o=256*o+t[e+c],c+=p,u-=8);for(s=o&(1<<-u)-1,o>>=-u,u+=r;0<u;s=256*s+t[e+c],c+=p,u-=8);if(0===o)o=1-l;else{if(o===h)return s?NaN:1/0*(d?-1:1);s+=Math.pow(2,r),o-=l}return(d?-1:1)*s*Math.pow(2,o-r)},Bg=function(t,e,i,r,n,o){var s,a,h,l=8*o-n-1,u=(1<<l)-1,c=u>>1,p=23===n?Math.pow(2,-24)-Math.pow(2,-77):0,d=r?0:o-1,f=r?1:-1,_=e<0||0===e&&1/e<0?1:0;for(e=Math.abs(e),isNaN(e)||e===1/0?(a=isNaN(e)?1:0,s=u):(s=Math.floor(Math.log(e)/Math.LN2),e*(h=Math.pow(2,-s))<1&&(s--,h*=2),2<=(e+=1<=s+c?p/h:p*Math.pow(2,1-c))*h&&(s++,h/=2),u<=s+c?(a=0,s=u):1<=s+c?(a=(e*h-1)*Math.pow(2,n),s+=c):(a=e*Math.pow(2,c-1)*Math.pow(2,n),s=0));8<=n;t[i+d]=255&a,d+=f,a/=256,n-=8);for(s=s<<n|a,l+=n;0<l;t[i+d]=255&s,d+=f,s/=256,l-=8);t[i+d-f]|=128*_},Xg=zg;function zg(t){this.buf=ArrayBuffer.isView&&ArrayBuffer.isView(t)?t:new Uint8Array(t||0),this.pos=0,this.type=0,this.length=this.buf.length}zg.Varint=0,zg.Fixed64=1,zg.Bytes=2,zg.Fixed32=5;var Vg=4294967296,Wg=1/Vg;function Kg(t){return t.type===zg.Bytes?t.readVarint()+t.pos:t.pos+1}function Hg(t,e,i){return i?4294967296*e+(t>>>0):4294967296*(e>>>0)+(t>>>0)}function Zg(t,e,i){var r=e<=16383?1:e<=2097151?2:e<=268435455?3:Math.ceil(Math.log(e)/(7*Math.LN2));i.realloc(r);for(var n=i.pos-1;t<=n;n--)i.buf[n+r]=i.buf[n]}function qg(t,e){for(var i=0;i<t.length;i++)e.writeVarint(t[i])}function Jg(t,e){for(var i=0;i<t.length;i++)e.writeSVarint(t[i])}function Qg(t,e){for(var i=0;i<t.length;i++)e.writeFloat(t[i])}function $g(t,e){for(var i=0;i<t.length;i++)e.writeDouble(t[i])}function ty(t,e){for(var i=0;i<t.length;i++)e.writeBoolean(t[i])}function ey(t,e){for(var i=0;i<t.length;i++)e.writeFixed32(t[i])}function iy(t,e){for(var i=0;i<t.length;i++)e.writeSFixed32(t[i])}function ry(t,e){for(var i=0;i<t.length;i++)e.writeFixed64(t[i])}function ny(t,e){for(var i=0;i<t.length;i++)e.writeSFixed64(t[i])}function oy(t,e){return(t[e]|t[e+1]<<8|t[e+2]<<16)+16777216*t[e+3]}function sy(t,e,i){t[i]=e,t[i+1]=e>>>8,t[i+2]=e>>>16,t[i+3]=e>>>24}function ay(t,e){return(t[e]|t[e+1]<<8|t[e+2]<<16)+(t[e+3]<<24)}zg.prototype={destroy:function(){this.buf=null},readFields:function(t,e,i){for(i=i||this.length;this.pos<i;){var r=this.readVarint(),n=r>>3,o=this.pos;this.type=7&r,t(n,e,this),this.pos===o&&this.skip(r)}return e},readMessage:function(t,e){return this.readFields(t,e,this.readVarint()+this.pos)},readFixed32:function(){var t=oy(this.buf,this.pos);return this.pos+=4,t},readSFixed32:function(){var t=ay(this.buf,this.pos);return this.pos+=4,t},readFixed64:function(){var t=oy(this.buf,this.pos)+oy(this.buf,this.pos+4)*Vg;return this.pos+=8,t},readSFixed64:function(){var t=oy(this.buf,this.pos)+ay(this.buf,this.pos+4)*Vg;return this.pos+=8,t},readFloat:function(){var t=Yg(this.buf,this.pos,!0,23,4);return this.pos+=4,t},readDouble:function(){var t=Yg(this.buf,this.pos,!0,52,8);return this.pos+=8,t},readVarint:function(t){var e,i,r=this.buf;return e=127&(i=r[this.pos++]),i<128?e:(e|=(127&(i=r[this.pos++]))<<7,i<128?e:(e|=(127&(i=r[this.pos++]))<<14,i<128?e:(e|=(127&(i=r[this.pos++]))<<21,i<128?e:function(t,e,i){var r,n,o=i.buf;if(n=o[i.pos++],r=(112&n)>>4,n<128)return Hg(t,r,e);if(n=o[i.pos++],r|=(127&n)<<3,n<128)return Hg(t,r,e);if(n=o[i.pos++],r|=(127&n)<<10,n<128)return Hg(t,r,e);if(n=o[i.pos++],r|=(127&n)<<17,n<128)return Hg(t,r,e);if(n=o[i.pos++],r|=(127&n)<<24,n<128)return Hg(t,r,e);if(n=o[i.pos++],r|=(1&n)<<31,n<128)return Hg(t,r,e);throw new Error("Expected varint not more than 10 bytes")}(e|=(15&(i=r[this.pos]))<<28,t,this))))},readVarint64:function(){return this.readVarint(!0)},readSVarint:function(){var t=this.readVarint();return t%2==1?(t+1)/-2:t/2},readBoolean:function(){return Boolean(this.readVarint())},readString:function(){var t=this.readVarint()+this.pos,e=function(t,e,i){var r="",n=e;for(;n<i;){var o,s,a,h=t[n],l=null,u=239<h?4:223<h?3:191<h?2:1;if(i<n+u)break;1===u?h<128&&(l=h):2===u?128==(192&(o=t[n+1]))&&(l=(31&h)<<6|63&o)<=127&&(l=null):3===u?(o=t[n+1],s=t[n+2],128==(192&o)&&128==(192&s)&&((l=(15&h)<<12|(63&o)<<6|63&s)<=2047||55296<=l&&l<=57343)&&(l=null)):4===u&&(o=t[n+1],s=t[n+2],a=t[n+3],128==(192&o)&&128==(192&s)&&128==(192&a)&&((l=(15&h)<<18|(63&o)<<12|(63&s)<<6|63&a)<=65535||1114112<=l)&&(l=null)),null===l?(l=65533,u=1):65535<l&&(l-=65536,r+=String.fromCharCode(l>>>10&1023|55296),l=56320|1023&l),r+=String.fromCharCode(l),n+=u}return r}(this.buf,this.pos,t);return this.pos=t,e},readBytes:function(){var t=this.readVarint()+this.pos,e=this.buf.subarray(this.pos,t);return this.pos=t,e},readPackedVarint:function(t,e){var i=Kg(this);for(t=t||[];this.pos<i;)t.push(this.readVarint(e));return t},readPackedSVarint:function(t){var e=Kg(this);for(t=t||[];this.pos<e;)t.push(this.readSVarint());return t},readPackedBoolean:function(t){var e=Kg(this);for(t=t||[];this.pos<e;)t.push(this.readBoolean());return t},readPackedFloat:function(t){var e=Kg(this);for(t=t||[];this.pos<e;)t.push(this.readFloat());return t},readPackedDouble:function(t){var e=Kg(this);for(t=t||[];this.pos<e;)t.push(this.readDouble());return t},readPackedFixed32:function(t){var e=Kg(this);for(t=t||[];this.pos<e;)t.push(this.readFixed32());return t},readPackedSFixed32:function(t){var e=Kg(this);for(t=t||[];this.pos<e;)t.push(this.readSFixed32());return t},readPackedFixed64:function(t){var e=Kg(this);for(t=t||[];this.pos<e;)t.push(this.readFixed64());return t},readPackedSFixed64:function(t){var e=Kg(this);for(t=t||[];this.pos<e;)t.push(this.readSFixed64());return t},skip:function(t){var e=7&t;if(e===zg.Varint)for(;127<this.buf[this.pos++];);else if(e===zg.Bytes)this.pos=this.readVarint()+this.pos;else if(e===zg.Fixed32)this.pos+=4;else{if(e!==zg.Fixed64)throw new Error("Unimplemented type: "+e);this.pos+=8}},writeTag:function(t,e){this.writeVarint(t<<3|e)},realloc:function(t){for(var e=this.length||16;e<this.pos+t;)e*=2;if(e!==this.length){var i=new Uint8Array(e);i.set(this.buf),this.buf=i,this.length=e}},finish:function(){return this.length=this.pos,this.pos=0,this.buf.subarray(0,this.length)},writeFixed32:function(t){this.realloc(4),sy(this.buf,t,this.pos),this.pos+=4},writeSFixed32:function(t){this.realloc(4),sy(this.buf,t,this.pos),this.pos+=4},writeFixed64:function(t){this.realloc(8),sy(this.buf,-1&t,this.pos),sy(this.buf,Math.floor(t*Wg),this.pos+4),this.pos+=8},writeSFixed64:function(t){this.realloc(8),sy(this.buf,-1&t,this.pos),sy(this.buf,Math.floor(t*Wg),this.pos+4),this.pos+=8},writeVarint:function(t){268435455<(t=+t||0)||t<0?function(t,e){var i,r;0<=t?(i=t%4294967296|0,r=t/4294967296|0):(r=~(-t/4294967296),4294967295^(i=~(-t%4294967296))?i=i+1|0:r=r+1|(i=0));if(0x10000000000000000<=t||t<-0x10000000000000000)throw new Error("Given varint doesn't fit into 10 bytes");e.realloc(10),n=i,o=e,o.buf[o.pos++]=127&n|128,n>>>=7,o.buf[o.pos++]=127&n|128,n>>>=7,o.buf[o.pos++]=127&n|128,n>>>=7,o.buf[o.pos++]=127&n|128,n>>>=7,o.buf[o.pos]=127&n,function(t,e){var i=(7&t)<<4;if(e.buf[e.pos++]|=i|((t>>>=3)?128:0),!t)return;if(e.buf[e.pos++]=127&t|((t>>>=7)?128:0),!t)return;if(e.buf[e.pos++]=127&t|((t>>>=7)?128:0),!t)return;if(e.buf[e.pos++]=127&t|((t>>>=7)?128:0),!t)return;if(e.buf[e.pos++]=127&t|((t>>>=7)?128:0),!t)return;e.buf[e.pos++]=127&t}(r,e);var n,o}(t,this):(this.realloc(4),this.buf[this.pos++]=127&t|(127<t?128:0),t<=127||(this.buf[this.pos++]=127&(t>>>=7)|(127<t?128:0),t<=127||(this.buf[this.pos++]=127&(t>>>=7)|(127<t?128:0),t<=127||(this.buf[this.pos++]=t>>>7&127))))},writeSVarint:function(t){this.writeVarint(t<0?2*-t-1:2*t)},writeBoolean:function(t){this.writeVarint(Boolean(t))},writeString:function(t){t=String(t),this.realloc(4*t.length),this.pos++;var e=this.pos;this.pos=function(t,e,i){for(var r,n,o=0;o<e.length;o++){if(55295<(r=e.charCodeAt(o))&&r<57344){if(!n){56319<r||o+1===e.length?(t[i++]=239,t[i++]=191,t[i++]=189):n=r;continue}if(r<56320){t[i++]=239,t[i++]=191,t[i++]=189,n=r;continue}r=n-55296<<10|r-56320|65536,n=null}else n&&(t[i++]=239,t[i++]=191,t[i++]=189,n=null);r<128?t[i++]=r:(r<2048?t[i++]=r>>6|192:(r<65536?t[i++]=r>>12|224:(t[i++]=r>>18|240,t[i++]=r>>12&63|128),t[i++]=r>>6&63|128),t[i++]=63&r|128)}return i}(this.buf,t,this.pos);var i=this.pos-e;128<=i&&Zg(e,i,this),this.pos=e-1,this.writeVarint(i),this.pos+=i},writeFloat:function(t){this.realloc(4),Bg(this.buf,t,this.pos,!0,23,4),this.pos+=4},writeDouble:function(t){this.realloc(8),Bg(this.buf,t,this.pos,!0,52,8),this.pos+=8},writeBytes:function(t){var e=t.length;this.writeVarint(e),this.realloc(e);for(var i=0;i<e;i++)this.buf[this.pos++]=t[i]},writeRawMessage:function(t,e){this.pos++;var i=this.pos;t(e,this);var r=this.pos-i;128<=r&&Zg(i,r,this),this.pos=i-1,this.writeVarint(r),this.pos+=r},writeMessage:function(t,e,i){this.writeTag(t,zg.Bytes),this.writeRawMessage(e,i)},writePackedVarint:function(t,e){this.writeMessage(t,qg,e)},writePackedSVarint:function(t,e){this.writeMessage(t,Jg,e)},writePackedBoolean:function(t,e){this.writeMessage(t,ty,e)},writePackedFloat:function(t,e){this.writeMessage(t,Qg,e)},writePackedDouble:function(t,e){this.writeMessage(t,$g,e)},writePackedFixed32:function(t,e){this.writeMessage(t,ey,e)},writePackedSFixed32:function(t,e){this.writeMessage(t,iy,e)},writePackedFixed64:function(t,e){this.writeMessage(t,ry,e)},writePackedSFixed64:function(t,e){this.writeMessage(t,ny,e)},writeBytesField:function(t,e){this.writeTag(t,zg.Bytes),this.writeBytes(e)},writeFixed32Field:function(t,e){this.writeTag(t,zg.Fixed32),this.writeFixed32(e)},writeSFixed32Field:function(t,e){this.writeTag(t,zg.Fixed32),this.writeSFixed32(e)},writeFixed64Field:function(t,e){this.writeTag(t,zg.Fixed64),this.writeFixed64(e)},writeSFixed64Field:function(t,e){this.writeTag(t,zg.Fixed64),this.writeSFixed64(e)},writeVarintField:function(t,e){this.writeTag(t,zg.Varint),this.writeVarint(e)},writeSVarintField:function(t,e){this.writeTag(t,zg.Varint),this.writeSVarint(e)},writeStringField:function(t,e){this.writeTag(t,zg.Bytes),this.writeString(e)},writeFloatField:function(t,e){this.writeTag(t,zg.Fixed32),this.writeFloat(e)},writeDoubleField:function(t,e){this.writeTag(t,zg.Fixed64),this.writeDouble(e)},writeBooleanField:function(t,e){this.writeVarintField(t,Boolean(e))}};var hy=[1,0,0,1,0,0],ly=function(t,e,i,r,n){this.extent_,this.id_=n,this.type_=t,this.flatCoordinates_=e,this.flatInteriorPoints_=null,this.flatMidpoints_=null,this.ends_=i,this.properties_=r};ly.prototype.get=function(t){return this.properties_[t]},ly.prototype.getExtent=function(){return this.extent_||(this.extent_=this.type_===Lt.POINT?V(this.flatCoordinates_):K(this.flatCoordinates_,0,this.flatCoordinates_.length,2)),this.extent_},ly.prototype.getFlatInteriorPoint=function(){if(!this.flatInteriorPoints_){var t=ot(this.getExtent());this.flatInteriorPoints_=Br(this.flatCoordinates_,0,this.ends_,2,t,0)}return this.flatInteriorPoints_},ly.prototype.getFlatInteriorPoints=function(){if(!this.flatInteriorPoints_){var t=rh(this.flatCoordinates_,0,this.ends_,2);this.flatInteriorPoints_=Xr(this.flatCoordinates_,0,this.ends_,2,t)}return this.flatInteriorPoints_},ly.prototype.getFlatMidpoint=function(){return this.flatMidpoints_||(this.flatMidpoints_=vn(this.flatCoordinates_,0,this.flatCoordinates_.length,2,.5)),this.flatMidpoints_},ly.prototype.getFlatMidpoints=function(){if(!this.flatMidpoints_){this.flatMidpoints_=[];for(var t=this.flatCoordinates_,e=0,i=this.ends_,r=0,n=i.length;r<n;++r){var o=i[r],s=vn(t,e,o,2,.5);pr(this.flatMidpoints_,s),e=o}}return this.flatMidpoints_},ly.prototype.getId=function(){return this.id_},ly.prototype.getOrientedFlatCoordinates=function(){return this.flatCoordinates_},ly.prototype.getGeometry=function(){return this},ly.prototype.getProperties=function(){return this.properties_},ly.prototype.getStride=function(){return 2},ly.prototype.getType=function(){return this.type_},ly.prototype.transform=function(t,e){var i=(t=ne(t)).getExtent(),r=t.getWorldExtent(),n=at(r)/at(i);Te(hy,r[0],r[3],n,-n,0,0,0),Rt(this.flatCoordinates_,0,this.flatCoordinates_.length,2,hy,this.flatCoordinates_)},ly.prototype.getEnds=ly.prototype.getEndss=function(){return this.ends_},ly.prototype.getFlatCoordinates=ly.prototype.getOrientedFlatCoordinates,ly.prototype.getSimplifiedGeometry=ly.prototype.getGeometry,ly.prototype.getStyleFunction=L;var uy=function(i){function t(t){i.call(this);var e=t||{};this.dataProjection=new At({code:"",units:Ot.TILE_PIXELS}),this.featureClass_=e.featureClass?e.featureClass:ly,this.geometryName_=e.geometryName,this.layerName_=e.layerName?e.layerName:"layer",this.layers_=e.layers?e.layers:null,this.extent_=null}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.readRawGeometry_=function(t,e,i,r){t.pos=e.geometry;for(var n=t.readVarint()+t.pos,o=1,s=0,a=0,h=0,l=0,u=0;t.pos<n;){if(!s){var c=t.readVarint();o=7&c,s=c>>3}s--,1===o||2===o?(a+=t.readSVarint(),h+=t.readSVarint(),1===o&&u<l&&(r.push(l),u=l),i.push(a,h),l+=2):7===o?u<l&&(i.push(i[u],i[u+1]),l+=2):Z(!1,59)}u<l&&(r.push(l),u=l)},t.prototype.createFeature_=function(t,e,i){var r,n=e.type;if(0===n)return null;var o=e.id,s=e.properties;s[this.layerName_]=e.layer.name;var a=[],h=[];this.readRawGeometry_(t,e,a,h);var l=function(t,e){var i;1===t?i=1===e?Lt.POINT:Lt.MULTI_POINT:2===t?i=1===e?Lt.LINE_STRING:Lt.MULTI_LINE_STRING:3===t&&(i=Lt.POLYGON);return i}(n,h.length);if(this.featureClass_===ly)r=new this.featureClass_(l,a,h,s,o);else{var u;if(l==Lt.POLYGON){for(var c=[],p=0,d=0,f=0,_=h.length;f<_;++f){var g=h[f];Hr(a,p,g,2)||(c.push(h.slice(d,f)),d=f),p=g}u=1<c.length?new nh(a,yr.XY,c):new Qr(a,yr.XY,h)}else u=l===Lt.POINT?new Dr(a,yr.XY):l===Lt.LINE_STRING?new Sn(a,yr.XY):l===Lt.POLYGON?new Qr(a,yr.XY,h):l===Lt.MULTI_POINT?new ih(a,yr.XY):l===Lt.MULTI_LINE_STRING?new eh(a,yr.XY,h):null;r=new this.featureClass_,this.geometryName_&&r.setGeometryName(this.geometryName_);var y=Yp(u,!1,this.adaptOptions(i));r.setGeometry(y),r.setId(o),r.setProperties(s)}return r},t.prototype.getLastExtent=function(){return this.extent_},t.prototype.getType=function(){return uh.ARRAY_BUFFER},t.prototype.readFeatures=function(t,e){var i=this.layers_,r=new Xg(t),n=r.readFields(cy,{}),o=[];for(var s in n)if(!i||-1!=i.indexOf(s)){for(var a=n[s],h=0,l=a.length;h<l;++h){var u=fy(r,a,h);o.push(this.createFeature_(r,u))}this.extent_=a?[0,0,a.extent,a.extent]:null}return o},t.prototype.readProjection=function(t){return this.dataProjection},t.prototype.setLayers=function(t){this.layers_=t},t.prototype.readFeature=function(){},t.prototype.readGeometry=function(){},t.prototype.writeFeature=function(){},t.prototype.writeGeometry=function(){},t.prototype.writeFeatures=function(){},t}(Up);function cy(t,e,i){if(3===t){var r={keys:[],values:[],features:[]},n=i.readVarint()+i.pos;i.readFields(py,r,n),r.length=r.features.length,r.length&&(e[r.name]=r)}}function py(t,e,i){if(15===t)e.version=i.readVarint();else if(1===t)e.name=i.readString();else if(5===t)e.extent=i.readVarint();else if(2===t)e.features.push(i.pos);else if(3===t)e.keys.push(i.readString());else if(4===t){for(var r=null,n=i.readVarint()+i.pos;i.pos<n;)r=1===(t=i.readVarint()>>3)?i.readString():2===t?i.readFloat():3===t?i.readDouble():4===t?i.readVarint64():5===t?i.readVarint():6===t?i.readSVarint():7===t?i.readBoolean():null;e.values.push(r)}}function dy(t,e,i){if(1==t)e.id=i.readVarint();else if(2==t)for(var r=i.readVarint()+i.pos;i.pos<r;){var n=e.layer.keys[i.readVarint()],o=e.layer.values[i.readVarint()];e.properties[n]=o}else 3==t?e.type=i.readVarint():4==t&&(e.geometry=i.pos)}function fy(t,e,i){t.pos=e.features[i];var r=t.readVarint()+t.pos,n={layer:e,type:0,properties:{}};return t.readFields(dy,n,r),n}var _y=[null],gy=fd(_y,{nd:function(t,e){e[e.length-1].ndrefs.push(t.getAttribute("ref"))},tag:xy}),yy=fd(_y,{node:function(t,e){var i=e[0],r=e[e.length-1],n=t.getAttribute("id"),o=[parseFloat(t.getAttribute("lon")),parseFloat(t.getAttribute("lat"))];r.nodes[n]=o;var s=gd({tags:{}},my,t,e);if(!Tt(s.tags)){var a=new Dr(o);Yp(a,!1,i);var h=new Ji(a);h.setId(n),h.setProperties(s.tags),r.features.push(h)}},way:function(t,e){var i=gd({id:t.getAttribute("id"),ndrefs:[],tags:{}},gy,t,e);e[e.length-1].ways.push(i)}}),vy=function(t){function e(){t.call(this),this.dataProjection=ne("EPSG:4326")}return t&&(e.__proto__=t),((e.prototype=Object.create(t&&t.prototype)).constructor=e).prototype.readFeaturesFromNode=function(t,e){var i=this.getReadOptions(t,e);if("osm"==t.localName){for(var r=gd({nodes:{},ways:[],features:[]},yy,t,[i]),n=0;n<r.ways.length;n++){for(var o=r.ways[n],s=[],a=0,h=o.ndrefs.length;a<h;a++){pr(s,r.nodes[o.ndrefs[a]])}var l=void 0;Yp(l=o.ndrefs[0]==o.ndrefs[o.ndrefs.length-1]?new Qr(s,yr.XY,[s.length]):new Sn(s,yr.XY),!1,i);var u=new Ji(l);u.setId(o.id),u.setProperties(o.tags),r.features.push(u)}if(r.features)return r.features}return[]},e.prototype.writeFeatureNode=function(t,e){},e.prototype.writeFeaturesNode=function(t,e){},e.prototype.writeGeometryNode=function(t,e){},e}(md),my=fd(_y,{tag:xy});function xy(t,e){e[e.length-1].tags[t.getAttribute("k")]=t.getAttribute("v")}function Sy(t,e,i,r,n,o){var s,a;void 0!==n?(s=n,a=void 0!==o?o:0):(s=[],a=0);for(var h=e;h<i;){var l=t[h++];s[a++]=t[h++],s[a++]=l;for(var u=2;u<r;++u)s[a++]=t[h++]}return s.length=a,s}var Cy=function(i){function t(t){i.call(this);var e=t||{};this.dataProjection=ne("EPSG:4326"),this.factor_=e.factor?e.factor:1e5,this.geometryLayout_=e.geometryLayout?e.geometryLayout:yr.XY}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.readFeatureFromText=function(t,e){var i=this.readGeometryFromText(t,e);return new Ji(i)},t.prototype.readFeaturesFromText=function(t,e){return[this.readFeatureFromText(t,e)]},t.prototype.readGeometryFromText=function(t,e){var i=mr(this.geometryLayout_),r=Ty(t,i,this.factor_);Sy(r,0,r.length,i,r);var n=Pr(r,0,r.length,i);return Yp(new Sn(n,this.geometryLayout_),!1,this.adaptOptions(e))},t.prototype.writeFeatureText=function(t,e){var i=t.getGeometry();return i?this.writeGeometryText(i,e):(Z(!1,40),"")},t.prototype.writeFeaturesText=function(t,e){return this.writeFeatureText(t[0],e)},t.prototype.writeGeometryText=function(t,e){var i=(t=Yp(t,!0,this.adaptOptions(e))).getFlatCoordinates(),r=t.getStride();return Sy(i,0,i.length,r,i),Ey(i,r,this.factor_)},t}(Pf);function Ey(t,e,i){var r,n=i||1e5,o=new Array(e);for(r=0;r<e;++r)o[r]=0;for(var s=0,a=t.length;s<a;)for(r=0;r<e;++r,++s){var h=t[s],l=h-o[r];o[r]=h,t[s]=l}return wy(t,n)}function Ty(t,e,i){var r,n=i||1e5,o=new Array(e);for(r=0;r<e;++r)o[r]=0;for(var s=Ry(t,n),a=0,h=s.length;a<h;)for(r=0;r<e;++r,++a)o[r]+=s[a],s[a]=o[r];return s}function wy(t,e){for(var i=e||1e5,r=0,n=t.length;r<n;++r)t[r]=Math.round(t[r]*i);return function(t){for(var e=0,i=t.length;e<i;++e){var r=t[e];t[e]=r<0?~(r<<1):r<<1}return function(t){for(var e="",i=0,r=t.length;i<r;++i)e+=Iy(t[i]);return e}(t)}(t)}function Ry(t,e){for(var i=e||1e5,r=function(t){for(var e=function(t){for(var e=[],i=0,r=0,n=0,o=t.length;n<o;++n){var s=t.charCodeAt(n)-63;i|=(31&s)<<r,s<32?(e.push(i),r=i=0):r+=5}return e}(t),i=0,r=e.length;i<r;++i){var n=e[i];e[i]=1&n?~(n>>1):n>>1}return e}(t),n=0,o=r.length;n<o;++n)r[n]/=i;return r}function Iy(t){for(var e,i="";32<=t;)e=63+(32|31&t),i+=String.fromCharCode(e),t>>=5;return e=t+63,i+=String.fromCharCode(e)}var Ly=function(i){function t(t){i.call(this);var e=t||{};this.layerName_=e.layerName,this.layers_=e.layers?e.layers:null,this.dataProjection=ne(e.dataProjection?e.dataProjection:"EPSG:4326")}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.readFeaturesFromObject=function(t,e){if("Topology"==t.type){var i,r=t,n=null,o=null;r.transform&&(n=(i=r.transform).scale,o=i.translate);var s=r.arcs;i&&function(t,e,i){for(var r=0,n=t.length;r<n;++r)Oy(t[r],e,i)}(s,n,o);var a,h=[],l=r.objects,u=this.layerName_;for(var c in l)this.layers_&&-1==this.layers_.indexOf(c)||("GeometryCollection"===l[c].type?(a=l[c],h.push.apply(h,Fy(a,s,n,o,u,c,e))):(a=l[c],h.push(My(a,s,n,o,u,c,e))));return h}return[]},t.prototype.readProjectionFromObject=function(t){return this.dataProjection},t.prototype.writeFeatureObject=function(t,e){},t.prototype.writeFeaturesObject=function(t,e){},t.prototype.writeGeometryObject=function(t,e){},t.prototype.readGeometryFromObject=function(){},t.prototype.readFeatureFromObject=function(){},t}(Bp),by={Point:function(t,e,i){var r=t.coordinates;e&&i&&Ny(r,e,i);return new Dr(r)},LineString:function(t,e){var i=Py(t.arcs,e);return new Sn(i)},Polygon:function(t,e){for(var i=[],r=0,n=t.arcs.length;r<n;++r)i[r]=Py(t.arcs[r],e);return new Qr(i)},MultiPoint:function(t,e,i){var r=t.coordinates;if(e&&i)for(var n=0,o=r.length;n<o;++n)Ny(r[n],e,i);return new ih(r)},MultiLineString:function(t,e){for(var i=[],r=0,n=t.arcs.length;r<n;++r)i[r]=Py(t.arcs[r],e);return new eh(i)},MultiPolygon:function(t,e){for(var i=[],r=0,n=t.arcs.length;r<n;++r){for(var o=t.arcs[r],s=[],a=0,h=o.length;a<h;++a)s[a]=Py(o[a],e);i[r]=s}return new nh(i)}};function Py(t,e){for(var i,r,n=[],o=0,s=t.length;o<s;++o)i=t[o],0<o&&n.pop(),r=0<=i?e[i]:e[~i].slice().reverse(),n.push.apply(n,r);for(var a=0,h=n.length;a<h;++a)n[a]=n[a].slice();return n}function Fy(t,e,i,r,n,o,s){for(var a=t.geometries,h=[],l=0,u=a.length;l<u;++l)h[l]=My(a[l],e,i,r,n,o,s);return h}function My(t,e,i,r,n,o,s){var a,h=t.type,l=by[h];a="Point"===h||"MultiPoint"===h?l(t,i,r):l(t,e);var u=new Ji;u.setGeometry(Yp(a,!1,s)),void 0!==t.id&&u.setId(t.id);var c=t.properties;return n&&(c||(c={}),c[n]=o),c&&u.setProperties(c),u}function Oy(t,e,i){for(var r=0,n=0,o=0,s=t.length;o<s;++o){var a=t[o];r+=a[0],n+=a[1],a[0]=r,a[1]=n,Ny(a,e,i)}}function Ny(t,e,i){t[0]=t[0]*e[0]+i[0],t[1]=t[1]*e[1]+i[1]}var Ay=function(t){this.tagName_=t};Ay.prototype.getTagName=function(){return this.tagName_};var Gy=function(i){function t(t,e){i.call(this,t),this.conditions=Array.prototype.slice.call(arguments,1),Z(2<=this.conditions.length,57)}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(Ay),ky=function(i){function t(t){var e=["And"].concat(Array.prototype.slice.call(arguments));i.apply(this,e)}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(Gy),Dy=function(r){function t(t,e,i){r.call(this,"BBOX"),this.geometryName=t,this.extent=e,this.srsName=i}return r&&(t.__proto__=r),(t.prototype=Object.create(r&&r.prototype)).constructor=t}(Ay),jy=function(n){function t(t,e,i,r){n.call(this,t),this.geometryName=e||"the_geom",this.geometry=i,this.srsName=r}return n&&(t.__proto__=n),(t.prototype=Object.create(n&&n.prototype)).constructor=t}(Ay),Uy=function(r){function t(t,e,i){r.call(this,"Contains",t,e,i)}return r&&(t.__proto__=r),(t.prototype=Object.create(r&&r.prototype)).constructor=t}(jy),Yy=function(i){function t(t,e){i.call(this,t),this.propertyName=e}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(Ay),By=function(r){function t(t,e,i){r.call(this,"During",t),this.begin=e,this.end=i}return r&&(t.__proto__=r),(t.prototype=Object.create(r&&r.prototype)).constructor=t}(Yy),Xy=function(n){function t(t,e,i,r){n.call(this,t,e),this.expression=i,this.matchCase=r}return n&&(t.__proto__=n),(t.prototype=Object.create(n&&n.prototype)).constructor=t}(Yy),zy=function(r){function t(t,e,i){r.call(this,"PropertyIsEqualTo",t,e,i)}return r&&(t.__proto__=r),(t.prototype=Object.create(r&&r.prototype)).constructor=t}(Xy),Vy=function(i){function t(t,e){i.call(this,"PropertyIsGreaterThan",t,e)}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(Xy),Wy=function(i){function t(t,e){i.call(this,"PropertyIsGreaterThanOrEqualTo",t,e)}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(Xy),Ky=function(r){function t(t,e,i){r.call(this,"Intersects",t,e,i)}return r&&(t.__proto__=r),(t.prototype=Object.create(r&&r.prototype)).constructor=t}(jy),Hy=function(r){function t(t,e,i){r.call(this,"PropertyIsBetween",t),this.lowerBoundary=e,this.upperBoundary=i}return r&&(t.__proto__=r),(t.prototype=Object.create(r&&r.prototype)).constructor=t}(Yy),Zy=function(s){function t(t,e,i,r,n,o){s.call(this,"PropertyIsLike",t),this.pattern=e,this.wildCard=void 0!==i?i:"*",this.singleChar=void 0!==r?r:".",this.escapeChar=void 0!==n?n:"!",this.matchCase=o}return s&&(t.__proto__=s),(t.prototype=Object.create(s&&s.prototype)).constructor=t}(Yy),qy=function(e){function t(t){e.call(this,"PropertyIsNull",t)}return e&&(t.__proto__=e),(t.prototype=Object.create(e&&e.prototype)).constructor=t}(Yy),Jy=function(i){function t(t,e){i.call(this,"PropertyIsLessThan",t,e)}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(Xy),Qy=function(i){function t(t,e){i.call(this,"PropertyIsLessThanOrEqualTo",t,e)}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(Xy),$y=function(e){function t(t){e.call(this,"Not"),this.condition=t}return e&&(t.__proto__=e),(t.prototype=Object.create(e&&e.prototype)).constructor=t}(Ay),tv=function(r){function t(t,e,i){r.call(this,"PropertyIsNotEqualTo",t,e,i)}return r&&(t.__proto__=r),(t.prototype=Object.create(r&&r.prototype)).constructor=t}(Xy),ev=function(i){function t(t){var e=["Or"].concat(Array.prototype.slice.call(arguments));i.apply(this,e)}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(Gy),iv=function(r){function t(t,e,i){r.call(this,"Within",t,e,i)}return r&&(t.__proto__=r),(t.prototype=Object.create(r&&r.prototype)).constructor=t}(jy);function rv(t){var e=[null].concat(Array.prototype.slice.call(arguments));return new(Function.prototype.bind.apply(ky,e))}function nv(t,e,i){return new Dy(t,e,i)}var ov={"http://www.opengis.net/gml":{boundedBy:hd(Cd.prototype.readGeometryElement,"bounds")}},sv={"http://www.opengis.net/wfs":{totalInserted:hd(Ld),totalUpdated:hd(Ld),totalDeleted:hd(Ld)}},av={"http://www.opengis.net/wfs":{TransactionSummary:hd(function(t,e){return gd({},sv,t,e)},"transactionSummary"),InsertResults:hd(function(t,e){return gd([],yv,t,e)},"insertIds")}},hv={"http://www.opengis.net/wfs":{PropertyName:ld(Nd)}},lv={"http://www.opengis.net/wfs":{Insert:ld(function(t,e,i){var r=i[i.length-1],n=r.featureType,o=r.featureNS,s=r.gmlVersion,a=$p(o,n);t.appendChild(a),2===s?Yd.prototype.writeFeatureElement(a,e,i):kd.prototype.writeFeatureElement(a,e,i)}),Update:ld(function(t,e,i){var r=i[i.length-1];Z(void 0!==e.getId(),27);var n=r.featureType,o=r.featurePrefix,s=r.featureNS,a=mv(o,n),h=e.getGeometryName();t.setAttribute("typeName",a),t.setAttributeNS(cv,"xmlns:"+o,s);var l=e.getId();if(void 0!==l){for(var u=e.getKeys(),c=[],p=0,d=u.length;p<d;p++){var f=e.get(u[p]);if(void 0!==f){var _=u[p];f instanceof Ie&&(_=h),c.push({name:_,value:f})}}vd({gmlVersion:r.gmlVersion,node:t,hasZ:r.hasZ,srsName:r.srsName},lv,cd("Property"),c,i),vv(t,l,i)}}),Delete:ld(function(t,e,i){var r=i[i.length-1];Z(void 0!==e.getId(),26);var n=r.featureType,o=r.featurePrefix,s=r.featureNS,a=mv(o,n);t.setAttribute("typeName",a),t.setAttributeNS(cv,"xmlns:"+o,s);var h=e.getId();void 0!==h&&vv(t,h,i)}),Property:ld(function(t,e,i){var r=$p(dv,"Name"),n=i[i.length-1].gmlVersion;if(t.appendChild(r),Nd(r,e.name),void 0!==e.value&&null!==e.value){var o=$p(dv,"Value");t.appendChild(o),e.value instanceof Ie?2===n?Yd.prototype.writeGeometryElement(o,e.value,i):kd.prototype.writeGeometryElement(o,e.value,i):Nd(o,e.value)}}),Native:ld(function(t,e,i){e.vendorId&&t.setAttribute("vendorId",e.vendorId);void 0!==e.safeToIgnore&&t.setAttribute("safeToIgnore",e.safeToIgnore);void 0!==e.value&&Nd(t,e.value)})}},uv="feature",cv="http://www.w3.org/2000/xmlns/",pv="http://www.opengis.net/ogc",dv="http://www.opengis.net/wfs",fv={"1.1.0":"http://www.opengis.net/wfs http://schemas.opengis.net/wfs/1.1.0/wfs.xsd","1.0.0":"http://www.opengis.net/wfs http://schemas.opengis.net/wfs/1.0.0/wfs.xsd"},_v=function(i){function t(t){i.call(this);var e=t||{};this.featureType_=e.featureType,this.featureNS_=e.featureNS,this.gmlFormat_=e.gmlFormat?e.gmlFormat:new kd,this.schemaLocation_=e.schemaLocation?e.schemaLocation:fv["1.1.0"]}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.getFeatureType=function(){return this.featureType_},t.prototype.setFeatureType=function(t){this.featureType_=t},t.prototype.readFeaturesFromNode=function(t,e){var i={featureType:this.featureType_,featureNS:this.featureNS_};C(i,this.getReadOptions(t,e||{}));var r=[i];this.gmlFormat_.FEATURE_COLLECTION_PARSERS[xd].featureMember=od(Cd.prototype.readFeaturesInternal);var n=gd([],this.gmlFormat_.FEATURE_COLLECTION_PARSERS,t,r,this.gmlFormat_);return n||(n=[]),n},t.prototype.readTransactionResponse=function(t){if(ed(t))return this.readTransactionResponseFromDocument(t);if(id(t))return this.readTransactionResponseFromNode(t);if("string"==typeof t){var e=rd(t);return this.readTransactionResponseFromDocument(e)}},t.prototype.readFeatureCollectionMetadata=function(t){if(ed(t))return this.readFeatureCollectionMetadataFromDocument(t);if(id(t))return this.readFeatureCollectionMetadataFromNode(t);if("string"==typeof t){var e=rd(t);return this.readFeatureCollectionMetadataFromDocument(e)}},t.prototype.readFeatureCollectionMetadataFromDocument=function(t){for(var e=t.firstChild;e;e=e.nextSibling)if(e.nodeType==Node.ELEMENT_NODE)return this.readFeatureCollectionMetadataFromNode(e)},t.prototype.readFeatureCollectionMetadataFromNode=function(t){var e={},i=bd(t.getAttribute("numberOfFeatures"));return e.numberOfFeatures=i,gd(e,ov,t,[],this.gmlFormat_)},t.prototype.readTransactionResponseFromDocument=function(t){for(var e=t.firstChild;e;e=e.nextSibling)if(e.nodeType==Node.ELEMENT_NODE)return this.readTransactionResponseFromNode(e)},t.prototype.readTransactionResponseFromNode=function(t){return gd({},av,t,[])},t.prototype.writeGetFeature=function(t){var e,i=$p(dv,"GetFeature");if(i.setAttribute("service","WFS"),i.setAttribute("version","1.1.0"),t&&(t.handle&&i.setAttribute("handle",t.handle),t.outputFormat&&i.setAttribute("outputFormat",t.outputFormat),void 0!==t.maxFeatures&&i.setAttribute("maxFeatures",t.maxFeatures),t.resultType&&i.setAttribute("resultType",t.resultType),void 0!==t.startIndex&&i.setAttribute("startIndex",t.startIndex),void 0!==t.count&&i.setAttribute("count",t.count),e=t.filter,t.bbox)){Z(t.geometryName,12);var r=nv(t.geometryName,t.bbox,t.srsName);e=e?rv(e,r):r}i.setAttributeNS(Qp,"xsi:schemaLocation",this.schemaLocation_);var n,o,s,a,h,l={node:i,srsName:t.srsName,featureNS:t.featureNS?t.featureNS:this.featureNS_,featurePrefix:t.featurePrefix,geometryName:t.geometryName,filter:e,propertyNames:t.propertyNames?t.propertyNames:[]};return Z(Array.isArray(t.featureTypes),11),n=i,o=t.featureTypes,a=(s=[l])[s.length-1],(h=C({},a)).node=n,vd(h,xv,cd("Query"),o,s),i},t.prototype.writeTransaction=function(t,e,i,r){var n,o,s=[],a=$p(dv,"Transaction"),h=r.version?r.version:"1.1.0",l="1.0.0"===h?2:3;a.setAttribute("service","WFS"),a.setAttribute("version",h),r&&(n=r.gmlOptions?r.gmlOptions:{},r.handle&&a.setAttribute("handle",r.handle));var u=fv[h];a.setAttributeNS(Qp,"xsi:schemaLocation",u);var c=r.featurePrefix?r.featurePrefix:uv;return t&&(o={node:a,featureNS:r.featureNS,featureType:r.featureType,featurePrefix:c,gmlVersion:l,hasZ:r.hasZ,srsName:r.srsName},C(o,n),vd(o,lv,cd("Insert"),t,s)),e&&(o={node:a,featureNS:r.featureNS,featureType:r.featureType,featurePrefix:c,gmlVersion:l,hasZ:r.hasZ,srsName:r.srsName},C(o,n),vd(o,lv,cd("Update"),e,s)),i&&vd({node:a,featureNS:r.featureNS,featureType:r.featureType,featurePrefix:c,gmlVersion:l,srsName:r.srsName},lv,cd("Delete"),i,s),r.nativeElements&&vd({node:a,featureNS:r.featureNS,featureType:r.featureType,featurePrefix:c,gmlVersion:l,srsName:r.srsName},lv,cd("Native"),r.nativeElements,s),a},t.prototype.readProjectionFromDocument=function(t){for(var e=t.firstChild;e;e=e.nextSibling)if(e.nodeType==Node.ELEMENT_NODE)return this.readProjectionFromNode(e);return null},t.prototype.readProjectionFromNode=function(t){if(t.firstElementChild&&t.firstElementChild.firstElementChild)for(var e=(t=t.firstElementChild.firstElementChild).firstElementChild;e;e=e.nextElementSibling)if(0!==e.childNodes.length&&(1!==e.childNodes.length||3!==e.firstChild.nodeType)){var i=[{}];return this.gmlFormat_.readGeometryElement(e,i),ne(i.pop().srsName)}return null},t}(md);var gv={"http://www.opengis.net/ogc":{FeatureId:od(function(t,e){return t.getAttribute("fid")})}};var yv={"http://www.opengis.net/wfs":{Feature:function(t,e){_d(gv,t,e)}}};function vv(t,e,i){var r=$p(pv,"Filter"),n=$p(pv,"FeatureId");r.appendChild(n),n.setAttribute("fid",e),t.appendChild(r)}function mv(t,e){var i=(t=t||uv)+":";return 0===e.indexOf(i)?e:i+e}var xv={"http://www.opengis.net/wfs":{Query:ld(function(t,e,i){var r,n=i[i.length-1],o=n.featurePrefix,s=n.featureNS,a=n.propertyNames,h=n.srsName;r=o?mv(o,e):e;t.setAttribute("typeName",r),h&&t.setAttribute("srsName",h);s&&t.setAttributeNS(cv,"xmlns:"+o,s);var l=C({},n);l.node=t,vd(l,hv,cd("PropertyName"),a,i);var u=n.filter;if(u){var c=$p(pv,"Filter");t.appendChild(c),Sv(c,u,i)}})},"http://www.opengis.net/ogc":{During:ld(function(t,e,i){var r=$p("http://www.opengis.net/fes","ValueReference");Nd(r,e.propertyName),t.appendChild(r);var n=$p(xd,"TimePeriod");t.appendChild(n);var o=$p(xd,"begin");n.appendChild(o),Iv(o,e.begin);var s=$p(xd,"end");n.appendChild(s),Iv(s,e.end)}),And:ld(Cv),Or:ld(Cv),Not:ld(function(t,e,i){var r={node:t},n=e.condition;vd(r,xv,cd(n.getTagName()),[n],i)}),BBOX:ld(function(t,e,i){i[i.length-1].srsName=e.srsName,wv(t,e.geometryName),kd.prototype.writeGeometryElement(t,e.extent,i)}),Contains:ld(function(t,e,i){i[i.length-1].srsName=e.srsName,wv(t,e.geometryName),kd.prototype.writeGeometryElement(t,e.geometry,i)}),Intersects:ld(function(t,e,i){i[i.length-1].srsName=e.srsName,wv(t,e.geometryName),kd.prototype.writeGeometryElement(t,e.geometry,i)}),Within:ld(function(t,e,i){i[i.length-1].srsName=e.srsName,wv(t,e.geometryName),kd.prototype.writeGeometryElement(t,e.geometry,i)}),PropertyIsEqualTo:ld(Ev),PropertyIsNotEqualTo:ld(Ev),PropertyIsLessThan:ld(Ev),PropertyIsLessThanOrEqualTo:ld(Ev),PropertyIsGreaterThan:ld(Ev),PropertyIsGreaterThanOrEqualTo:ld(Ev),PropertyIsNull:ld(function(t,e,i){wv(t,e.propertyName)}),PropertyIsBetween:ld(function(t,e,i){wv(t,e.propertyName);var r=$p(pv,"LowerBoundary");t.appendChild(r),Rv(r,""+e.lowerBoundary);var n=$p(pv,"UpperBoundary");t.appendChild(n),Rv(n,""+e.upperBoundary)}),PropertyIsLike:ld(function(t,e,i){t.setAttribute("wildCard",e.wildCard),t.setAttribute("singleChar",e.singleChar),t.setAttribute("escapeChar",e.escapeChar),void 0!==e.matchCase&&t.setAttribute("matchCase",e.matchCase.toString());wv(t,e.propertyName),Rv(t,""+e.pattern)})}};function Sv(t,e,i){vd({node:t},xv,cd(e.getTagName()),[e],i)}function Cv(t,e,i){for(var r={node:t},n=e.conditions,o=0,s=n.length;o<s;++o){var a=n[o];vd(r,xv,cd(a.getTagName()),[a],i)}}function Ev(t,e,i){void 0!==e.matchCase&&t.setAttribute("matchCase",e.matchCase.toString()),wv(t,e.propertyName),Rv(t,""+e.expression)}function Tv(t,e,i){var r=$p(pv,t);Nd(r,i),e.appendChild(r)}function wv(t,e){Tv("PropertyName",t,e)}function Rv(t,e){Tv("Literal",t,e)}function Iv(t,e){var i=$p(xd,"TimeInstant");t.appendChild(i);var r=$p(xd,"timePosition");i.appendChild(r),Nd(r,e)}var Lv={POINT:Dr,LINESTRING:Sn,POLYGON:Qr,MULTIPOINT:ih,MULTILINESTRING:eh,MULTIPOLYGON:nh},bv="EMPTY",Pv="Z",Fv="M",Mv=1,Ov=2,Nv=3,Av=4,Gv=5,kv=6,Dv={};for(var jv in Lt)Dv[jv]=Lt[jv].toUpperCase();var Uv=function(t){this.wkt=t,this.index_=-1};Uv.prototype.isAlpha_=function(t){return"a"<=t&&t<="z"||"A"<=t&&t<="Z"},Uv.prototype.isNumeric_=function(t,e){return"0"<=t&&t<="9"||"."==t&&!(void 0!==e&&e)},Uv.prototype.isWhiteSpace_=function(t){return" "==t||"\t"==t||"\r"==t||"\n"==t},Uv.prototype.nextChar_=function(){return this.wkt.charAt(++this.index_)},Uv.prototype.nextToken=function(){var t=this.nextChar_(),e={position:this.index_,value:t};if("("==t)e.type=Ov;else if(","==t)e.type=Gv;else if(")"==t)e.type=Nv;else if(this.isNumeric_(t)||"-"==t)e.type=Av,e.value=this.readNumber_();else if(this.isAlpha_(t))e.type=Mv,e.value=this.readText_();else{if(this.isWhiteSpace_(t))return this.nextToken();if(""!==t)throw new Error("Unexpected character: "+t);e.type=kv}return e},Uv.prototype.readNumber_=function(){for(var t,e=this.index_,i=!1,r=!1;"."==t?i=!0:"e"!=t&&"E"!=t||(r=!0),t=this.nextChar_(),this.isNumeric_(t,i)||!r&&("e"==t||"E"==t)||r&&("-"==t||"+"==t););return parseFloat(this.wkt.substring(e,this.index_--))},Uv.prototype.readText_=function(){for(var t,e=this.index_;t=this.nextChar_(),this.isAlpha_(t););return this.wkt.substring(e,this.index_--).toUpperCase()};var Yv=function(t){this.lexer_=t,this.token_,this.layout_=yr.XY};Yv.prototype.consume_=function(){this.token_=this.lexer_.nextToken()},Yv.prototype.isTokenType=function(t){return this.token_.type==t},Yv.prototype.match=function(t){var e=this.isTokenType(t);return e&&this.consume_(),e},Yv.prototype.parse=function(){return this.consume_(),this.parseGeometry_()},Yv.prototype.parseGeometryLayout_=function(){var t=yr.XY,e=this.token_;if(this.isTokenType(Mv)){var i=e.value;i===Pv?t=yr.XYZ:i===Fv?t=yr.XYM:"ZM"===i&&(t=yr.XYZM),t!==yr.XY&&this.consume_()}return t},Yv.prototype.parseGeometryCollectionText_=function(){if(this.match(Ov)){for(var t=[];t.push(this.parseGeometry_()),this.match(Gv););if(this.match(Nv))return t}else if(this.isEmptyGeometry_())return[];throw new Error(this.formatErrorMessage_())},Yv.prototype.parsePointText_=function(){if(this.match(Ov)){var t=this.parsePoint_();if(this.match(Nv))return t}else if(this.isEmptyGeometry_())return null;throw new Error(this.formatErrorMessage_())},Yv.prototype.parseLineStringText_=function(){if(this.match(Ov)){var t=this.parsePointList_();if(this.match(Nv))return t}else if(this.isEmptyGeometry_())return[];throw new Error(this.formatErrorMessage_())},Yv.prototype.parsePolygonText_=function(){if(this.match(Ov)){var t=this.parseLineStringTextList_();if(this.match(Nv))return t}else if(this.isEmptyGeometry_())return[];throw new Error(this.formatErrorMessage_())},Yv.prototype.parseMultiPointText_=function(){var t;if(this.match(Ov)){if(t=this.token_.type==Ov?this.parsePointTextList_():this.parsePointList_(),this.match(Nv))return t}else if(this.isEmptyGeometry_())return[];throw new Error(this.formatErrorMessage_())},Yv.prototype.parseMultiLineStringText_=function(){if(this.match(Ov)){var t=this.parseLineStringTextList_();if(this.match(Nv))return t}else if(this.isEmptyGeometry_())return[];throw new Error(this.formatErrorMessage_())},Yv.prototype.parseMultiPolygonText_=function(){if(this.match(Ov)){var t=this.parsePolygonTextList_();if(this.match(Nv))return t}else if(this.isEmptyGeometry_())return[];throw new Error(this.formatErrorMessage_())},Yv.prototype.parsePoint_=function(){for(var t=[],e=this.layout_.length,i=0;i<e;++i){var r=this.token_;if(!this.match(Av))break;t.push(r.value)}if(t.length==e)return t;throw new Error(this.formatErrorMessage_())},Yv.prototype.parsePointList_=function(){for(var t=[this.parsePoint_()];this.match(Gv);)t.push(this.parsePoint_());return t},Yv.prototype.parsePointTextList_=function(){for(var t=[this.parsePointText_()];this.match(Gv);)t.push(this.parsePointText_());return t},Yv.prototype.parseLineStringTextList_=function(){for(var t=[this.parseLineStringText_()];this.match(Gv);)t.push(this.parseLineStringText_());return t},Yv.prototype.parsePolygonTextList_=function(){for(var t=[this.parsePolygonText_()];this.match(Gv);)t.push(this.parsePolygonText_());return t},Yv.prototype.isEmptyGeometry_=function(){var t=this.isTokenType(Mv)&&this.token_.value==bv;return t&&this.consume_(),t},Yv.prototype.formatErrorMessage_=function(){return"Unexpected `"+this.token_.value+"` at position "+this.token_.position+" in `"+this.lexer_.wkt+"`"},Yv.prototype.parseGeometry_=function(){var t=this.token_;if(this.match(Mv)){var e=t.value;if(this.layout_=this.parseGeometryLayout_(),"GEOMETRYCOLLECTION"==e){var i=this.parseGeometryCollectionText_();return new Ef(i)}var r,n=Lv[e];if(!n)throw new Error("Invalid geometry type: "+e);switch(e){case"POINT":r=this.parsePointText_();break;case"LINESTRING":r=this.parseLineStringText_();break;case"POLYGON":r=this.parsePolygonText_();break;case"MULTIPOINT":r=this.parseMultiPointText_();break;case"MULTILINESTRING":r=this.parseMultiLineStringText_();break;case"MULTIPOLYGON":r=this.parseMultiPolygonText_();break;default:throw new Error("Invalid geometry type: "+e)}return r||(r=n===Lv.POINT?[NaN,NaN]:[]),new n(r,this.layout_)}throw new Error(this.formatErrorMessage_())};var Bv=function(i){function t(t){i.call(this);var e=t||{};this.splitCollection_=void 0!==e.splitCollection&&e.splitCollection}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.parse_=function(t){var e=new Uv(t);return new Yv(e).parse()},t.prototype.readFeatureFromText=function(t,e){var i=this.readGeometryFromText(t,e);if(i){var r=new Ji;return r.setGeometry(i),r}return null},t.prototype.readFeaturesFromText=function(t,e){for(var i=[],r=this.readGeometryFromText(t,e),n=[],o=0,s=(i=this.splitCollection_&&r.getType()==Lt.GEOMETRY_COLLECTION?r.getGeometriesArray():[r]).length;o<s;++o){var a=new Ji;a.setGeometry(i[o]),n.push(a)}return n},t.prototype.readGeometryFromText=function(t,e){var i=this.parse_(t);return i?Yp(i,!1,e):null},t.prototype.writeFeatureText=function(t,e){var i=t.getGeometry();return i?this.writeGeometryText(i,e):""},t.prototype.writeFeaturesText=function(t,e){if(1==t.length)return this.writeFeatureText(t[0],e);for(var i=[],r=0,n=t.length;r<n;++r)i.push(t[r].getGeometry());var o=new Ef(i);return this.writeGeometryText(o,e)},t.prototype.writeGeometryText=function(t,e){return Kv(Yp(t,!0,e))},t}(Pf);function Xv(t){var e=t.getCoordinates();return 0===e.length?"":e.join(" ")}function zv(t){for(var e=t.getCoordinates(),i=[],r=0,n=e.length;r<n;++r)i.push(e[r].join(" "));return i.join(",")}function Vv(t){for(var e=[],i=t.getLinearRings(),r=0,n=i.length;r<n;++r)e.push("("+zv(i[r])+")");return e.join(",")}var Wv={Point:Xv,LineString:zv,Polygon:Vv,MultiPoint:function(t){for(var e=[],i=t.getPoints(),r=0,n=i.length;r<n;++r)e.push("("+Xv(i[r])+")");return e.join(",")},MultiLineString:function(t){for(var e=[],i=t.getLineStrings(),r=0,n=i.length;r<n;++r)e.push("("+zv(i[r])+")");return e.join(",")},MultiPolygon:function(t){for(var e=[],i=t.getPolygons(),r=0,n=i.length;r<n;++r)e.push("("+Vv(i[r])+")");return e.join(",")},GeometryCollection:function(t){for(var e=[],i=t.getGeometries(),r=0,n=i.length;r<n;++r)e.push(Kv(i[r]));return e.join(",")}};function Kv(t){var e,i,r=t.getType(),n=(0,Wv[r])(t);if(r=r.toUpperCase(),t instanceof vr){var o=(e=t.getLayout(),i="",e!==yr.XYZ&&e!==yr.XYZM||(i+=Pv),e!==yr.XYM&&e!==yr.XYZM||(i+=Fv),i);0<o.length&&(r+=" "+o)}return 0===n.length?r+" "+bv:r+"("+n+")"}var Hv="http://www.w3.org/1999/xlink";function Zv(t){return t.getAttributeNS(Hv,"href")}var qv=function(){};qv.prototype.read=function(t){if(ed(t))return this.readFromDocument(t);if(id(t))return this.readFromNode(t);if("string"==typeof t){var e=rd(t);return this.readFromDocument(e)}return null},qv.prototype.readFromDocument=function(t){},qv.prototype.readFromNode=function(t){};var Jv=[null,"http://www.opengis.net/wms"],Qv=fd(Jv,{Service:hd(function(t,e){return gd({},em,t,e)}),Capability:hd(function(t,e){return gd({},$v,t,e)})}),$v=fd(Jv,{Request:hd(function(t,e){return gd({},lm,t,e)}),Exception:hd(function(t,e){return gd([],om,t,e)}),Layer:hd(function(t,e){return gd({},sm,t,e)})}),tm=function(t){function e(){t.call(this),this.version=void 0}return t&&(e.__proto__=t),((e.prototype=Object.create(t&&t.prototype)).constructor=e).prototype.readFromDocument=function(t){for(var e=t.firstChild;e;e=e.nextSibling)if(e.nodeType==Node.ELEMENT_NODE)return this.readFromNode(e);return null},e.prototype.readFromNode=function(t){this.version=t.getAttribute("version").trim();var e=gd({version:this.version},Qv,t,[]);return e||null},e}(qv),em=fd(Jv,{Name:hd(Pd),Title:hd(Pd),Abstract:hd(Pd),KeywordList:hd(mm),OnlineResource:hd(Zv),ContactInformation:hd(function(t,e){return gd({},im,t,e)}),Fees:hd(Pd),AccessConstraints:hd(Pd),LayerLimit:hd(Ld),MaxWidth:hd(Ld),MaxHeight:hd(Ld)}),im=fd(Jv,{ContactPersonPrimary:hd(function(t,e){return gd({},rm,t,e)}),ContactPosition:hd(Pd),ContactAddress:hd(function(t,e){return gd({},nm,t,e)}),ContactVoiceTelephone:hd(Pd),ContactFacsimileTelephone:hd(Pd),ContactElectronicMailAddress:hd(Pd)}),rm=fd(Jv,{ContactPerson:hd(Pd),ContactOrganization:hd(Pd)}),nm=fd(Jv,{AddressType:hd(Pd),Address:hd(Pd),City:hd(Pd),StateOrProvince:hd(Pd),PostCode:hd(Pd),Country:hd(Pd)}),om=fd(Jv,{Format:od(Pd)}),sm=fd(Jv,{Name:hd(Pd),Title:hd(Pd),Abstract:hd(Pd),KeywordList:hd(mm),CRS:ad(Pd),EX_GeographicBoundingBox:hd(function(t,e){var i=gd({},hm,t,e);if(!i)return;var r=i.westBoundLongitude,n=i.southBoundLatitude,o=i.eastBoundLongitude,s=i.northBoundLatitude;if(void 0===r||void 0===n||void 0===o||void 0===s)return;return[r,n,o,s]}),BoundingBox:ad(function(t,e){var i=[Id(t.getAttribute("minx")),Id(t.getAttribute("miny")),Id(t.getAttribute("maxx")),Id(t.getAttribute("maxy"))],r=[Id(t.getAttribute("resx")),Id(t.getAttribute("resy"))];return{crs:t.getAttribute("CRS"),extent:i,res:r}}),Dimension:ad(function(t,e){return{name:t.getAttribute("name"),units:t.getAttribute("units"),unitSymbol:t.getAttribute("unitSymbol"),default:t.getAttribute("default"),multipleValues:Td(t.getAttribute("multipleValues")),nearestValue:Td(t.getAttribute("nearestValue")),current:Td(t.getAttribute("current")),values:Pd(t)}}),Attribution:hd(function(t,e){return gd({},am,t,e)}),AuthorityURL:ad(function(t,e){var i=gm(t,e);if(i)return i.name=t.getAttribute("name"),i;return}),Identifier:ad(Pd),MetadataURL:ad(function(t,e){var i=gm(t,e);if(i)return i.type=t.getAttribute("type"),i;return}),DataURL:ad(gm),FeatureListURL:ad(gm),Style:ad(function(t,e){return gd({},dm,t,e)}),MinScaleDenominator:hd(Rd),MaxScaleDenominator:hd(Rd),Layer:ad(function(t,e){var i=e[e.length-1],r=gd({},sm,t,e);if(!r)return;var n=Td(t.getAttribute("queryable"));void 0===n&&(n=i.queryable);r.queryable=void 0!==n&&n;var o=bd(t.getAttribute("cascaded"));void 0===o&&(o=i.cascaded);r.cascaded=o;var s=Td(t.getAttribute("opaque"));void 0===s&&(s=i.opaque);r.opaque=void 0!==s&&s;var a=Td(t.getAttribute("noSubsets"));void 0===a&&(a=i.noSubsets);r.noSubsets=void 0!==a&&a;var h=Id(t.getAttribute("fixedWidth"));h||(h=i.fixedWidth);r.fixedWidth=h;var l=Id(t.getAttribute("fixedHeight"));l||(l=i.fixedHeight);r.fixedHeight=l,["Style","CRS","AuthorityURL"].forEach(function(t){if(t in i){var e=r[t]||[];r[t]=e.concat(i[t])}});return["EX_GeographicBoundingBox","BoundingBox","Dimension","Attribution","MinScaleDenominator","MaxScaleDenominator"].forEach(function(t){if(!(t in r)){var e=i[t];r[t]=e}}),r})}),am=fd(Jv,{Title:hd(Pd),OnlineResource:hd(Zv),LogoURL:hd(vm)}),hm=fd(Jv,{westBoundLongitude:hd(Rd),eastBoundLongitude:hd(Rd),southBoundLatitude:hd(Rd),northBoundLatitude:hd(Rd)}),lm=fd(Jv,{GetCapabilities:hd(ym),GetMap:hd(ym),GetFeatureInfo:hd(ym)}),um=fd(Jv,{Format:ad(Pd),DCPType:ad(function(t,e){return gd({},cm,t,e)})}),cm=fd(Jv,{HTTP:hd(function(t,e){return gd({},pm,t,e)})}),pm=fd(Jv,{Get:hd(gm),Post:hd(gm)}),dm=fd(Jv,{Name:hd(Pd),Title:hd(Pd),Abstract:hd(Pd),LegendURL:ad(vm),StyleSheetURL:hd(gm),StyleURL:hd(gm)}),fm=fd(Jv,{Format:hd(Pd),OnlineResource:hd(Zv)}),_m=fd(Jv,{Keyword:od(Pd)});function gm(t,e){return gd({},fm,t,e)}function ym(t,e){return gd({},um,t,e)}function vm(t,e){var i=gm(t,e);if(i){var r=[bd(t.getAttribute("width")),bd(t.getAttribute("height"))];return i.size=r,i}}function mm(t,e){return gd([],_m,t,e)}var xm=function(i){function t(t){i.call(this);var e=t||{};this.featureNS_="http://mapserver.gis.umn.edu/mapserver",this.gmlFormat_=new Yd,this.layers_=e.layers?e.layers:null}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.getLayers=function(){return this.layers_},t.prototype.setLayers=function(t){this.layers_=t},t.prototype.readFeatures_=function(t,e){t.setAttribute("namespaceURI",this.featureNS_);var i=t.localName,r=[];if(0===t.childNodes.length)return r;if("msGMLOutput"==i)for(var n=0,o=t.childNodes.length;n<o;n++){var s=t.childNodes[n];if(s.nodeType===Node.ELEMENT_NODE){var a=e[0],h=s.localName.replace("_layer","");if(!this.layers_||lr(this.layers_,h)){var l=h+"_feature";a.featureType=l,a.featureNS=this.featureNS_;var u={};u[l]=od(this.gmlFormat_.readFeatureElement,this.gmlFormat_);var c=fd([a.featureNS,null],u);s.setAttribute("namespaceURI",this.featureNS_);var p=gd([],c,s,e,this.gmlFormat_);p&&pr(r,p)}}}if("FeatureCollection"==i){var d=gd([],this.gmlFormat_.FEATURE_COLLECTION_PARSERS,t,[{}],this.gmlFormat_);d&&(r=d)}return r},t.prototype.readFeaturesFromNode=function(t,e){var i={};return e&&C(i,this.getReadOptions(t,e)),this.readFeatures_(t,[i])},t.prototype.writeFeatureNode=function(t,e){},t.prototype.writeFeaturesNode=function(t,e){},t.prototype.writeGeometryNode=function(t,e){},t}(md),Sm=[null,"http://www.opengis.net/ows/1.1"],Cm=fd(Sm,{ServiceIdentification:hd(function(t,e){return gd({},Am,t,e)}),ServiceProvider:hd(function(t,e){return gd({},Gm,t,e)}),OperationsMetadata:hd(function(t,e){return gd({},Fm,t,e)})}),Em=function(t){function e(){t.call(this)}return t&&(e.__proto__=t),((e.prototype=Object.create(t&&t.prototype)).constructor=e).prototype.readFromDocument=function(t){for(var e=t.firstChild;e;e=e.nextSibling)if(e.nodeType==Node.ELEMENT_NODE)return this.readFromNode(e);return null},e.prototype.readFromNode=function(t){var e=gd({},Cm,t,[]);return e||null},e}(qv),Tm=fd(Sm,{DeliveryPoint:hd(Pd),City:hd(Pd),AdministrativeArea:hd(Pd),PostalCode:hd(Pd),Country:hd(Pd),ElectronicMailAddress:hd(Pd)}),wm=fd(Sm,{Value:ad(function(t,e){return Pd(t)})}),Rm=fd(Sm,{AllowedValues:hd(function(t,e){return gd({},wm,t,e)})}),Im=fd(Sm,{Phone:hd(function(t,e){return gd({},Mm,t,e)}),Address:hd(function(t,e){return gd({},Tm,t,e)})}),Lm=fd(Sm,{HTTP:hd(function(t,e){return gd({},bm,t,e)})}),bm=fd(Sm,{Get:ad(function(t,e){var i=Zv(t);if(!i)return;return gd({href:i},Om,t,e)}),Post:void 0}),Pm=fd(Sm,{DCP:hd(function(t,e){return gd({},Lm,t,e)})}),Fm=fd(Sm,{Operation:function(t,e){var i=t.getAttribute("name"),r=gd({},Pm,t,e);if(!r)return;e[e.length-1][i]=r}}),Mm=fd(Sm,{Voice:hd(Pd),Facsimile:hd(Pd)}),Om=fd(Sm,{Constraint:ad(function(t,e){var i=t.getAttribute("name");if(!i)return;return gd({name:i},Rm,t,e)})}),Nm=fd(Sm,{IndividualName:hd(Pd),PositionName:hd(Pd),ContactInfo:hd(function(t,e){return gd({},Im,t,e)})}),Am=fd(Sm,{Abstract:hd(Pd),AccessConstraints:hd(Pd),Fees:hd(Pd),Title:hd(Pd),ServiceTypeVersion:hd(Pd),ServiceType:hd(Pd)}),Gm=fd(Sm,{ProviderName:hd(Pd),ProviderSite:hd(Zv),ServiceContact:hd(function(t,e){return gd({},Nm,t,e)})});var km=[null,"http://www.opengis.net/wmts/1.0"],Dm=[null,"http://www.opengis.net/ows/1.1"],jm=fd(km,{Contents:hd(function(t,e){return gd({},Ym,t,e)})}),Um=function(t){function e(){t.call(this),this.owsParser_=new Em}return t&&(e.__proto__=t),((e.prototype=Object.create(t&&t.prototype)).constructor=e).prototype.readFromDocument=function(t){for(var e=t.firstChild;e;e=e.nextSibling)if(e.nodeType==Node.ELEMENT_NODE)return this.readFromNode(e);return null},e.prototype.readFromNode=function(t){var e=t.getAttribute("version").trim(),i=this.owsParser_.readFromNode(t);return i?(i.version=e,(i=gd(i,jm,t,[]))||null):null},e}(qv),Ym=fd(km,{Layer:ad(function(t,e){return gd({},Bm,t,e)}),TileMatrixSet:ad(function(t,e){return gd({},Zm,t,e)})}),Bm=fd(km,{Style:ad(function(t,e){var i=gd({},Xm,t,e);if(!i)return;var r="true"===t.getAttribute("isDefault");return i.isDefault=r,i}),Format:ad(Pd),TileMatrixSetLink:ad(function(t,e){return gd({},zm,t,e)}),Dimension:ad(function(t,e){return gd({},Km,t,e)}),ResourceURL:ad(function(t,e){var i=t.getAttribute("format"),r=t.getAttribute("template"),n=t.getAttribute("resourceType"),o={};i&&(o.format=i);r&&(o.template=r);n&&(o.resourceType=n);return o})},fd(Dm,{Title:hd(Pd),Abstract:hd(Pd),WGS84BoundingBox:hd(function(t,e){var i=gd([],Hm,t,e);if(2!=i.length)return;return A(i)}),Identifier:hd(Pd)})),Xm=fd(km,{LegendURL:ad(function(t,e){var i={};return i.format=t.getAttribute("format"),i.href=Zv(t),i})},fd(Dm,{Title:hd(Pd),Identifier:hd(Pd)})),zm=fd(km,{TileMatrixSet:hd(Pd),TileMatrixSetLimits:hd(function(t,e){return gd([],Vm,t,e)})}),Vm=fd(km,{TileMatrixLimits:od(function(t,e){return gd({},Wm,t,e)})}),Wm=fd(km,{TileMatrix:hd(Pd),MinTileRow:hd(Ld),MaxTileRow:hd(Ld),MinTileCol:hd(Ld),MaxTileCol:hd(Ld)}),Km=fd(km,{Default:hd(Pd),Value:ad(Pd)},fd(Dm,{Identifier:hd(Pd)})),Hm=fd(Dm,{LowerCorner:od(Jm),UpperCorner:od(Jm)}),Zm=fd(km,{WellKnownScaleSet:hd(Pd),TileMatrix:ad(function(t,e){return gd({},qm,t,e)})},fd(Dm,{SupportedCRS:hd(Pd),Identifier:hd(Pd)})),qm=fd(km,{TopLeftCorner:hd(Jm),ScaleDenominator:hd(Rd),TileWidth:hd(Ld),TileHeight:hd(Ld),MatrixWidth:hd(Ld),MatrixHeight:hd(Ld)},fd(Dm,{Identifier:hd(Pd)}));function Jm(t,e){var i=Pd(t).split(" ");if(i&&2==i.length){var r=+i[0],n=+i[1];if(!isNaN(r)&&!isNaN(n))return[r,n]}}var Qm="blur",$m="gradient",tx="radius",ex=["#00f","#0ff","#0f0","#ff0","#f00"],ix=function(n){function t(t){var e=t||{},i=C({},e);delete i.gradient,delete i.radius,delete i.blur,delete i.shadow,delete i.weight,n.call(this,i),this.gradient_=null,this.shadow_=void 0!==e.shadow?e.shadow:250,this.circleImage_=void 0,this.styleCache_=null,E(this,b($m),this.handleGradientChanged_,this),this.setGradient(e.gradient?e.gradient:ex),this.setBlur(void 0!==e.blur?e.blur:15),this.setRadius(void 0!==e.radius?e.radius:8),E(this,b(Qm),this.handleStyleChanged_,this),E(this,b(tx),this.handleStyleChanged_,this),this.handleStyleChanged_();var s,r=e.weight?e.weight:"weight";s="string"==typeof r?function(t){return t.get(r)}:r,this.setStyle(function(t,e){var i=s(t),r=void 0!==i?gt(i,0,1):1,n=255*r|0,o=this.styleCache_[n];return o||(o=[new Wi({image:new Qf({opacity:r,src:this.circleImage_})})],this.styleCache_[n]=o),o}.bind(this)),this.setRenderOrder(null),E(this,wn,this.handleRender_,this)}return n&&(t.__proto__=n),((t.prototype=Object.create(n&&n.prototype)).constructor=t).prototype.createCircle_=function(){var t=this.getRadius(),e=this.getBlur(),i=t+e+1,r=2*i,n=De(r,r);n.shadowOffsetX=n.shadowOffsetY=this.shadow_,n.shadowBlur=e,n.shadowColor="#000",n.beginPath();var o=i-this.shadow_;return n.arc(o,o,t,0,2*Math.PI,!0),n.fill(),n.canvas.toDataURL()},t.prototype.getBlur=function(){return this.get(Qm)},t.prototype.getGradient=function(){return this.get($m)},t.prototype.getRadius=function(){return this.get(tx)},t.prototype.handleGradientChanged_=function(){this.gradient_=function(t){for(var e=De(1,256),i=e.createLinearGradient(0,0,1,256),r=1/(t.length-1),n=0,o=t.length;n<o;++n)i.addColorStop(n*r,t[n]);return e.fillStyle=i,e.fillRect(0,0,1,256),e.getImageData(0,0,1,256).data}(this.getGradient())},t.prototype.handleStyleChanged_=function(){this.circleImage_=this.createCircle_(),this.styleCache_=new Array(256),this.changed()},t.prototype.handleRender_=function(t){for(var e=t.context,i=e.canvas,r=e.getImageData(0,0,i.width,i.height),n=r.data,o=0,s=n.length;o<s;o+=4){var a=4*n[o+3];a&&(n[o]=this.gradient_[a],n[o+1]=this.gradient_[a+1],n[o+2]=this.gradient_[a+2])}e.putImageData(r,0,0)},t.prototype.setBlur=function(t){this.set(Qm,t)},t.prototype.setGradient=function(t){this.set($m,t)},t.prototype.setRadius=function(t){this.set(tx,t)},t}(lh);var rx=function(i){function t(t){var e=t||{};i.call(this,e),this.type=oh.IMAGE}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(Ls);rx.prototype.getSource;var nx="preload",ox="useInterimTilesOnError",sx=function(r){function t(t){var e=t||{},i=C({},e);delete i.preload,delete i.useInterimTilesOnError,r.call(this,i),this.setPreload(void 0!==e.preload?e.preload:0),this.setUseInterimTilesOnError(void 0===e.useInterimTilesOnError||e.useInterimTilesOnError),this.type=oh.TILE}return r&&(t.__proto__=r),((t.prototype=Object.create(r&&r.prototype)).constructor=t).prototype.getPreload=function(){return this.get(nx)},t.prototype.setPreload=function(t){this.set(nx,t)},t.prototype.getUseInterimTilesOnError=function(){return this.get(ox)},t.prototype.setUseInterimTilesOnError=function(t){this.set(ox,t)},t}(Ls);sx.prototype.getSource;var ax=function(n){function t(t){var e=t||{},i=e.renderMode||Au;Z(null==i||i==Nu||i==Au||i==Gu,28),e.declutter&&i==Nu&&(i=Au),e.renderMode=i;var r=C({},e);delete r.preload,delete r.useInterimTilesOnError,n.call(this,r),this.setPreload(e.preload?e.preload:0),this.setUseInterimTilesOnError(void 0===e.useInterimTilesOnError||e.useInterimTilesOnError),this.type=oh.VECTOR_TILE}return n&&(t.__proto__=n),((t.prototype=Object.create(n&&n.prototype)).constructor=t).prototype.getPreload=function(){return this.get(nx)},t.prototype.getUseInterimTilesOnError=function(){return this.get(ox)},t.prototype.setPreload=function(t){this.set(nx,t)},t.prototype.setUseInterimTilesOnError=function(t){this.set(ox,t)},t}(lh);function hx(t,e,i,r){return void 0!==r?(r[0]=t,r[1]=e,r[2]=i,r):[t,e,i]}function lx(t,e,i){return t+"/"+e+"/"+i}function ux(t){return lx(t[0],t[1],t[2])}function cx(t){return(t[1]<<t[0])+t[2]}function px(r,n){var o=/\{z\}/g,s=/\{x\}/g,a=/\{y\}/g,h=/\{-y\}/g;return function(i,t,e){return i?r.replace(o,i[0].toString()).replace(s,i[1].toString()).replace(a,function(){return(-i[2]-1).toString()}).replace(h,function(){var t=i[0],e=n.getFullTileRange(t);return Z(e,55),(e.getHeight()+i[2]).toString()}):void 0}}function dx(t,e){for(var i=t.length,r=new Array(i),n=0;n<i;++n)r[n]=px(t[n],e);return fx(r)}function fx(n){return 1===n.length?n[0]:function(t,e,i){if(t){var r=Ct(cx(t),n.length);return n[r](t,e,i)}}}function _x(t,e,i){}function gx(t){var e=[],i=/\{([a-z])-([a-z])\}/.exec(t);if(i){var r,n=i[1].charCodeAt(0),o=i[2].charCodeAt(0);for(r=n;r<=o;++r)e.push(t.replace(i[0],String.fromCharCode(r)));return e}if(i=i=/\{(\d+)-(\d+)\}/.exec(t)){for(var s=parseInt(i[2],10),a=parseInt(i[1],10);a<=s;a++)e.push(t.replace(i[0],a.toString()));return e}return e.push(t),e}function yx(t,e,i,r){var n=document.createElement("script"),o="olc_"+Et(e);function s(){delete window[o],n.parentNode.removeChild(n)}n.async=!0,n.src=t+(-1==t.indexOf("?")?"?":"&")+(r||"callback")+"="+o;var a=setTimeout(function(){s(),i&&i()},1e4);window[o]=function(t){clearTimeout(a),s(),e(t)},document.getElementsByTagName("head")[0].appendChild(n)}ax.prototype.getSource;var vx=function(e){function t(t){e.call(this,t)}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.expireCache=function(t){for(;this.canExpireCache();){var e=this.peekLast(),i=e.tileCoord[0].toString();if(i in t&&t[i].contains(e.tileCoord))break;this.pop().dispose()}},t.prototype.pruneExceptNewestZ=function(){if(0!==this.getCount()){var t=this.peekFirstKey(),e=t.split("/").map(Number)[0];this.forEach(function(t){t.tileCoord[0]!==e&&(this.remove(ux(t.tileCoord)),t.dispose())},this)}},t}(mi);function mx(t,e,i,r){var n=de(i,e,t),o=oe(e,r,i),s=e.getMetersPerUnit();void 0!==s&&(o*=s);var a=t.getMetersPerUnit();void 0!==a&&(o/=a);var h=t.getExtent();if(!h||j(h,n)){var l=oe(t,o,n)/o;isFinite(l)&&0<l&&(o/=l)}return o}function xx(t,e,i,r){var n=i-t,o=r-e,s=Math.sqrt(n*n+o*o);return[Math.round(i+n/s),Math.round(r+o/s)]}function Sx(t,e,w,R,i,I,r,n,o,a,s){var L=De(Math.round(w*t),Math.round(w*e));if(0===o.length)return L.canvas;L.scale(w,w);var b=[1/0,1/0,-1/0,-1/0];o.forEach(function(t,e,i){H(b,t.extent)});var h=ct(b),l=at(b),P=De(Math.round(w*h/R),Math.round(w*l/R)),u=w/R;o.forEach(function(t,e,i){var r=t.extent[0]-b[0],n=-(t.extent[3]-b[3]),o=ct(t.extent),s=at(t.extent);P.drawImage(t.image,a,a,t.image.width-2*a,t.image.height-2*a,r*u,n*u,o*u,s*u)});var F=lt(r);return n.getTriangles().forEach(function(t,e,i){var r=t.source,n=t.target,o=r[0][0],s=r[0][1],a=r[1][0],h=r[1][1],l=r[2][0],u=r[2][1],c=(n[0][0]-F[0])/I,p=-(n[0][1]-F[1])/I,d=(n[1][0]-F[0])/I,f=-(n[1][1]-F[1])/I,_=(n[2][0]-F[0])/I,g=-(n[2][1]-F[1])/I,y=o,v=s,m=function(t){for(var e=t.length,i=0;i<e;i++){for(var r=i,n=Math.abs(t[i][i]),o=i+1;o<e;o++){var s=Math.abs(t[o][i]);n<s&&(n=s,r=o)}if(0===n)return null;var a=t[r];t[r]=t[i],t[i]=a;for(var h=i+1;h<e;h++)for(var l=-t[h][i]/t[i][i],u=i;u<e+1;u++)i==u?t[h][u]=0:t[h][u]+=l*t[i][u]}for(var c=new Array(e),p=e-1;0<=p;p--){c[p]=t[p][e]/t[p][p];for(var d=p-1;0<=d;d--)t[d][e]-=t[d][p]*c[p]}return c}([[a-=y,h-=v,s=o=0,0,d-c],[l-=y,u-=v,0,0,_-c],[0,0,a,h,f-p],[0,0,l,u,g-p]]);if(m){L.save(),L.beginPath();var x=(c+d+_)/3,S=(p+f+g)/3,C=xx(x,S,c,p),E=xx(x,S,d,f),T=xx(x,S,_,g);L.moveTo(E[0],E[1]),L.lineTo(C[0],C[1]),L.lineTo(T[0],T[1]),L.clip(),L.transform(m[0],m[2],m[1],m[3],c,p),L.translate(b[0]-y,b[3]-v),L.scale(R/w,-R/w),L.drawImage(P.canvas,0,0),L.restore()}}),s&&(L.save(),L.strokeStyle="black",L.lineWidth=1,n.getTriangles().forEach(function(t,e,i){var r=t.target,n=(r[0][0]-F[0])/I,o=-(r[0][1]-F[1])/I,s=(r[1][0]-F[0])/I,a=-(r[1][1]-F[1])/I,h=(r[2][0]-F[0])/I,l=-(r[2][1]-F[1])/I;L.beginPath(),L.moveTo(s,a),L.lineTo(n,o),L.lineTo(h,l),L.closePath(),L.stroke()}),L.restore()),L.canvas}var Cx=function(t,e,i,r,n){this.sourceProj_=t,this.targetProj_=e;var o={},s=pe(this.targetProj_,this.sourceProj_);this.transformInv_=function(t){var e=t[0]+"/"+t[1];return o[e]||(o[e]=s(t)),o[e]},this.maxSourceExtent_=r,this.errorThresholdSquared_=n*n,this.triangles_=[],this.wrapsXInSource_=!1,this.canWrapXInSource_=this.sourceProj_.canWrapX()&&!!r&&!!this.sourceProj_.getExtent()&&ct(r)==ct(this.sourceProj_.getExtent()),this.sourceWorldWidth_=this.sourceProj_.getExtent()?ct(this.sourceProj_.getExtent()):null,this.targetWorldWidth_=this.targetProj_.getExtent()?ct(this.targetProj_.getExtent()):null;var a=lt(i),h=ut(i),l=nt(i),u=rt(i),c=this.transformInv_(a),p=this.transformInv_(h),d=this.transformInv_(l),f=this.transformInv_(u);if(this.addQuad_(a,h,l,u,c,p,d,f,10),this.wrapsXInSource_){var _=1/0;this.triangles_.forEach(function(t,e,i){_=Math.min(_,t.source[0][0],t.source[1][0],t.source[2][0])}),this.triangles_.forEach(function(t){if(Math.max(t.source[0][0],t.source[1][0],t.source[2][0])-_>this.sourceWorldWidth_/2){var e=[[t.source[0][0],t.source[0][1]],[t.source[1][0],t.source[1][1]],[t.source[2][0],t.source[2][1]]];e[0][0]-_>this.sourceWorldWidth_/2&&(e[0][0]-=this.sourceWorldWidth_),e[1][0]-_>this.sourceWorldWidth_/2&&(e[1][0]-=this.sourceWorldWidth_),e[2][0]-_>this.sourceWorldWidth_/2&&(e[2][0]-=this.sourceWorldWidth_);var i=Math.min(e[0][0],e[1][0],e[2][0]);Math.max(e[0][0],e[1][0],e[2][0])-i<this.sourceWorldWidth_/2&&(t.source=e)}}.bind(this))}o={}};Cx.prototype.addTriangle_=function(t,e,i,r,n,o){this.triangles_.push({source:[r,n,o],target:[t,e,i]})},Cx.prototype.addQuad_=function(t,e,i,r,n,o,s,a,h){var l=A([n,o,s,a]),u=this.sourceWorldWidth_?ct(l)/this.sourceWorldWidth_:null,c=this.sourceWorldWidth_,p=this.sourceProj_.canWrapX()&&.5<u&&u<1,d=!1;if(0<h){if(this.targetProj_.isGlobal()&&this.targetWorldWidth_)d|=.25<ct(A([t,e,i,r]))/this.targetWorldWidth_;!p&&this.sourceProj_.isGlobal()&&u&&(d|=.25<u)}if(d||!this.maxSourceExtent_||wt(l,this.maxSourceExtent_)){if(!(d||isFinite(n[0])&&isFinite(n[1])&&isFinite(o[0])&&isFinite(o[1])&&isFinite(s[0])&&isFinite(s[1])&&isFinite(a[0])&&isFinite(a[1]))){if(!(0<h))return;d=!0}if(0<h){if(!d){var f,_=[(t[0]+i[0])/2,(t[1]+i[1])/2],g=this.transformInv_(_);if(p)f=(Ct(n[0],c)+Ct(s[0],c))/2-Ct(g[0],c);else f=(n[0]+s[0])/2-g[0];var y=(n[1]+s[1])/2-g[1];d=f*f+y*y>this.errorThresholdSquared_}if(d){if(Math.abs(t[0]-i[0])<=Math.abs(t[1]-i[1])){var v=[(e[0]+i[0])/2,(e[1]+i[1])/2],m=this.transformInv_(v),x=[(r[0]+t[0])/2,(r[1]+t[1])/2],S=this.transformInv_(x);this.addQuad_(t,e,v,x,n,o,m,S,h-1),this.addQuad_(x,v,i,r,S,m,s,a,h-1)}else{var C=[(t[0]+e[0])/2,(t[1]+e[1])/2],E=this.transformInv_(C),T=[(i[0]+r[0])/2,(i[1]+r[1])/2],w=this.transformInv_(T);this.addQuad_(t,C,T,r,n,E,w,a,h-1),this.addQuad_(C,e,i,T,E,o,s,w,h-1)}return}}if(p){if(!this.canWrapXInSource_)return;this.wrapsXInSource_=!0}this.addTriangle_(t,i,r,n,s,a),this.addTriangle_(t,e,i,n,o,s)}},Cx.prototype.calculateSourceExtent=function(){var n=[1/0,1/0,-1/0,-1/0];return this.triangles_.forEach(function(t,e,i){var r=t.source;q(n,r[0]),q(n,r[1]),q(n,r[2])}),n},Cx.prototype.getTriangles=function(){return this.triangles_};var Ex=function(T){function t(t,e,i,r,n,o,s,a,h,l,u){T.call(this,n,Nn),this.renderEdges_=void 0!==u&&u,this.pixelRatio_=s,this.gutter_=a,this.canvas_=null,this.sourceTileGrid_=e,this.targetTileGrid_=r,this.wrappedTileCoord_=o||n,this.sourceTiles_=[],this.sourcesListenerKeys_=null,this.sourceZ_=0;var c=r.getTileCoordExtent(this.wrappedTileCoord_),p=this.targetTileGrid_.getExtent(),d=this.sourceTileGrid_.getExtent(),f=p?ht(c,p):c;if(0!==it(f)){var _=t.getExtent();_&&(d=d?ht(d,_):_);var g=r.getResolution(this.wrappedTileCoord_[0]),y=mx(t,i,ot(f),g);if(!isFinite(y)||y<=0)this.state=Dn;else{var v=void 0!==l?l:.5;if(this.triangulation_=new Cx(t,i,f,d,y*v),0!==this.triangulation_.getTriangles().length){this.sourceZ_=e.getZForResolution(y);var m=this.triangulation_.calculateSourceExtent();if(d&&(t.canWrapX()?(m[1]=gt(m[1],d[1],d[3]),m[3]=gt(m[3],d[1],d[3])):m=ht(m,d)),it(m)){for(var x=e.getTileRangeForExtentAndZ(m,this.sourceZ_),S=x.minX;S<=x.maxX;S++)for(var C=x.minY;C<=x.maxY;C++){var E=h(this.sourceZ_,S,C,s);E&&this.sourceTiles_.push(E)}0===this.sourceTiles_.length&&(this.state=Dn)}else this.state=Dn}else this.state=Dn}}else this.state=Dn}return T&&(t.__proto__=T),((t.prototype=Object.create(T&&T.prototype)).constructor=t).prototype.disposeInternal=function(){this.state==An&&this.unlistenSources_(),T.prototype.disposeInternal.call(this)},t.prototype.getImage=function(){return this.canvas_},t.prototype.reproject_=function(){var r=[];if(this.sourceTiles_.forEach(function(t,e,i){t&&t.getState()==Gn&&r.push({extent:this.sourceTileGrid_.getTileCoordExtent(t.tileCoord),image:t.getImage()})}.bind(this)),(this.sourceTiles_.length=0)===r.length)this.state=kn;else{var t=this.wrappedTileCoord_[0],e=this.targetTileGrid_.getTileSize(t),i="number"==typeof e?e:e[0],n="number"==typeof e?e:e[1],o=this.targetTileGrid_.getResolution(t),s=this.sourceTileGrid_.getResolution(this.sourceZ_),a=this.targetTileGrid_.getTileCoordExtent(this.wrappedTileCoord_);this.canvas_=Sx(i,n,this.pixelRatio_,s,this.sourceTileGrid_.getExtent(),o,a,this.triangulation_,r,this.gutter_,this.renderEdges_),this.state=Gn}this.changed()},t.prototype.load=function(){if(this.state==Nn){this.state=An,this.changed();var o=0;this.sourcesListenerKeys_=[],this.sourceTiles_.forEach(function(i,t,e){var r=i.getState();if(r==Nn||r==An){o++;var n=E(i,w.CHANGE,function(t){var e=i.getState();e!=Gn&&e!=kn&&e!=Dn||(g(n),0===--o&&(this.unlistenSources_(),this.reproject_()))},this);this.sourcesListenerKeys_.push(n)}}.bind(this)),this.sourceTiles_.forEach(function(t,e,i){t.getState()==Nn&&t.load()}),0===o&&setTimeout(this.reproject_.bind(this),0)}},t.prototype.unlistenSources_=function(){this.sourcesListenerKeys_.forEach(g),this.sourcesListenerKeys_=null},t}(zn),Tx=[0,0,0],wx=function(t){var r,n,o,e;if(this.minZoom=void 0!==t.minZoom?t.minZoom:0,this.resolutions_=t.resolutions,Z((r=this.resolutions_,n=!0,o=function(t,e){return e-t}||hr,r.every(function(t,e){if(0===e)return!0;var i=o(r[e-1],t);return!(0<i||n&&0===i)})),17),!t.origins)for(var i=0,s=this.resolutions_.length-1;i<s;++i)if(e){if(this.resolutions_[i]/this.resolutions_[i+1]!==e){e=void 0;break}}else e=this.resolutions_[i]/this.resolutions_[i+1];this.zoomFactor_=e,this.maxZoom=this.resolutions_.length-1,this.origin_=void 0!==t.origin?t.origin:null,this.origins_=null,void 0!==t.origins&&(this.origins_=t.origins,Z(this.origins_.length==this.resolutions_.length,20));var a=t.extent;void 0===a||this.origin_||this.origins_||(this.origin_=lt(a)),Z(!this.origin_&&this.origins_||this.origin_&&!this.origins_,18),this.tileSizes_=null,void 0!==t.tileSizes&&(this.tileSizes_=t.tileSizes,Z(this.tileSizes_.length==this.resolutions_.length,19)),this.tileSize_=void 0!==t.tileSize?t.tileSize:this.tileSizes_?null:$o,Z(!this.tileSize_&&this.tileSizes_||this.tileSize_&&!this.tileSizes_,22),this.extent_=void 0!==a?a:null,this.fullTileRanges_=null,this.tmpSize_=[0,0],void 0!==t.sizes?this.fullTileRanges_=t.sizes.map(function(t,e){return new Vl(Math.min(0,t[0]),Math.max(t[0]-1,-1),Math.min(0,t[1]),Math.max(t[1]-1,-1))},this):a&&this.calculateTileRanges_(a)};function Rx(t){var e=t.getDefaultTileGrid();return e||(e=Px(t),t.setDefaultTileGrid(e)),e}function Ix(t,e,i,r){var n,o,s,a=void 0!==r?r:O.TOP_LEFT,h=bx(t,e,i);return new wx({extent:t,origin:(n=t,o=a,o===O.BOTTOM_LEFT?s=rt(n):o===O.BOTTOM_RIGHT?s=nt(n):o===O.TOP_LEFT?s=lt(n):o===O.TOP_RIGHT?s=ut(n):Z(!1,13),s),resolutions:h,tileSize:i})}function Lx(t){var e={};return C(e,void 0!==t?t:{}),void 0===e.extent&&(e.extent=ne("EPSG:3857").getExtent()),e.resolutions=bx(e.extent,e.maxZoom,e.tileSize),delete e.maxZoom,new wx(e)}function bx(t,e,i){for(var r=void 0!==e?e:Qo,n=at(t),o=ct(t),s=ws(void 0!==i?i:$o),a=Math.max(o/s[0],n/s[1]),h=r+1,l=new Array(h),u=0;u<h;++u)l[u]=a/Math.pow(2,u);return l}function Px(t,e,i,r){return Ix(Fx(t),e,i,r)}function Fx(t){var e=(t=ne(t)).getExtent();if(!e){var i=180*Nt[Ot.DEGREES]/t.getMetersPerUnit();e=X(-i,-i,i,i)}return e}wx.prototype.forEachTileCoord=function(t,e,i){for(var r=this.getTileRangeForExtentAndZ(t,e),n=r.minX,o=r.maxX;n<=o;++n)for(var s=r.minY,a=r.maxY;s<=a;++s)i([e,n,s])},wx.prototype.forEachTileCoordParentTileRange=function(t,e,i,r,n){var o,s,a,h=null,l=t[0]-1;for(2===this.zoomFactor_?(s=t[1],a=t[2]):h=this.getTileCoordExtent(t,n);l>=this.minZoom;){if(o=2===this.zoomFactor_?Wl(s=Math.floor(s/2),s,a=Math.floor(a/2),a,r):this.getTileRangeForExtentAndZ(h,l,r),e.call(i,l,o))return!0;--l}return!1},wx.prototype.getExtent=function(){return this.extent_},wx.prototype.getMaxZoom=function(){return this.maxZoom},wx.prototype.getMinZoom=function(){return this.minZoom},wx.prototype.getOrigin=function(t){return this.origin_?this.origin_:this.origins_[t]},wx.prototype.getResolution=function(t){return this.resolutions_[t]},wx.prototype.getResolutions=function(){return this.resolutions_},wx.prototype.getTileCoordChildTileRange=function(t,e,i){if(t[0]<this.maxZoom){if(2===this.zoomFactor_){var r=2*t[1],n=2*t[2];return Wl(r,r+1,n,n+1,e)}var o=this.getTileCoordExtent(t,i);return this.getTileRangeForExtentAndZ(o,t[0]+1,e)}return null},wx.prototype.getTileRangeExtent=function(t,e,i){var r=this.getOrigin(t),n=this.getResolution(t),o=ws(this.getTileSize(t),this.tmpSize_),s=r[0]+e.minX*o[0]*n,a=r[0]+(e.maxX+1)*o[0]*n;return X(s,r[1]+e.minY*o[1]*n,a,r[1]+(e.maxY+1)*o[1]*n,i)},wx.prototype.getTileRangeForExtentAndZ=function(t,e,i){var r=Tx;this.getTileCoordForXYAndZ_(t[0],t[1],e,!1,r);var n=r[1],o=r[2];return this.getTileCoordForXYAndZ_(t[2],t[3],e,!0,r),Wl(n,r[1],o,r[2],i)},wx.prototype.getTileCoordCenter=function(t){var e=this.getOrigin(t[0]),i=this.getResolution(t[0]),r=ws(this.getTileSize(t[0]),this.tmpSize_);return[e[0]+(t[1]+.5)*r[0]*i,e[1]+(t[2]+.5)*r[1]*i]},wx.prototype.getTileCoordExtent=function(t,e){var i=this.getOrigin(t[0]),r=this.getResolution(t[0]),n=ws(this.getTileSize(t[0]),this.tmpSize_),o=i[0]+t[1]*n[0]*r,s=i[1]+t[2]*n[1]*r;return X(o,s,o+n[0]*r,s+n[1]*r,e)},wx.prototype.getTileCoordForCoordAndResolution=function(t,e,i){return this.getTileCoordForXYAndResolution_(t[0],t[1],e,!1,i)},wx.prototype.getTileCoordForXYAndResolution_=function(t,e,i,r,n){var o=this.getZForResolution(i),s=i/this.getResolution(o),a=this.getOrigin(o),h=ws(this.getTileSize(o),this.tmpSize_),l=r?.5:0,u=r?0:.5,c=Math.floor((t-a[0])/i+l),p=Math.floor((e-a[1])/i+u),d=s*c/h[0],f=s*p/h[1];return r?(d=Math.ceil(d)-1,f=Math.ceil(f)-1):(d=Math.floor(d),f=Math.floor(f)),hx(o,d,f,n)},wx.prototype.getTileCoordForXYAndZ_=function(t,e,i,r,n){var o=this.getOrigin(i),s=this.getResolution(i),a=ws(this.getTileSize(i),this.tmpSize_),h=r?.5:0,l=r?0:.5,u=Math.floor((t-o[0])/s+h),c=Math.floor((e-o[1])/s+l),p=u/a[0],d=c/a[1];return r?(p=Math.ceil(p)-1,d=Math.ceil(d)-1):(p=Math.floor(p),d=Math.floor(d)),hx(i,p,d,n)},wx.prototype.getTileCoordForCoordAndZ=function(t,e,i){return this.getTileCoordForXYAndZ_(t[0],t[1],e,!1,i)},wx.prototype.getTileCoordResolution=function(t){return this.resolutions_[t[0]]},wx.prototype.getTileSize=function(t){return this.tileSize_?this.tileSize_:this.tileSizes_[t]},wx.prototype.getFullTileRange=function(t){return this.fullTileRanges_?this.fullTileRanges_[t]:null},wx.prototype.getZForResolution=function(t,e){return gt(ur(this.resolutions_,t,e||0),this.minZoom,this.maxZoom)},wx.prototype.calculateTileRanges_=function(t){for(var e=this.resolutions_.length,i=new Array(e),r=this.minZoom;r<e;++r)i[r]=this.getTileRangeForExtentAndZ(t,r);this.fullTileRanges_=i};var Mx=function(e){function t(t){e.call(this,{attributions:t.attributions,extent:t.extent,projection:t.projection,state:t.state,wrapX:t.wrapX}),this.opaque_=void 0!==t.opaque&&t.opaque,this.tilePixelRatio_=void 0!==t.tilePixelRatio?t.tilePixelRatio:1,this.tileGrid=void 0!==t.tileGrid?t.tileGrid:null,this.tileCache=new vx(t.cacheSize),this.tmpSize=[0,0],this.key_="",this.tileOptions={transition:t.transition}}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.canExpireCache=function(){return this.tileCache.canExpireCache()},t.prototype.expireCache=function(t,e){var i=this.getTileCacheForProjection(t);i&&i.expireCache(e)},t.prototype.forEachLoadedTile=function(t,e,i,r){var n=this.getTileCacheForProjection(t);if(!n)return!1;for(var o,s,a,h=!0,l=i.minX;l<=i.maxX;++l)for(var u=i.minY;u<=i.maxY;++u)s=lx(e,l,u),a=!1,n.containsKey(s)&&(a=(o=n.get(s)).getState()===Gn)&&(a=!1!==r(o)),a||(h=!1);return h},t.prototype.getGutter=function(t){return 0},t.prototype.getKey=function(){return this.key_},t.prototype.setKey=function(t){this.key_!==t&&(this.key_=t,this.changed())},t.prototype.getOpaque=function(t){return this.opaque_},t.prototype.getResolutions=function(){return this.tileGrid.getResolutions()},t.prototype.getTile=function(t,e,i,r,n){},t.prototype.getTileGrid=function(){return this.tileGrid},t.prototype.getTileGridForProjection=function(t){return this.tileGrid?this.tileGrid:Rx(t)},t.prototype.getTileCacheForProjection=function(t){var e=this.getProjection();return e&&!ue(e,t)?null:this.tileCache},t.prototype.getTilePixelRatio=function(t){return this.tilePixelRatio_},t.prototype.getTilePixelSize=function(t,e,i){var r=this.getTileGridForProjection(i),n=this.getTilePixelRatio(e),o=ws(r.getTileSize(t),this.tmpSize);return 1==n?o:Ts(o,n,this.tmpSize)},t.prototype.getTileCoordForTileUrlFunction=function(t,e){var i=void 0!==e?e:this.getProjection(),r=this.getTileGridForProjection(i);return this.getWrapX()&&i.isGlobal()&&(t=function(t,e,i){var r=e[0],n=t.getTileCoordCenter(e),o=Fx(i);if(j(o,n))return e;var s=ct(o),a=Math.ceil((o[0]-n[0])/s);return n[0]+=s*a,t.getTileCoordForCoordAndZ(n,r)}(r,t,i)),function(t,e){var i=t[0],r=t[1],n=t[2];if(e.getMinZoom()>i||i>e.getMaxZoom())return!1;var o,s=e.getExtent();return!(o=s?e.getTileRangeForExtentAndZ(s,i):e.getFullTileRange(i))||o.containsXY(r,n)}(t,r)?t:null},t.prototype.refresh=function(){this.tileCache.clear(),this.changed()},t}(fh);Mx.prototype.useTile=L;var Ox=function(i){function t(t,e){i.call(this,t),this.tile=e}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(m),Nx="tileloadstart",Ax="tileloadend",Gx="tileloaderror",kx=function(e){function t(t){e.call(this,{attributions:t.attributions,cacheSize:t.cacheSize,extent:t.extent,opaque:t.opaque,projection:t.projection,state:t.state,tileGrid:t.tileGrid,tilePixelRatio:t.tilePixelRatio,wrapX:t.wrapX,transition:t.transition}),this.tileLoadFunction=t.tileLoadFunction,this.tileUrlFunction=this.fixedTileUrlFunction?this.fixedTileUrlFunction.bind(this):_x,this.urls=null,t.urls?this.setUrls(t.urls):t.url&&this.setUrl(t.url),t.tileUrlFunction&&this.setTileUrlFunction(t.tileUrlFunction),this.tileLoadingKeys_={}}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.getTileLoadFunction=function(){return this.tileLoadFunction},t.prototype.getTileUrlFunction=function(){return this.tileUrlFunction},t.prototype.getUrls=function(){return this.urls},t.prototype.handleTileChange=function(t){var e,i=t.target,r=Et(i),n=i.getState();n==An?(this.tileLoadingKeys_[r]=!0,e=Nx):r in this.tileLoadingKeys_&&(delete this.tileLoadingKeys_[r],e=n==kn?Gx:n==Gn||n==jn?Ax:void 0),null!=e&&this.dispatchEvent(new Ox(e,i))},t.prototype.setTileLoadFunction=function(t){this.tileCache.clear(),this.tileLoadFunction=t,this.changed()},t.prototype.setTileUrlFunction=function(t,e){this.tileUrlFunction=t,this.tileCache.pruneExceptNewestZ(),void 0!==e?this.setKey(e):this.changed()},t.prototype.setUrl=function(t){var e=this.urls=gx(t);this.setTileUrlFunction(this.fixedTileUrlFunction?this.fixedTileUrlFunction.bind(this):dx(e,this.tileGrid),t)},t.prototype.setUrls=function(t){var e=(this.urls=t).join("\n");this.setTileUrlFunction(this.fixedTileUrlFunction?this.fixedTileUrlFunction.bind(this):dx(t,this.tileGrid),e)},t.prototype.useTile=function(t,e,i){var r=lx(t,e,i);this.tileCache.containsKey(r)&&this.tileCache.get(r)},t}(Mx);kx.prototype.fixedTileUrlFunction;var Dx=function(e){function t(t){e.call(this,{attributions:t.attributions,cacheSize:t.cacheSize,extent:t.extent,opaque:t.opaque,projection:t.projection,state:t.state,tileGrid:t.tileGrid,tileLoadFunction:t.tileLoadFunction?t.tileLoadFunction:jx,tilePixelRatio:t.tilePixelRatio,tileUrlFunction:t.tileUrlFunction,url:t.url,urls:t.urls,wrapX:t.wrapX,transition:t.transition}),this.crossOrigin=void 0!==t.crossOrigin?t.crossOrigin:null,this.tileClass=void 0!==t.tileClass?t.tileClass:Vn,this.tileCacheForProjection={},this.tileGridForProjection={},this.reprojectionErrorThreshold_=t.reprojectionErrorThreshold,this.renderReprojectionEdges_=!1}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.canExpireCache=function(){if(this.tileCache.canExpireCache())return!0;for(var t in this.tileCacheForProjection)if(this.tileCacheForProjection[t].canExpireCache())return!0;return!1},t.prototype.expireCache=function(t,e){var i=this.getTileCacheForProjection(t);for(var r in this.tileCache.expireCache(this.tileCache==i?e:{}),this.tileCacheForProjection){var n=this.tileCacheForProjection[r];n.expireCache(n==i?e:{})}},t.prototype.getGutter=function(t){return this.getProjection()&&t&&!ue(this.getProjection(),t)?0:this.getGutterInternal()},t.prototype.getGutterInternal=function(){return 0},t.prototype.getOpaque=function(t){return!(this.getProjection()&&t&&!ue(this.getProjection(),t))&&e.prototype.getOpaque.call(this,t)},t.prototype.getTileGridForProjection=function(t){var e=this.getProjection();if(!this.tileGrid||e&&!ue(e,t)){var i=Et(t).toString();return i in this.tileGridForProjection||(this.tileGridForProjection[i]=Rx(t)),this.tileGridForProjection[i]}return this.tileGrid},t.prototype.getTileCacheForProjection=function(t){var e=this.getProjection();if(!e||ue(e,t))return this.tileCache;var i=Et(t).toString();return i in this.tileCacheForProjection||(this.tileCacheForProjection[i]=new vx(this.tileCache.highWaterMark)),this.tileCacheForProjection[i]},t.prototype.createTile_=function(t,e,i,r,n,o){var s=[t,e,i],a=this.getTileCoordForTileUrlFunction(s,n),h=a?this.tileUrlFunction(a,r,n):void 0,l=new this.tileClass(s,void 0!==h?Nn:Dn,void 0!==h?h:"",this.crossOrigin,this.tileLoadFunction,this.tileOptions);return l.key=o,E(l,w.CHANGE,this.handleTileChange,this),l},t.prototype.getTile=function(t,e,i,r,n){var o=this.getProjection();if(o&&n&&!ue(o,n)){var s,a=this.getTileCacheForProjection(n),h=[t,e,i],l=ux(h);a.containsKey(l)&&(s=a.get(l));var u=this.getKey();if(s&&s.key==u)return s;var c=this.getTileGridForProjection(o),p=this.getTileGridForProjection(n),d=this.getTileCoordForTileUrlFunction(h,n),f=new Ex(o,c,n,p,h,d,this.getTilePixelRatio(r),this.getGutterInternal(),function(t,e,i,r){return this.getTileInternal(t,e,i,r,o)}.bind(this),this.reprojectionErrorThreshold_,this.renderReprojectionEdges_);return f.key=u,s?(f.interimTile=s,f.refreshInterimChain(),a.replace(l,f)):a.set(l,f),f}return this.getTileInternal(t,e,i,r,o||n)},t.prototype.getTileInternal=function(t,e,i,r,n){var o=null,s=lx(t,e,i),a=this.getKey();if(this.tileCache.containsKey(s)){if((o=this.tileCache.get(s)).key!=a){var h=o;o=this.createTile_(t,e,i,r,n,a),h.getState()==Nn?o.interimTile=h.interimTile:o.interimTile=h,o.refreshInterimChain(),this.tileCache.replace(s,o)}}else o=this.createTile_(t,e,i,r,n,a),this.tileCache.set(s,o);return o},t.prototype.setRenderReprojectionEdges=function(t){if(this.renderReprojectionEdges_!=t){for(var e in this.renderReprojectionEdges_=t,this.tileCacheForProjection)this.tileCacheForProjection[e].clear();this.changed()}},t.prototype.setTileGridForProjection=function(t,e){var i=ne(t);if(i){var r=Et(i).toString();r in this.tileGridForProjection||(this.tileGridForProjection[r]=e)}},t}(kx);function jx(t,e){t.getImage().src=e}var Ux=function(i){function t(t){var e=void 0!==t.hidpi&&t.hidpi;i.call(this,{cacheSize:t.cacheSize,crossOrigin:"anonymous",opaque:!0,projection:ne("EPSG:3857"),reprojectionErrorThreshold:t.reprojectionErrorThreshold,state:vs,tileLoadFunction:t.tileLoadFunction,tilePixelRatio:e?2:1,wrapX:void 0===t.wrapX||t.wrapX,transition:t.transition}),this.hidpi_=e,this.culture_=void 0!==t.culture?t.culture:"en-us",this.maxZoom_=void 0!==t.maxZoom?t.maxZoom:-1,this.apiKey_=t.key,this.imagerySet_=t.imagerySet,yx("https://dev.virtualearth.net/REST/v1/Imagery/Metadata/"+this.imagerySet_+"?uriScheme=https&include=ImageryProviders&key="+this.apiKey_+"&c="+this.culture_,this.handleImageryMetadataResponse.bind(this),void 0,"jsonp")}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.getApiKey=function(){return this.apiKey_},t.prototype.getImagerySet=function(){return this.imagerySet_},t.prototype.handleImageryMetadataResponse=function(t){if(200==t.statusCode&&"OK"==t.statusDescription&&"ValidCredentials"==t.authenticationResultCode&&1==t.resourceSets.length&&1==t.resourceSets[0].resources.length){var e=t.resourceSets[0].resources[0],i=-1==this.maxZoom_?e.zoomMax:this.maxZoom_,r=Fx(this.getProjection()),n=e.imageWidth==e.imageHeight?e.imageWidth:[e.imageWidth,e.imageHeight],o=Lx({extent:r,minZoom:e.zoomMin,maxZoom:i,tileSize:n/(this.hidpi_?2:1)});this.tileGrid=o;var s=this.culture_,a=this.hidpi_;if(this.tileUrlFunction=fx(e.imageUrlSubdomains.map(function(t){var n=[0,0,0],o=e.imageUrl.replace("{subdomain}",t).replace("{culture}",s);return function(t,e,i){if(t){hx(t[0],t[1],-t[2]-1,n);var r=o;return a&&(r+="&dpi=d1&device=mobile"),r.replace("{quadkey}",function(t){var e,i,r=t[0],n=new Array(r),o=1<<r-1;for(e=0;e<r;++e)i=48,t[1]&o&&(i+=1),t[2]&o&&(i+=2),n[e]=String.fromCharCode(i),o>>=1;return n.join("")}(n))}}})),e.imageryProviders){var u=ce(ne("EPSG:4326"),this.getProjection());this.setAttributions(function(a){var h=[],l=a.viewState.zoom;return e.imageryProviders.map(function(t){for(var e=!1,i=t.coverageAreas,r=0,n=i.length;r<n;++r){var o=i[r];if(l>=o.zoomMin&&l<=o.zoomMax){var s=o.bbox;if(wt(ft([s[1],s[0],s[3],s[2]],u),a.extent)){e=!0;break}}}e&&h.push(t.attribution)}),h.push('<a class="ol-attribution-bing-tos" href="https://www.microsoft.com/maps/product/terms.html">Terms of Use</a>'),h})}this.setState(ms)}else this.setState(xs)},t}(Dx),Yx=function(n){function t(t){var e=t||{},i=void 0!==e.projection?e.projection:"EPSG:3857",r=void 0!==e.tileGrid?e.tileGrid:Lx({extent:Fx(i),maxZoom:e.maxZoom,minZoom:e.minZoom,tileSize:e.tileSize});n.call(this,{attributions:e.attributions,cacheSize:e.cacheSize,crossOrigin:e.crossOrigin,opaque:e.opaque,projection:i,reprojectionErrorThreshold:e.reprojectionErrorThreshold,tileGrid:r,tileLoadFunction:e.tileLoadFunction,tilePixelRatio:e.tilePixelRatio,tileUrlFunction:e.tileUrlFunction,url:e.url,urls:e.urls,wrapX:void 0===e.wrapX||e.wrapX,transition:e.transition})}return n&&(t.__proto__=n),(t.prototype=Object.create(n&&n.prototype)).constructor=t}(Dx),Bx=function(e){function t(t){e.call(this,{attributions:t.attributions,cacheSize:t.cacheSize,crossOrigin:t.crossOrigin,maxZoom:void 0!==t.maxZoom?t.maxZoom:18,minZoom:t.minZoom,projection:t.projection,state:vs,wrapX:t.wrapX}),this.account_=t.account,this.mapId_=t.map||"",this.config_=t.config||{},this.templateCache_={},this.initializeMap_()}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.getConfig=function(){return this.config_},t.prototype.updateConfig=function(t){C(this.config_,t),this.initializeMap_()},t.prototype.setConfig=function(t){this.config_=t||{},this.initializeMap_()},t.prototype.initializeMap_=function(){var t=JSON.stringify(this.config_);if(this.templateCache_[t])this.applyTemplate_(this.templateCache_[t]);else{var e="https://"+this.account_+".carto.com/api/v1/map";this.mapId_&&(e+="/named/"+this.mapId_);var i=new XMLHttpRequest;i.addEventListener("load",this.handleInitResponse_.bind(this,t)),i.addEventListener("error",this.handleInitError_.bind(this)),i.open("POST",e),i.setRequestHeader("Content-type","application/json"),i.send(JSON.stringify(this.config_))}},t.prototype.handleInitResponse_=function(t,e){var i=e.target;if(!i.status||200<=i.status&&i.status<300){var r;try{r=JSON.parse(i.responseText)}catch(t){return void this.setState(xs)}this.applyTemplate_(r),this.templateCache_[t]=r,this.setState(ms)}else this.setState(xs)},t.prototype.handleInitError_=function(t){this.setState(xs)},t.prototype.applyTemplate_=function(t){var e="https://"+t.cdn_url.https+"/"+this.account_+"/api/v1/map/"+t.layergroupid+"/{z}/{x}/{y}.png";this.setUrl(e)},t}(Yx),Xx=function(e){function t(t){e.call(this,{attributions:t.attributions,extent:t.extent,projection:t.projection,wrapX:t.wrapX}),this.resolution=void 0,this.distance=void 0!==t.distance?t.distance:20,this.features=[],this.geometryFunction=t.geometryFunction||function(t){var e=t.getGeometry();return Z(e instanceof Dr,10),e},this.source=t.source,E(this.source,w.CHANGE,this.refresh,this)}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.getDistance=function(){return this.distance},t.prototype.getSource=function(){return this.source},t.prototype.loadFeatures=function(t,e,i){this.source.loadFeatures(t,e,i),e!==this.resolution&&(this.clear(),this.resolution=e,this.cluster(),this.addFeatures(this.features))},t.prototype.setDistance=function(t){this.distance=t,this.refresh()},t.prototype.refresh=function(){this.clear(),this.cluster(),this.addFeatures(this.features),e.prototype.refresh.call(this)},t.prototype.cluster=function(){if(void 0!==this.resolution)for(var t=[1/(this.features.length=0),1/0,-1/0,-1/0],e=this.distance*this.resolution,i=this.source.getFeatures(),r={},n=0,o=i.length;n<o;n++){var s=i[n];if(!(Et(s).toString()in r)){var a=this.geometryFunction(s);if(a){V(a.getCoordinates(),t),G(t,e,t);var h=this.source.getFeaturesInExtent(t);h=h.filter(function(t){var e=Et(t).toString();return!(e in r)&&(r[e]=!0)}),this.features.push(this.createCluster(h))}}}},t.prototype.createCluster=function(t){for(var e=[0,0],i=t.length-1;0<=i;--i){var r=this.geometryFunction(t[i]);r?an(e,r.getCoordinates()):t.splice(i,1)}dn(e,1/t.length);var n=new Ji(new Dr(e));return n.set("features",t),n},t}(Dh),zx=function(f){function t(t,e,i,r,n,o){var s=t.getExtent(),a=e.getExtent(),h=a?ht(i,a):i,l=mx(t,e,ot(h),r),u=new Cx(t,e,h,s,.5*l),c=o(u.calculateSourceExtent(),l,n),p=di.LOADED;c&&(p=di.IDLE);var d=c?c.getPixelRatio():1;f.call(this,i,r,d,p),this.targetProj_=e,this.maxSourceExtent_=s,this.triangulation_=u,this.targetResolution_=r,this.targetExtent_=i,this.sourceImage_=c,this.sourcePixelRatio_=d,this.canvas_=null,this.sourceListenerKey_=null}return f&&(t.__proto__=f),((t.prototype=Object.create(f&&f.prototype)).constructor=t).prototype.disposeInternal=function(){this.state==di.LOADING&&this.unlistenSource_(),f.prototype.disposeInternal.call(this)},t.prototype.getImage=function(){return this.canvas_},t.prototype.getProjection=function(){return this.targetProj_},t.prototype.reproject_=function(){var t=this.sourceImage_.getState();if(t==di.LOADED){var e=ct(this.targetExtent_)/this.targetResolution_,i=at(this.targetExtent_)/this.targetResolution_;this.canvas_=Sx(e,i,this.sourcePixelRatio_,this.sourceImage_.getResolution(),this.maxSourceExtent_,this.targetResolution_,this.targetExtent_,this.triangulation_,[{extent:this.sourceImage_.getExtent(),image:this.sourceImage_.getImage()}],0)}this.state=t,this.changed()},t.prototype.load=function(){if(this.state==di.IDLE){this.state=di.LOADING,this.changed();var t=this.sourceImage_.getState();t==di.LOADED||t==di.ERROR?this.reproject_():(this.sourceListenerKey_=E(this.sourceImage_,w.CHANGE,function(t){var e=this.sourceImage_.getState();e!=di.LOADED&&e!=di.ERROR||(this.unlistenSource_(),this.reproject_())},this),this.sourceImage_.load())}},t.prototype.unlistenSource_=function(){g(this.sourceListenerKey_),this.sourceListenerKey_=null},t}(Mn),Vx="imageloadstart",Wx="imageloadend",Kx="imageloaderror",Hx=function(i){function t(t,e){i.call(this,t),this.image=e}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(m),Zx=function(e){function t(t){e.call(this,{attributions:t.attributions,extent:t.extent,projection:t.projection,state:t.state}),this.resolutions_=void 0!==t.resolutions?t.resolutions:null,this.reprojectedImage_=null,this.reprojectedRevision_=0}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.getResolutions=function(){return this.resolutions_},t.prototype.findNearestResolution=function(t){if(this.resolutions_){var e=ur(this.resolutions_,t,0);t=this.resolutions_[e]}return t},t.prototype.getImage=function(t,e,i,r){var n=this.getProjection();if(n&&r&&!ue(n,r)){if(this.reprojectedImage_){if(this.reprojectedRevision_==this.getRevision()&&ue(this.reprojectedImage_.getProjection(),r)&&this.reprojectedImage_.getResolution()==e&&$(this.reprojectedImage_.getExtent(),t))return this.reprojectedImage_;this.reprojectedImage_.dispose(),this.reprojectedImage_=null}return this.reprojectedImage_=new zx(n,r,t,e,i,function(t,e,i){return this.getImageInternal(t,e,i,n)}.bind(this)),this.reprojectedRevision_=this.getRevision(),this.reprojectedImage_}return n&&(r=n),this.getImageInternal(t,e,i,r)},t.prototype.getImageInternal=function(t,e,i,r){},t.prototype.handleImageChange=function(t){var e=t.target;switch(e.getState()){case di.LOADING:this.dispatchEvent(new Hx(Vx,e));break;case di.LOADED:this.dispatchEvent(new Hx(Wx,e));break;case di.ERROR:this.dispatchEvent(new Hx(Kx,e))}},t}(fh);function qx(t,e){t.getImage().src=e}function Jx(t,e){var i=[];Object.keys(e).forEach(function(t){null!==e[t]&&void 0!==e[t]&&i.push(t+"="+encodeURIComponent(e[t]))});var r=i.join("&");return(t=-1===(t=t.replace(/[?&]$/,"")).indexOf("?")?t+"?":t+"&")+r}var Qx=function(i){function t(t){var e=t||{};i.call(this,{attributions:e.attributions,projection:e.projection,resolutions:e.resolutions}),this.crossOrigin_=void 0!==e.crossOrigin?e.crossOrigin:null,this.hidpi_=void 0===e.hidpi||e.hidpi,this.url_=e.url,this.imageLoadFunction_=void 0!==e.imageLoadFunction?e.imageLoadFunction:qx,this.params_=e.params||{},this.image_=null,this.imageSize_=[0,0],this.renderedRevision_=0,this.ratio_=void 0!==e.ratio?e.ratio:1.5}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.getParams=function(){return this.params_},t.prototype.getImageInternal=function(t,e,i,r){if(void 0===this.url_)return null;e=this.findNearestResolution(e),i=this.hidpi_?i:1;var n=this.image_;if(n&&this.renderedRevision_==this.getRevision()&&n.getResolution()==e&&n.getPixelRatio()==i&&Q(n.getExtent(),t))return n;var o={F:"image",FORMAT:"PNG32",TRANSPARENT:!0};C(o,this.params_);var s=((t=t.slice())[0]+t[2])/2,a=(t[1]+t[3])/2;if(1!=this.ratio_){var h=this.ratio_*ct(t)/2,l=this.ratio_*at(t)/2;t[0]=s-h,t[1]=a-l,t[2]=s+h,t[3]=a+l}var u=e/i,c=Math.ceil(ct(t)/u),p=Math.ceil(at(t)/u);t[0]=s-u*c/2,t[2]=s+u*c/2,t[1]=a-u*p/2,t[3]=a+u*p/2,this.imageSize_[0]=c,this.imageSize_[1]=p;var d=this.getRequestUrl_(t,this.imageSize_,i,r,o);return this.image_=new On(t,e,i,d,this.crossOrigin_,this.imageLoadFunction_),this.renderedRevision_=this.getRevision(),E(this.image_,w.CHANGE,this.handleImageChange,this),this.image_},t.prototype.getImageLoadFunction=function(){return this.imageLoadFunction_},t.prototype.getRequestUrl_=function(t,e,i,r,n){var o=r.getCode().split(":").pop();n.SIZE=e[0]+","+e[1],n.BBOX=t.join(","),n.BBOXSR=o,n.IMAGESR=o,n.DPI=Math.round(90*i);var s=this.url_,a=s.replace(/MapServer\/?$/,"MapServer/export").replace(/ImageServer\/?$/,"ImageServer/exportImage");return a==s&&Z(!1,50),Jx(a,n)},t.prototype.getUrl=function(){return this.url_},t.prototype.setImageLoadFunction=function(t){this.image_=null,this.imageLoadFunction_=t,this.changed()},t.prototype.setUrl=function(t){t!=this.url_&&(this.url_=t,this.image_=null,this.changed())},t.prototype.updateParams=function(t){C(this.params_,t),this.image_=null,this.changed()},t}(Zx),$x=function(e){function t(t){e.call(this,{attributions:t.attributions,projection:t.projection,resolutions:t.resolutions,state:t.state}),this.canvasFunction_=t.canvasFunction,this.canvas_=null,this.renderedRevision_=0,this.ratio_=void 0!==t.ratio?t.ratio:1.5}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.getImageInternal=function(t,e,i,r){e=this.findNearestResolution(e);var n=this.canvas_;if(n&&this.renderedRevision_==this.getRevision()&&n.getResolution()==e&&n.getPixelRatio()==i&&Q(n.getExtent(),t))return n;dt(t=t.slice(),this.ratio_);var o=[ct(t)/e*i,at(t)/e*i],s=this.canvasFunction_(t,e,i,o,r);return s&&(n=new bl(t,e,i,s)),this.canvas_=n,this.renderedRevision_=this.getRevision(),n},t}(Zx),tS=function(e){function t(t){e.call(this,{projection:t.projection,resolutions:t.resolutions}),this.crossOrigin_=void 0!==t.crossOrigin?t.crossOrigin:null,this.displayDpi_=void 0!==t.displayDpi?t.displayDpi:96,this.params_=t.params||{},this.url_=t.url,this.imageLoadFunction_=void 0!==t.imageLoadFunction?t.imageLoadFunction:qx,this.hidpi_=void 0===t.hidpi||t.hidpi,this.metersPerUnit_=void 0!==t.metersPerUnit?t.metersPerUnit:1,this.ratio_=void 0!==t.ratio?t.ratio:1,this.useOverlay_=void 0!==t.useOverlay&&t.useOverlay,this.image_=null,this.renderedRevision_=0}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.getParams=function(){return this.params_},t.prototype.getImageInternal=function(t,e,i,r){e=this.findNearestResolution(e),i=this.hidpi_?i:1;var n=this.image_;if(n&&this.renderedRevision_==this.getRevision()&&n.getResolution()==e&&n.getPixelRatio()==i&&Q(n.getExtent(),t))return n;1!=this.ratio_&&dt(t=t.slice(),this.ratio_);var o=[ct(t)/e*i,at(t)/e*i];if(void 0!==this.url_){var s=this.getUrl(this.url_,this.params_,t,o,r);E(n=new On(t,e,i,s,this.crossOrigin_,this.imageLoadFunction_),w.CHANGE,this.handleImageChange,this)}else n=null;return this.image_=n,this.renderedRevision_=this.getRevision(),n},t.prototype.getImageLoadFunction=function(){return this.imageLoadFunction_},t.prototype.updateParams=function(t){C(this.params_,t),this.changed()},t.prototype.getUrl=function(t,e,i,r,n){var o,s,a,h,l,u,c,p,d,f=(o=i,s=r,a=this.metersPerUnit_,h=this.displayDpi_,l=ct(o),u=at(o),c=s[0],p=s[1],d=.0254/h,c*u<p*l?l*a/(c*d):u*a/(p*d)),_=ot(i),g={OPERATION:this.useOverlay_?"GETDYNAMICMAPOVERLAYIMAGE":"GETMAPIMAGE",VERSION:"2.0.0",LOCALE:"en",CLIENTAGENT:"ol/source/ImageMapGuide source",CLIP:"1",SETDISPLAYDPI:this.displayDpi_,SETDISPLAYWIDTH:Math.round(r[0]),SETDISPLAYHEIGHT:Math.round(r[1]),SETVIEWSCALE:f,SETVIEWCENTERX:_[0],SETVIEWCENTERY:_[1]};return C(g,e),Jx(t,g)},t.prototype.setImageLoadFunction=function(t){this.image_=null,this.imageLoadFunction_=t,this.changed()},t}(Zx);var eS=function(l){function t(t){var e=t.imageExtent,i=void 0!==t.crossOrigin?t.crossOrigin:null,r=void 0!==t.imageLoadFunction?t.imageLoadFunction:qx;l.call(this,{attributions:t.attributions,projection:ne(t.projection)}),this.image_=new On(e,void 0,1,t.url,i,r),this.imageSize_=t.imageSize?t.imageSize:null,E(this.image_,w.CHANGE,this.handleImageChange,this)}return l&&(t.__proto__=l),((t.prototype=Object.create(l&&l.prototype)).constructor=t).prototype.getImageInternal=function(t,e,i,r){return wt(t,this.image_.getExtent())?this.image_:null},t.prototype.handleImageChange=function(t){if(this.image_.getState()==di.LOADED){var e,i,r=this.image_.getExtent(),n=this.image_.getImage();this.imageSize_?(e=this.imageSize_[0],i=this.imageSize_[1]):(e=n.width,i=n.height);var o=at(r)/i,s=Math.ceil(ct(r)/o);if(s!=e){var a=De(s,i),h=a.canvas;a.drawImage(n,0,0,e,i,0,0,h.width,h.height),this.image_.setImage(h)}}l.prototype.handleImageChange.call(this,t)},t}(Zx),iS="1.3.0",rS="carmentaserver",nS="geoserver",oS="mapserver",sS="qgis",aS=[101,101],hS=function(i){function t(t){var e=t||{};i.call(this,{attributions:e.attributions,projection:e.projection,resolutions:e.resolutions}),this.crossOrigin_=void 0!==e.crossOrigin?e.crossOrigin:null,this.url_=e.url,this.imageLoadFunction_=void 0!==e.imageLoadFunction?e.imageLoadFunction:qx,this.params_=e.params||{},this.v13_=!0,this.updateV13_(),this.serverType_=e.serverType,this.hidpi_=void 0===e.hidpi||e.hidpi,this.image_=null,this.imageSize_=[0,0],this.renderedRevision_=0,this.ratio_=void 0!==e.ratio?e.ratio:1.5}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.getGetFeatureInfoUrl=function(t,e,i,r){if(void 0!==this.url_){var n=ne(i),o=this.getProjection();o&&o!==n&&(e=mx(o,n,t,e),t=de(t,n,o));var s=st(t,e,0,aS),a={SERVICE:"WMS",VERSION:iS,REQUEST:"GetFeatureInfo",FORMAT:"image/png",TRANSPARENT:!0,QUERY_LAYERS:this.params_.LAYERS};C(a,this.params_,r);var h=Math.floor((t[0]-s[0])/e),l=Math.floor((s[3]-t[1])/e);return a[this.v13_?"I":"X"]=h,a[this.v13_?"J":"Y"]=l,this.getRequestUrl_(s,aS,1,o||n,a)}},t.prototype.getParams=function(){return this.params_},t.prototype.getImageInternal=function(t,e,i,r){if(void 0===this.url_)return null;e=this.findNearestResolution(e),1==i||this.hidpi_&&void 0!==this.serverType_||(i=1);var n=e/i,o=ot(t),s=st(o,n,0,[Math.ceil(ct(t)/n),Math.ceil(at(t)/n)]),a=st(o,n,0,[Math.ceil(this.ratio_*ct(t)/n),Math.ceil(this.ratio_*at(t)/n)]),h=this.image_;if(h&&this.renderedRevision_==this.getRevision()&&h.getResolution()==e&&h.getPixelRatio()==i&&Q(h.getExtent(),s))return h;var l={SERVICE:"WMS",VERSION:iS,REQUEST:"GetMap",FORMAT:"image/png",TRANSPARENT:!0};C(l,this.params_),this.imageSize_[0]=Math.round(ct(a)/n),this.imageSize_[1]=Math.round(at(a)/n);var u=this.getRequestUrl_(a,this.imageSize_,i,r,l);return this.image_=new On(a,e,i,u,this.crossOrigin_,this.imageLoadFunction_),this.renderedRevision_=this.getRevision(),E(this.image_,w.CHANGE,this.handleImageChange,this),this.image_},t.prototype.getImageLoadFunction=function(){return this.imageLoadFunction_},t.prototype.getRequestUrl_=function(t,e,i,r,n){if(Z(void 0!==this.url_,9),n[this.v13_?"CRS":"SRS"]=r.getCode(),"STYLES"in this.params_||(n.STYLES=""),1!=i)switch(this.serverType_){case nS:var o=90*i+.5|0;"FORMAT_OPTIONS"in n?n.FORMAT_OPTIONS+=";dpi:"+o:n.FORMAT_OPTIONS="dpi:"+o;break;case oS:n.MAP_RESOLUTION=90*i;break;case rS:case sS:n.DPI=90*i;break;default:Z(!1,8)}n.WIDTH=e[0],n.HEIGHT=e[1];var s,a=r.getAxisOrientation();return s=this.v13_&&"ne"==a.substr(0,2)?[t[1],t[0],t[3],t[2]]:t,n.BBOX=s.join(","),Jx(this.url_,n)},t.prototype.getUrl=function(){return this.url_},t.prototype.setImageLoadFunction=function(t){this.image_=null,this.imageLoadFunction_=t,this.changed()},t.prototype.setUrl=function(t){t!=this.url_&&(this.url_=t,this.image_=null,this.changed())},t.prototype.updateParams=function(t){C(this.params_,t),this.updateV13_(),this.image_=null,this.changed()},t.prototype.updateV13_=function(){var t=this.params_.VERSION||iS;this.v13_=0<=sn(t,"1.3")},t}(Zx),lS='© <a href="https://www.openstreetmap.org/copyright">OpenStreetMap</a> contributors.',uS=function(o){function t(t){var e,i=t||{};e=void 0!==i.attributions?i.attributions:[lS];var r=void 0!==i.crossOrigin?i.crossOrigin:"anonymous",n=void 0!==i.url?i.url:"https://{a-c}.tile.openstreetmap.org/{z}/{x}/{y}.png";o.call(this,{attributions:e,cacheSize:i.cacheSize,crossOrigin:r,opaque:void 0===i.opaque||i.opaque,maxZoom:void 0!==i.maxZoom?i.maxZoom:19,reprojectionErrorThreshold:i.reprojectionErrorThreshold,tileLoadFunction:i.tileLoadFunction,url:n,wrapX:i.wrapX})}return o&&(t.__proto__=o),(t.prototype=Object.create(o&&o.prototype)).constructor=t}(Yx),cS=!0;try{new ImageData(10,10)}catch(t){cS=!1}var pS=document.createElement("canvas").getContext("2d");var dS={newImageData:function(t,e,i){if(cS)return new ImageData(t,e,i);var r=pS.createImageData(e,i);return r.data.set(t),r}}.newImageData;function fS(x){var S=!0;try{new ImageData(10,10)}catch(t){S=!1}return function(t){var e,i,r,n,o,s=t.buffers,a=t.meta,h=t.imageOps,l=t.width,u=t.height,c=s.length,p=s[0].byteLength;if(h){var d=new Array(c);for(i=0;i<c;++i)d[i]=(r=new Uint8ClampedArray(s[i]),n=l,o=u,S?new ImageData(r,n,o):{data:r,width:n,height:o});e=x(d,a).data}else{e=new Uint8ClampedArray(p);var f=new Array(c),_=new Array(c);for(i=0;i<c;++i)f[i]=new Uint8ClampedArray(s[i]),_[i]=[0,0,0,0];for(var g=0;g<p;g+=4){for(var y=0;y<c;++y){var v=f[y];_[y][0]=v[g],_[y][1]=v[g+1],_[y][2]=v[g+2],_[y][3]=v[g+3]}var m=x(_,a);e[g]=m[0],e[g+1]=m[1],e[g+2]=m[2],e[g+3]=m[3]}}return e.buffer}}function _S(e,t){var i=Object.keys(e.lib||{}).map(function(t){return"var "+t+" = "+e.lib[t].toString()+";"}).concat(["var __minion__ = ("+fS.toString()+")(",e.operation.toString(),");",'self.addEventListener("message", function(event) {'," var buffer = __minion__(event.data);"," self.postMessage({buffer: buffer, meta: event.data.meta}, [buffer]);","});"]),r=new Blob(i,{type:"text/javascript"}),n=URL.createObjectURL(r),o=new Worker(n);return o.addEventListener("message",t),o}function gS(t){var e;this._imageOps=!!t.imageOps;var i,r,n,o=[];if(e=0===t.threads?0:this._imageOps?1:t.threads||1)for(var s=0;s<e;++s)o[s]=_S(t,this._onWorkerMessage.bind(this,s));else o[0]=(i=t,r=this._onWorkerMessage.bind(this,0),n=fS(i.operation),{postMessage:function(t){setTimeout(function(){r({data:{buffer:n(t),meta:t.meta}})},0)}});this._workers=o,this._queue=[],this._maxQueueLength=t.queue||1/0,this._running=0,this._dataLookup={},this._job=null}gS.prototype.process=function(t,e,i){this._enqueue({inputs:t,meta:e,callback:i}),this._dispatch()},gS.prototype.destroy=function(){for(var t in this)this[t]=null;this._destroyed=!0},gS.prototype._enqueue=function(t){for(this._queue.push(t);this._queue.length>this._maxQueueLength;)this._queue.shift().callback(null,null)},gS.prototype._dispatch=function(){if(0===this._running&&0<this._queue.length){var t=this._job=this._queue.shift(),e=t.inputs[0].width,i=t.inputs[0].height,r=t.inputs.map(function(t){return t.data.buffer}),n=this._workers.length;if(1===(this._running=n))this._workers[0].postMessage({buffers:r,meta:t.meta,imageOps:this._imageOps,width:e,height:i},r);else for(var o=t.inputs[0].data.length,s=4*Math.ceil(o/4/n),a=0;a<n;++a){for(var h=a*s,l=[],u=0,c=r.length;u<c;++u)l.push(r[a].slice(h,h+s));this._workers[a].postMessage({buffers:l,meta:t.meta,imageOps:this._imageOps,width:e,height:i},l)}}},gS.prototype._onWorkerMessage=function(t,e){this._destroyed||(this._dataLookup[t]=e.data,--this._running,0===this._running&&this._resolveJob())},gS.prototype._resolveJob=function(){var t,e,i=this._job,r=this._workers.length;if(1===r)t=new Uint8ClampedArray(this._dataLookup[0].buffer),e=this._dataLookup[0].meta;else{var n=i.inputs[0].data.length;t=new Uint8ClampedArray(n),e=new Array(n);for(var o=4*Math.ceil(n/4/r),s=0;s<r;++s){var a=this._dataLookup[s].buffer,h=s*o;t.set(new Uint8ClampedArray(a),h),e[s]=this._dataLookup[s].meta}}this._job=null,this._dataLookup={},i.callback(null,dS(t,i.inputs[0].width,i.inputs[0].height),e),this._dispatch()};var yS=gS,vS="beforeoperations",mS="afteroperations",xS="pixel",SS="image",CS=function(r){function t(t,e,i){r.call(this,t),this.extent=e.extent,this.resolution=e.viewState.resolution/e.pixelRatio,this.data=i}return r&&(t.__proto__=r),(t.prototype=Object.create(r&&r.prototype)).constructor=t}(m),ES=function(a){function t(t){a.call(this,{}),this.worker_=null,this.operationType_=void 0!==t.operationType?t.operationType:xS,this.threads_=void 0!==t.threads?t.threads:1,this.renderers_=function(t){for(var e=t.length,i=new Array(e),r=0;r<e;++r)i[r]=RS(t[r]);return i}(t.sources);for(var e=0,i=this.renderers_.length;e<i;++e)E(this.renderers_[e],w.CHANGE,this.changed,this);this.tileQueue_=new Jo(function(){return 1},this.changed.bind(this));for(var r=this.renderers_.map(function(t){return t.getLayer().getLayerState()}),n={},o=0,s=r.length;o<s;++o)n[Et(r[o].layer)]=r[o];this.requestedFrameState_,this.renderedImageCanvas_=null,this.renderedRevision_,this.frameState_={animate:!1,coordinateToPixelTransform:[1,0,0,1,0,0],extent:null,focus:null,index:0,layerStates:n,layerStatesArray:r,pixelRatio:1,pixelToCoordinateTransform:[1,0,0,1,0,0],postRenderFunctions:[],size:[0,0],skippedFeatureUids:{},tileQueue:this.tileQueue_,time:Date.now(),usedTiles:{},viewState:{rotation:0},viewHints:[],wantedTiles:{}},void 0!==t.operation&&this.setOperation(t.operation,t.lib)}return a&&(t.__proto__=a),((t.prototype=Object.create(a&&a.prototype)).constructor=t).prototype.setOperation=function(t,e){this.worker_=new yS({operation:t,imageOps:this.operationType_===SS,queue:1,lib:e,threads:this.threads_}),this.changed()},t.prototype.updateFrameState_=function(t,e,i){var r=C({},this.frameState_);r.viewState=C({},r.viewState);var n=ot(t);r.extent=t.slice(),r.focus=n,r.size[0]=Math.round(ct(t)/e),r.size[1]=Math.round(at(t)/e),r.time=Date.now(),r.animate=!1;var o=r.viewState;return o.center=n,o.projection=i,o.resolution=e,r},t.prototype.allSourcesReady_=function(){for(var t=!0,e=0,i=this.renderers_.length;e<i;++e)if(this.renderers_[e].getLayer().getSource().getState()!==ms){t=!1;break}return t},t.prototype.getImage=function(t,e,i,r){if(!this.allSourcesReady_())return null;var n=this.updateFrameState_(t,e,r);if(this.requestedFrameState_=n,this.renderedImageCanvas_){var o=this.renderedImageCanvas_.getResolution(),s=this.renderedImageCanvas_.getExtent();e===o&&$(t,s)||(this.renderedImageCanvas_=null)}return this.renderedImageCanvas_&&this.getRevision()===this.renderedRevision_||this.processSources_(),n.tileQueue.loadMoreTiles(16,16),n.animate&&requestAnimationFrame(this.changed.bind(this)),this.renderedImageCanvas_},t.prototype.processSources_=function(){for(var t=this.requestedFrameState_,e=this.renderers_.length,i=new Array(e),r=0;r<e;++r){var n=wS(this.renderers_[r],t,t.layerStatesArray[r]);if(!n)return;i[r]=n}var o={};this.dispatchEvent(new CS(vS,t,o)),this.worker_.process(i,o,this.onWorkerComplete_.bind(this,t))},t.prototype.onWorkerComplete_=function(t,e,i,r){if(!e&&i){var n=t.extent,o=t.viewState.resolution;if(o===this.requestedFrameState_.viewState.resolution&&$(n,this.requestedFrameState_.extent)){var s;if(this.renderedImageCanvas_)s=this.renderedImageCanvas_.getImage().getContext("2d");else s=De(Math.round(ct(n)/o),Math.round(at(n)/o)),this.renderedImageCanvas_=new bl(n,o,1,s.canvas);s.putImageData(i,0,0),this.changed(),this.renderedRevision_=this.getRevision(),this.dispatchEvent(new CS(mS,t,r))}}},t.prototype.getImageInternal=function(){return null},t}(Zx),TS=null;function wS(t,e,i){if(!t.prepareFrame(e,i))return null;var r=e.size[0],n=e.size[1];if(TS){var o=TS.canvas;o.width!==r||o.height!==n?TS=De(r,n):TS.clearRect(0,0,r,n)}else TS=De(r,n);return t.composeFrame(e,i,TS),TS.getImageData(0,0,r,n)}function RS(t){var e,i,r=null;return t instanceof Mx?(i=new sx({source:t}),r=new Kl(i)):t instanceof Zx?(e=new rx({source:t}),r=new zl(e)):t instanceof sx?r=new Kl(t):t instanceof Ls&&(t.getType()==oh.IMAGE||t.getType()==oh.VECTOR)&&(r=new zl(t)),r}var IS=['Map tiles by <a href="https://stamen.com/">Stamen Design</a>, under <a href="https://creativecommons.org/licenses/by/3.0/">CC BY 3.0</a>.',lS],LS={terrain:{extension:"jpg",opaque:!0},"terrain-background":{extension:"jpg",opaque:!0},"terrain-labels":{extension:"png",opaque:!1},"terrain-lines":{extension:"png",opaque:!1},"toner-background":{extension:"png",opaque:!0},toner:{extension:"png",opaque:!0},"toner-hybrid":{extension:"png",opaque:!1},"toner-labels":{extension:"png",opaque:!1},"toner-lines":{extension:"png",opaque:!1},"toner-lite":{extension:"png",opaque:!0},watercolor:{extension:"jpg",opaque:!0}},bS={terrain:{minZoom:4,maxZoom:18},toner:{minZoom:0,maxZoom:20},watercolor:{minZoom:1,maxZoom:16}},PS=function(s){function t(t){var e=t.layer.indexOf("-"),i=-1==e?t.layer:t.layer.slice(0,e),r=bS[i],n=LS[t.layer],o=void 0!==t.url?t.url:"https://stamen-tiles-{a-d}.a.ssl.fastly.net/"+t.layer+"/{z}/{x}/{y}."+n.extension;s.call(this,{attributions:IS,cacheSize:t.cacheSize,crossOrigin:"anonymous",maxZoom:null!=t.maxZoom?t.maxZoom:r.maxZoom,minZoom:null!=t.minZoom?t.minZoom:r.minZoom,opaque:n.opaque,reprojectionErrorThreshold:t.reprojectionErrorThreshold,tileLoadFunction:t.tileLoadFunction,url:o,wrapX:t.wrapX})}return s&&(t.__proto__=s),(t.prototype=Object.create(s&&s.prototype)).constructor=t}(Yx),FS=function(i){function t(t){var e=t||{};i.call(this,{attributions:e.attributions,cacheSize:e.cacheSize,crossOrigin:e.crossOrigin,projection:e.projection,reprojectionErrorThreshold:e.reprojectionErrorThreshold,tileGrid:e.tileGrid,tileLoadFunction:e.tileLoadFunction,url:e.url,urls:e.urls,wrapX:void 0===e.wrapX||e.wrapX,transition:e.transition}),this.params_=e.params||{},this.tmpExtent_=[1/0,1/0,-1/0,-1/0],this.setKey(this.getKeyForParams_())}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.getKeyForParams_=function(){var t=0,e=[];for(var i in this.params_)e[t++]=i+"-"+this.params_[i];return e.join("/")},t.prototype.getParams=function(){return this.params_},t.prototype.getRequestUrl_=function(t,e,i,r,n,o){var s=this.urls;if(s){var a,h=n.getCode().split(":").pop();if(o.SIZE=e[0]+","+e[1],o.BBOX=i.join(","),o.BBOXSR=h,o.IMAGESR=h,o.DPI=Math.round(o.DPI?o.DPI*r:90*r),1==s.length)a=s[0];else a=s[Ct(cx(t),s.length)];return Jx(a.replace(/MapServer\/?$/,"MapServer/export").replace(/ImageServer\/?$/,"ImageServer/exportImage"),o)}},t.prototype.getTilePixelRatio=function(t){return t},t.prototype.fixedTileUrlFunction=function(t,e,i){var r=this.getTileGrid();if(r||(r=this.getTileGridForProjection(i)),!(r.getResolutions().length<=t[0])){var n=r.getTileCoordExtent(t,this.tmpExtent_),o=ws(r.getTileSize(t[0]),this.tmpSize);1!=e&&(o=Ts(o,e,this.tmpSize));var s={F:"image",FORMAT:"PNG32",TRANSPARENT:!0};return C(s,this.params_),this.getRequestUrl_(t,o,n,e,i,s)}},t.prototype.updateParams=function(t){C(this.params_,t),this.setKey(this.getKeyForParams_())},t}(Dx),MS=function(r){function t(t,e,i){r.call(this,t,Gn),this.tileSize_=e,this.text_=i,this.canvas_=null}return r&&(t.__proto__=r),((t.prototype=Object.create(r&&r.prototype)).constructor=t).prototype.getImage=function(){if(this.canvas_)return this.canvas_;var t=this.tileSize_,e=De(t[0],t[1]);return e.strokeStyle="black",e.strokeRect(.5,.5,t[0]+.5,t[1]+.5),e.fillStyle="black",e.textAlign="center",e.textBaseline="middle",e.font="24px sans-serif",e.fillText(this.text_,t[0]/2,t[1]/2),this.canvas_=e.canvas,e.canvas},t.prototype.load=function(){},t}(zn),OS=function(e){function t(t){e.call(this,{opaque:!1,projection:t.projection,tileGrid:t.tileGrid,wrapX:void 0===t.wrapX||t.wrapX})}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.getTile=function(t,e,i){var r=lx(t,e,i);if(this.tileCache.containsKey(r))return this.tileCache.get(r);var n=ws(this.tileGrid.getTileSize(t)),o=[t,e,i],s=this.getTileCoordForTileUrlFunction(o),a=s?this.getTileCoordForTileUrlFunction(s).toString():"",h=new MS(o,n,a);return this.tileCache.set(r,h),h},t}(Mx),NS=function(i){function t(t){if(i.call(this,{attributions:t.attributions,cacheSize:t.cacheSize,crossOrigin:t.crossOrigin,projection:ne("EPSG:3857"),reprojectionErrorThreshold:t.reprojectionErrorThreshold,state:vs,tileLoadFunction:t.tileLoadFunction,wrapX:void 0===t.wrapX||t.wrapX,transition:t.transition}),this.tileJSON_=null,t.url)if(t.jsonp)yx(t.url,this.handleTileJSONResponse.bind(this),this.handleTileJSONError.bind(this));else{var e=new XMLHttpRequest;e.addEventListener("load",this.onXHRLoad_.bind(this)),e.addEventListener("error",this.onXHRError_.bind(this)),e.open("GET",t.url),e.send()}else t.tileJSON?this.handleTileJSONResponse(t.tileJSON):Z(!1,51)}return i&&(t.__proto__=i),((t.prototype=Object.create(i&&i.prototype)).constructor=t).prototype.onXHRLoad_=function(t){var e=t.target;if(!e.status||200<=e.status&&e.status<300){var i;try{i=JSON.parse(e.responseText)}catch(t){return void this.handleTileJSONError()}this.handleTileJSONResponse(i)}else this.handleTileJSONError()},t.prototype.onXHRError_=function(t){this.handleTileJSONError()},t.prototype.getTileJSON=function(){return this.tileJSON_},t.prototype.handleTileJSONResponse=function(e){var t,i=ne("EPSG:4326"),r=this.getProjection();if(void 0!==e.bounds){var n=ce(i,r);t=ft(e.bounds,n)}var o=e.minzoom||0,s=e.maxzoom||22,a=Lx({extent:Fx(r),maxZoom:s,minZoom:o});if(this.tileGrid=a,this.tileUrlFunction=dx(e.tiles,a),void 0!==e.attribution&&!this.getAttributions()){var h=void 0!==t?t:i.getExtent();this.setAttributions(function(t){return wt(h,t.extent)?[e.attribution]:null})}this.tileJSON_=e,this.setState(ms)},t.prototype.handleTileJSONError=function(){this.setState(xs)},t}(Dx),AS=function(n){function t(t){var e=t||{},i=e.params||{},r=!("TRANSPARENT"in i)||i.TRANSPARENT;n.call(this,{attributions:e.attributions,cacheSize:e.cacheSize,crossOrigin:e.crossOrigin,opaque:!r,projection:e.projection,reprojectionErrorThreshold:e.reprojectionErrorThreshold,tileClass:e.tileClass,tileGrid:e.tileGrid,tileLoadFunction:e.tileLoadFunction,url:e.url,urls:e.urls,wrapX:void 0===e.wrapX||e.wrapX,transition:e.transition}),this.gutter_=void 0!==e.gutter?e.gutter:0,this.params_=i,this.v13_=!0,this.serverType_=e.serverType,this.hidpi_=void 0===e.hidpi||e.hidpi,this.tmpExtent_=[1/0,1/0,-1/0,-1/0],this.updateV13_(),this.setKey(this.getKeyForParams_())}return n&&(t.__proto__=n),((t.prototype=Object.create(n&&n.prototype)).constructor=t).prototype.getGetFeatureInfoUrl=function(t,e,i,r){var n=ne(i),o=this.getProjection(),s=this.getTileGrid();s||(s=this.getTileGridForProjection(n));var a=s.getTileCoordForCoordAndResolution(t,e);if(!(s.getResolutions().length<=a[0])){var h=s.getResolution(a[0]),l=s.getTileCoordExtent(a,this.tmpExtent_),u=ws(s.getTileSize(a[0]),this.tmpSize),c=this.gutter_;0!==c&&(u=Es(u,c,this.tmpSize),l=G(l,h*c,l)),o&&o!==n&&(h=mx(o,n,t,h),l=fe(l,n,o),t=de(t,n,o));var p={SERVICE:"WMS",VERSION:iS,REQUEST:"GetFeatureInfo",FORMAT:"image/png",TRANSPARENT:!0,QUERY_LAYERS:this.params_.LAYERS};C(p,this.params_,r);var d=Math.floor((t[0]-l[0])/h),f=Math.floor((l[3]-t[1])/h);return p[this.v13_?"I":"X"]=d,p[this.v13_?"J":"Y"]=f,this.getRequestUrl_(a,u,l,1,o||n,p)}},t.prototype.getGutterInternal=function(){return this.gutter_},t.prototype.getParams=function(){return this.params_},t.prototype.getRequestUrl_=function(t,e,i,r,n,o){var s=this.urls;if(s){if(o.WIDTH=e[0],o.HEIGHT=e[1],o[this.v13_?"CRS":"SRS"]=n.getCode(),"STYLES"in this.params_||(o.STYLES=""),1!=r)switch(this.serverType_){case nS:var a=90*r+.5|0;"FORMAT_OPTIONS"in o?o.FORMAT_OPTIONS+=";dpi:"+a:o.FORMAT_OPTIONS="dpi:"+a;break;case oS:o.MAP_RESOLUTION=90*r;break;case rS:case sS:o.DPI=90*r;break;default:Z(!1,52)}var h,l,u=n.getAxisOrientation(),c=i;if(this.v13_&&"ne"==u.substr(0,2))h=i[0],c[0]=i[1],c[1]=h,h=i[2],c[2]=i[3],c[3]=h;if(o.BBOX=c.join(","),1==s.length)l=s[0];else l=s[Ct(cx(t),s.length)];return Jx(l,o)}},t.prototype.getTilePixelRatio=function(t){return this.hidpi_&&void 0!==this.serverType_?t:1},t.prototype.getKeyForParams_=function(){var t=0,e=[];for(var i in this.params_)e[t++]=i+"-"+this.params_[i];return e.join("/")},t.prototype.fixedTileUrlFunction=function(t,e,i){var r=this.getTileGrid();if(r||(r=this.getTileGridForProjection(i)),!(r.getResolutions().length<=t[0])){1==e||this.hidpi_&&void 0!==this.serverType_||(e=1);var n=r.getResolution(t[0]),o=r.getTileCoordExtent(t,this.tmpExtent_),s=ws(r.getTileSize(t[0]),this.tmpSize),a=this.gutter_;0!==a&&(s=Es(s,a,this.tmpSize),o=G(o,n*a,o)),1!=e&&(s=Ts(s,e,this.tmpSize));var h={SERVICE:"WMS",VERSION:iS,REQUEST:"GetMap",FORMAT:"image/png",TRANSPARENT:!0};return C(h,this.params_),this.getRequestUrl_(t,s,o,e,i,h)}},t.prototype.updateParams=function(t){C(this.params_,t),this.updateV13_(),this.setKey(this.getKeyForParams_())},t.prototype.updateV13_=function(){var t=this.params_.VERSION||iS;this.v13_=0<=sn(t,"1.3")},t}(Dx),GS=function(s){function t(t,e,i,r,n,o){s.call(this,t,e),this.src_=i,this.extent_=r,this.preemptive_=n,this.grid_=null,this.keys_=null,this.data_=null,this.jsonp_=o}return s&&(t.__proto__=s),(t.prototype=Object.create(s&&s.prototype)).constructor=t}(zn);GS.prototype.getImage=function(){return null},GS.prototype.getData=function(t){if(!this.grid_||!this.keys_)return null;var e=(t[0]-this.extent_[0])/(this.extent_[2]-this.extent_[0]),i=(t[1]-this.extent_[1])/(this.extent_[3]-this.extent_[1]),r=this.grid_[Math.floor((1-i)*this.grid_.length)];if("string"!=typeof r)return null;var n=r.charCodeAt(Math.floor(e*r.length));93<=n&&n--,35<=n&&n--;var o=null;if((n-=32)in this.keys_){var s=this.keys_[n];o=this.data_&&s in this.data_?this.data_[s]:s}return o},GS.prototype.forDataAtCoordinate=function(e,i,r,t){this.state==Nn&&!0===t?(p(this,w.CHANGE,function(t){i.call(r,this.getData(e))},this),this.loadInternal_()):!0===t?setTimeout(function(){i.call(r,this.getData(e))}.bind(this),0):i.call(r,this.getData(e))},GS.prototype.getKey=function(){return this.src_},GS.prototype.handleError_=function(){this.state=kn,this.changed()},GS.prototype.handleLoad_=function(t){this.grid_=t.grid,this.keys_=t.keys,this.data_=t.data,this.state=Dn,this.changed()},GS.prototype.loadInternal_=function(){if(this.state==Nn)if(this.state=An,this.jsonp_)yx(this.src_,this.handleLoad_.bind(this),this.handleError_.bind(this));else{var t=new XMLHttpRequest;t.addEventListener("load",this.onXHRLoad_.bind(this)),t.addEventListener("error",this.onXHRError_.bind(this)),t.open("GET",this.src_),t.send()}},GS.prototype.onXHRLoad_=function(t){var e=t.target;if(!e.status||200<=e.status&&e.status<300){var i;try{i=JSON.parse(e.responseText)}catch(t){return void this.handleError_()}this.handleLoad_(i)}else this.handleError_()},GS.prototype.onXHRError_=function(t){this.handleError_()},GS.prototype.load=function(){this.preemptive_&&this.loadInternal_()};var kS=function(i){function t(t){if(i.call(this,{projection:ne("EPSG:3857"),state:vs}),this.preemptive_=void 0===t.preemptive||t.preemptive,this.tileUrlFunction_=_x,this.template_=void 0,this.jsonp_=t.jsonp||!1,t.url)if(this.jsonp_)yx(t.url,this.handleTileJSONResponse.bind(this),this.handleTileJSONError.bind(this));else{var e=new XMLHttpRequest;e.addEventListener("load",this.onXHRLoad_.bind(this)),e.addEventListener("error",this.onXHRError_.bind(this)),e.open("GET",t.url),e.send()}else t.tileJSON?this.handleTileJSONResponse(t.tileJSON):Z(!1,51)}return i&&(t.__proto__=i),(t.prototype=Object.create(i&&i.prototype)).constructor=t}(Mx);kS.prototype.onXHRLoad_=function(t){var e=t.target;if(!e.status||200<=e.status&&e.status<300){var i;try{i=JSON.parse(e.responseText)}catch(t){return void this.handleTileJSONError()}this.handleTileJSONResponse(i)}else this.handleTileJSONError()},kS.prototype.onXHRError_=function(t){this.handleTileJSONError()},kS.prototype.getTemplate=function(){return this.template_},kS.prototype.forDataAtCoordinateAndResolution=function(t,e,i,r){if(this.tileGrid){var n=this.tileGrid.getTileCoordForCoordAndResolution(t,e);this.getTile(n[0],n[1],n[2],1,this.getProjection()).forDataAtCoordinate(t,i,null,r)}else!0===r?setTimeout(function(){i(null)},0):i(null)},kS.prototype.handleTileJSONError=function(){this.setState(xs)},kS.prototype.handleTileJSONResponse=function(e){var t,i=ne("EPSG:4326"),r=this.getProjection();if(void 0!==e.bounds){var n=ce(i,r);t=ft(e.bounds,n)}var o=e.minzoom||0,s=e.maxzoom||22,a=Lx({extent:Fx(r),maxZoom:s,minZoom:o});this.tileGrid=a,this.template_=e.template;var h=e.grids;if(h){if(this.tileUrlFunction_=dx(h,a),void 0!==e.attribution){var l=void 0!==t?t:i.getExtent();this.setAttributions(function(t){return wt(l,t.extent)?[e.attribution]:null})}this.setState(ms)}else this.setState(xs)},kS.prototype.getTile=function(t,e,i,r,n){var o=lx(t,e,i);if(this.tileCache.containsKey(o))return this.tileCache.get(o);var s=[t,e,i],a=this.getTileCoordForTileUrlFunction(s,n),h=this.tileUrlFunction_(a,r,n),l=new GS(s,void 0!==h?Nn:Dn,void 0!==h?h:"",this.tileGrid.getTileCoordExtent(s),this.preemptive_,this.jsonp_);return this.tileCache.set(o,l),l},kS.prototype.useTile=function(t,e,i){var r=lx(t,e,i);this.tileCache.containsKey(r)&&this.tileCache.get(r)};var DS=function(S){function C(t,e,i,s,a,r,h,l,n,u,c,p,d,f,o){if(S.call(this,t,e,{transition:0}),this.context_={},this.loader_,this.replayState_={},this.sourceTiles_=u,this.tileKeys=[],this.extent=null,this.sourceRevision_=i,this.wrappedTileCoord=r,this.loadListenerKeys_=[],this.sourceTileListenerKeys_=[],r){var _=this.extent=n.getTileCoordExtent(r),g=n.getResolution(o),y=l.getZForResolution(g),v=o!=t[0],m=0;if(l.forEachTileCoord(_,y,function(t){var e=ht(_,l.getTileCoordExtent(t)),i=l.getExtent();if(i&&(e=ht(e,i,e)),.5<=ct(e)/g&&.5<=at(e)/g){++m;var r=t.toString(),n=u[r];if(!n&&!v){var o=h(t,c,p);n=u[r]=new d(t,null==o?Dn:Nn,null==o?"":o,s,a),this.sourceTileListenerKeys_.push(E(n,w.CHANGE,f))}!n||v&&n.getState()!=Gn||(n.consumers++,this.tileKeys.push(r))}}.bind(this)),v&&m==this.tileKeys.length&&this.finishLoading_(),o<=t[0]&&this.state!=Gn)for(;o>n.getMinZoom();){var x=new C(t,e,i,s,a,r,h,l,n,u,c,p,d,L,--o);if(x.state==Gn){this.interimTile=x;break}}}}return S&&(C.__proto__=S),((C.prototype=Object.create(S&&S.prototype)).constructor=C).prototype.disposeInternal=function(){this.state=jn,this.changed(),this.interimTile&&this.interimTile.dispose();for(var t=0,e=this.tileKeys.length;t<e;++t){var i=this.tileKeys[t],r=this.getTile(i);r.consumers--,0==r.consumers&&(delete this.sourceTiles_[i],r.dispose())}this.tileKeys.length=0,this.sourceTiles_=null,this.loadListenerKeys_.forEach(g),this.loadListenerKeys_.length=0,this.sourceTileListenerKeys_.forEach(g),this.sourceTileListenerKeys_.length=0,S.prototype.disposeInternal.call(this)},C.prototype.getContext=function(t){var e=Et(t).toString();return e in this.context_||(this.context_[e]=De()),this.context_[e]},C.prototype.getImage=function(t){return-1==this.getReplayState(t).renderedTileRevision?null:this.getContext(t).canvas},C.prototype.getReplayState=function(t){var e=Et(t).toString();return e in this.replayState_||(this.replayState_[e]={dirty:!1,renderedRenderOrder:null,renderedRevision:-1,renderedTileRevision:-1}),this.replayState_[e]},C.prototype.getKey=function(){return this.tileKeys.join("/")+"-"+this.sourceRevision_},C.prototype.getTile=function(t){return this.sourceTiles_[t]},C.prototype.load=function(){var n=0,o={};this.state==Nn&&this.setState(An),this.state==An&&this.tileKeys.forEach(function(t){var r=this.getTile(t);if(r.state==Nn&&(r.setLoader(this.loader_),r.load()),r.state==An){var e=E(r,w.CHANGE,function(t){var e=r.getState();if(e==Gn||e==kn){var i=Et(r);e==kn?o[i]=!0:(--n,delete o[i]),n-Object.keys(o).length==0&&this.finishLoading_()}}.bind(this));this.loadListenerKeys_.push(e),++n}}.bind(this)),n-Object.keys(o).length==0&&setTimeout(this.finishLoading_.bind(this),0)},C.prototype.finishLoading_=function(){for(var t=this.tileKeys.length,e=0,i=t-1;0<=i;--i){var r=this.getTile(this.tileKeys[i]).getState();r!=Gn&&--t,r==Dn&&++e}t==this.tileKeys.length?(this.loadListenerKeys_.forEach(g),this.loadListenerKeys_.length=0,this.setState(Gn)):this.setState(e==this.tileKeys.length?Dn:kn)},C}(zn);function jS(t,e){var i=ch(e,t.getFormat(),t.onLoad.bind(t),t.onError.bind(t));t.setLoader(i)}var US=function(n){function t(t){var e=t.projection||"EPSG:3857",i=t.extent||Fx(e),r=t.tileGrid||Lx({extent:i,maxZoom:t.maxZoom||22,minZoom:t.minZoom,tileSize:t.tileSize||512});n.call(this,{attributions:t.attributions,cacheSize:void 0!==t.cacheSize?t.cacheSize:128,extent:i,opaque:!1,projection:e,state:t.state,tileGrid:r,tileLoadFunction:t.tileLoadFunction?t.tileLoadFunction:jS,tileUrlFunction:t.tileUrlFunction,url:t.url,urls:t.urls,wrapX:void 0===t.wrapX||t.wrapX,transition:t.transition}),this.format_=t.format?t.format:null,this.sourceTiles_={},this.overlaps_=null==t.overlaps||t.overlaps,this.tileClass=t.tileClass?t.tileClass:nc,this.tileGrids_={}}return n&&(t.__proto__=n),(t.prototype=Object.create(n&&n.prototype)).constructor=t}(kx);US.prototype.getOverlaps=function(){return this.overlaps_},US.prototype.clear=function(){this.tileCache.clear(),this.sourceTiles_={}},US.prototype.getTile=function(t,e,i,r,n){var o=lx(t,e,i);if(this.tileCache.containsKey(o))return this.tileCache.get(o);var s=[t,e,i],a=this.getTileCoordForTileUrlFunction(s,n),h=new DS(s,null!==a?Nn:Dn,this.getRevision(),this.format_,this.tileLoadFunction,a,this.tileUrlFunction,this.tileGrid,this.getTileGridForProjection(n),this.sourceTiles_,r,n,this.tileClass,this.handleTileChange.bind(this),s[0]);return this.tileCache.set(o,h),h},US.prototype.getTileGridForProjection=function(t){var e=t.getCode(),i=this.tileGrids_[e];if(!i){var r=this.tileGrid;i=this.tileGrids_[e]=Px(t,void 0,r?r.getTileSize(r.getMinZoom()):void 0)}return i},US.prototype.getTilePixelRatio=function(t){return t},US.prototype.getTilePixelSize=function(t,e,i){var r=ws(this.getTileGridForProjection(i).getTileSize(t),this.tmpSize);return[Math.round(r[0]*e),Math.round(r[1]*e)]};var YS={KVP:"KVP",REST:"REST"},BS=function(e){function t(t){e.call(this,{extent:t.extent,origin:t.origin,origins:t.origins,resolutions:t.resolutions,tileSize:t.tileSize,tileSizes:t.tileSizes,sizes:t.sizes}),this.matrixIds_=t.matrixIds}return e&&(t.__proto__=e),((t.prototype=Object.create(e&&e.prototype)).constructor=t).prototype.getMatrixId=function(t){return this.matrixIds_[t]},t.prototype.getMatrixIds=function(){return this.matrixIds_},t}(wx);function XS(n,t,e){var o=[],s=[],a=[],h=[],l=[],u=void 0!==e?e:[],c="TileMatrix",p="Identifier",d="ScaleDenominator",f="TopLeftCorner",i=n.SupportedCRS,r=ne(i.replace(/urn:ogc:def:crs:(\w+):(.*:)?(\w+)$/,"$1:$3"))||ne(i),_=r.getMetersPerUnit(),g="ne"==r.getAxisOrientation().substr(0,2);return n[c].sort(function(t,e){return e[d]-t[d]}),n[c].forEach(function(e){if(!(0<u.length)||dr(u,function(t){return e[p]==t[c]||-1===e[p].indexOf(":")&&n[p]+":"+e[p]===t[c]})){s.push(e[p]);var t=28e-5*e[d]/_,i=e.TileWidth,r=e.TileHeight;g?a.push([e[f][1],e[f][0]]):a.push(e[f]),o.push(t),h.push(i==r?i:[i,r]),l.push([e.MatrixWidth,-e.MatrixHeight])}}),new BS({extent:t,origins:a,resolutions:o,matrixIds:s,tileSizes:h,sizes:l})}var zS=function(n){function t(t){var e=void 0!==t.requestEncoding?t.requestEncoding:YS.KVP,i=t.tileGrid,r=t.urls;void 0===r&&void 0!==t.url&&(r=gx(t.url)),n.call(this,{attributions:t.attributions,cacheSize:t.cacheSize,crossOrigin:t.crossOrigin,projection:t.projection,reprojectionErrorThreshold:t.reprojectionErrorThreshold,tileClass:t.tileClass,tileGrid:i,tileLoadFunction:t.tileLoadFunction,tilePixelRatio:t.tilePixelRatio,tileUrlFunction:_x,urls:r,wrapX:void 0!==t.wrapX&&t.wrapX,transition:t.transition}),this.version_=void 0!==t.version?t.version:"1.0.0",this.format_=void 0!==t.format?t.format:"image/jpeg",this.dimensions_=void 0!==t.dimensions?t.dimensions:{},this.layer_=t.layer,this.matrixSet_=t.matrixSet,this.style_=t.style,this.requestEncoding_=e,this.setKey(this.getKeyForDimensions_()),r&&0<r.length&&(this.tileUrlFunction=fx(r.map(VS.bind(this))))}return n&&(t.__proto__=n),(t.prototype=Object.create(n&&n.prototype)).constructor=t}(Dx);function VS(o){var s=this.requestEncoding_,i={layer:this.layer_,style:this.style_,tilematrixset:this.matrixSet_};s==YS.KVP&&C(i,{Service:"WMTS",Request:"GetTile",Version:this.version_,Format:this.format_}),o=s==YS.KVP?Jx(o,i):o.replace(/\{(\w+?)\}/g,function(t,e){return e.toLowerCase()in i?i[e.toLowerCase()]:t});var a=this.tileGrid;return function(t,e,i){if(t){var r={TileMatrix:a.getMatrixId(t[0]),TileCol:t[1],TileRow:-t[2]-1};C(r,this.dimensions_);var n=o;return n=s==YS.KVP?Jx(n,r):n.replace(/\{(\w+?)\}/g,function(t,e){return r[e]})}}}zS.prototype.setUrls=function(t){var e=(this.urls=t).join("\n");this.setTileUrlFunction(this.fixedTileUrlFunction?this.fixedTileUrlFunction.bind(this):fx(t.map(VS.bind(this))),e)},zS.prototype.getDimensions=function(){return this.dimensions_},zS.prototype.getFormat=function(){return this.format_},zS.prototype.getLayer=function(){return this.layer_},zS.prototype.getMatrixSet=function(){return this.matrixSet_},zS.prototype.getRequestEncoding=function(){return this.requestEncoding_},zS.prototype.getStyle=function(){return this.style_},zS.prototype.getVersion=function(){return this.version_},zS.prototype.getKeyForDimensions_=function(){var t=0,e=[];for(var i in this.dimensions_)e[t++]=i+"-"+this.dimensions_[i];return e.join("/")},zS.prototype.updateDimensions=function(t){C(this.dimensions_,t),this.setKey(this.getKeyForDimensions_())};var WS="default",KS="truncated",HS=function(a){function t(t,e,i,r,n,o,s){a.call(this,e,i,r,n,o,s),this.zoomifyImage_=null,this.tileSize_=ws(t.getTileSize(e[0]))}return a&&(t.__proto__=a),(t.prototype=Object.create(a&&a.prototype)).constructor=t}(Vn);HS.prototype.getImage=function(){if(this.zoomifyImage_)return this.zoomifyImage_;var t=Vn.prototype.getImage.call(this);if(this.state==Gn){var e=this.tileSize_;if(t.width==e[0]&&t.height==e[1])return this.zoomifyImage_=t;var i=De(e[0],e[1]);return i.drawImage(t,0,0),this.zoomifyImage_=i.canvas,i.canvas}return t};var ZS=function(x){function t(t){var e=t||{},i=e.size,r=void 0!==e.tierSizeCalculation?e.tierSizeCalculation:WS,n=i[0],o=i[1],s=e.extent||[0,-i[1],i[0],0],u=[],a=e.tileSize||$o,h=a;switch(r){case WS:for(;h<n||h<o;)u.push([Math.ceil(n/h),Math.ceil(o/h)]),h+=h;break;case KS:for(var l=n,c=o;h<l||h<c;)u.push([Math.ceil(l/h),Math.ceil(c/h)]),l>>=1,c>>=1;break;default:Z(!1,53)}u.push([1,1]),u.reverse();for(var p=[1],d=[0],f=1,_=u.length;f<_;f++)p.push(1<<f),d.push(u[f-1][0]*u[f-1][1]+d[f-1]);p.reverse();var g=new wx({tileSize:a,extent:s,origin:lt(s),resolutions:p}),y=e.url;y&&-1==y.indexOf("{TileGroup}")&&-1==y.indexOf("{tileIndex}")&&(y+="{TileGroup}/{z}-{x}-{y}.jpg");var v=fx(gx(y).map(function(l){return function(t,e,i){if(t){var r=t[0],n=t[1],o=-t[2]-1,s=n+o*u[r][0],a=g.getTileSize(r),h={z:r,x:n,y:o,tileIndex:s,TileGroup:"TileGroup"+((s+d[r])/a|0)};return l.replace(/\{(\w+?)\}/g,function(t,e){return h[e]})}}})),m=HS.bind(null,g);x.call(this,{attributions:e.attributions,cacheSize:e.cacheSize,crossOrigin:e.crossOrigin,projection:e.projection,reprojectionErrorThreshold:e.reprojectionErrorThreshold,tileClass:m,tileGrid:g,tileUrlFunction:v,transition:e.transition})}return x&&(t.__proto__=x),(t.prototype=Object.create(x&&x.prototype)).constructor=t}(Dx);var qS=window.ol={};qS.color={},qS.colorlike={},qS.control={},qS.coordinate={},qS.easing={},qS.events={},qS.events.condition={},qS.extent={},qS.featureloader={},qS.format={},qS.format.filter={},qS.geom={},qS.has={},qS.interaction={},qS.layer={},qS.loadingstrategy={},qS.proj={},qS.proj.Units={},qS.proj.proj4={},qS.render={},qS.render.canvas={},qS.renderer={},qS.renderer.canvas={},qS.renderer.webgl={},qS.size={},qS.source={},qS.sphere={},qS.style={},qS.style.IconImageCache={},qS.tilegrid={},qS.xml={},qS.Collection=M,qS.Feature=Ji,qS.Geolocation=nn,qS.Graticule=Fn,qS.Kinetic=Kn,qS.Map=Yu,qS.Object=R,qS.Observable=S,qS.Observable.unByKey=function(t){if(Array.isArray(t))for(var e=0,i=t.length;e<i;++e)g(t[e]);else g(t)},qS.Overlay=ic,qS.PluggableMap=Rs,qS.View=as,qS.WebGLMap=Ap,qS.color.asArray=Ne,qS.color.asString=Pe,qS.colorlike.asColorLike=ke,qS.control.Attribution=Ps,qS.control.Attribution.render=Fs,qS.control.Control=Is,qS.control.FullScreen=sc,qS.control.MousePosition=Dp,qS.control.MousePosition.render=jp,qS.control.OverviewMap=uc,qS.control.OverviewMap.render=cc,qS.control.Rotate=Ms,qS.control.Rotate.render=Os,qS.control.ScaleLine=mc,qS.control.ScaleLine.render=xc,qS.control.Zoom=Ns,qS.control.ZoomSlider=Ec,qS.control.ZoomSlider.render=Tc,qS.control.ZoomToExtent=wc,qS.control.defaults=As,qS.coordinate.add=an,qS.coordinate.createStringXY=function(e){return function(t){return yn(t,e)}},qS.coordinate.format=un,qS.coordinate.rotate=pn,qS.coordinate.toStringHDMS=function(t,e){return t?ln("NS",t[1],e)+" "+ln("EW",t[0],e):""},qS.coordinate.toStringXY=yn,qS.easing.easeIn=Un,qS.easing.easeOut=Yn,qS.easing.inAndOut=Bn,qS.easing.linear=Xn,qS.easing.upAndDown=function(t){return t<.5?Bn(2*t):1-Bn(2*(t-.5))},qS.events.condition.altKeyOnly=Vs,qS.events.condition.altShiftKeysOnly=Ws,qS.events.condition.always=Ks,qS.events.condition.click=function(t){return t.type==qn.CLICK},qS.events.condition.doubleClick=function(t){return t.type==qn.DBLCLICK},qS.events.condition.focus=function(t){return t.target.getTargetElement()===document.activeElement},qS.events.condition.mouseOnly=ea,qS.events.condition.never=Zs,qS.events.condition.noModifierKeys=Qs,qS.events.condition.platformModifierKeyOnly=function(t){var e=t.originalEvent;return!e.altKey&&(si?e.metaKey:e.ctrlKey)&&!e.shiftKey},qS.events.condition.pointerMove=qs,qS.events.condition.primaryAction=ia,qS.events.condition.shiftKeyOnly=$s,qS.events.condition.singleClick=Js,qS.events.condition.targetNotEditable=ta,qS.extent.applyTransform=ft,qS.extent.boundingExtent=A,qS.extent.buffer=G,qS.extent.containsCoordinate=j,qS.extent.containsExtent=Q,qS.extent.containsXY=U,qS.extent.createEmpty=B,qS.extent.equals=$,qS.extent.extend=H,qS.extent.getArea=it,qS.extent.getBottomLeft=rt,qS.extent.getBottomRight=nt,qS.extent.getCenter=ot,qS.extent.getHeight=at,qS.extent.getIntersection=ht,qS.extent.getSize=function(t){return[t[2]-t[0],t[3]-t[1]]},qS.extent.getTopLeft=lt,qS.extent.getTopRight=ut,qS.extent.getWidth=ct,qS.extent.intersects=wt,qS.extent.isEmpty=pt,qS.featureloader.xhr=ph,qS.format.EsriJSON=Wp,qS.format.Feature=Up,qS.format.GML=Dd,qS.format.GML2=Yd,qS.format.GML3=kd,qS.format.GPX=Kd,qS.format.GeoJSON=wf,qS.format.IGC=jf,qS.format.KML=f_,qS.format.MVT=uy,qS.format.OSMXML=vy,qS.format.Polyline=Cy,qS.format.Polyline.decodeDeltas=Ty,qS.format.Polyline.decodeFloats=Ry,qS.format.Polyline.encodeDeltas=Ey,qS.format.Polyline.encodeFloats=wy,qS.format.TopoJSON=Ly,qS.format.WFS=_v,qS.format.WFS.writeFilter=function(t){var e=$p(pv,"Filter");return Sv(e,t,[]),e},qS.format.WKT=Bv,qS.format.WMSCapabilities=tm,qS.format.WMSGetFeatureInfo=xm,qS.format.WMTSCapabilities=Um,qS.format.filter.Bbox=Dy,qS.format.filter.Contains=Uy,qS.format.filter.During=By,qS.format.filter.EqualTo=zy,qS.format.filter.GreaterThan=Vy,qS.format.filter.GreaterThanOrEqualTo=Wy,qS.format.filter.Intersects=Ky,qS.format.filter.IsBetween=Hy,qS.format.filter.IsLike=Zy,qS.format.filter.IsNull=qy,qS.format.filter.LessThan=Jy,qS.format.filter.LessThanOrEqualTo=Qy,qS.format.filter.Not=$y,qS.format.filter.NotEqualTo=tv,qS.format.filter.Or=ev,qS.format.filter.Within=iv,qS.format.filter.and=rv,qS.format.filter.bbox=nv,qS.format.filter.between=function(t,e,i){return new Hy(t,e,i)},qS.format.filter.contains=function(t,e,i){return new Uy(t,e,i)},qS.format.filter.during=function(t,e,i){return new By(t,e,i)},qS.format.filter.equalTo=function(t,e,i){return new zy(t,e,i)},qS.format.filter.greaterThan=function(t,e){return new Vy(t,e)},qS.format.filter.greaterThanOrEqualTo=function(t,e){return new Wy(t,e)},qS.format.filter.intersects=function(t,e,i){return new Ky(t,e,i)},qS.format.filter.isNull=function(t){return new qy(t)},qS.format.filter.lessThan=function(t,e){return new Jy(t,e)},qS.format.filter.lessThanOrEqualTo=function(t,e){return new Qy(t,e)},qS.format.filter.like=function(t,e,i,r,n,o){return new Zy(t,e,i,r,n,o)},qS.format.filter.not=function(t){return new $y(t)},qS.format.filter.notEqualTo=function(t,e,i){return new tv(t,e,i)},qS.format.filter.or=function(t){var e=[null].concat(Array.prototype.slice.call(arguments));return new(Function.prototype.bind.apply(ev,e))},qS.format.filter.within=function(t,e,i){return new iv(t,e,i)},qS.geom.Circle=th,qS.geom.Geometry=Ie,qS.geom.GeometryCollection=Ef,qS.geom.LineString=Sn,qS.geom.LinearRing=kr,qS.geom.MultiLineString=eh,qS.geom.MultiPoint=ih,qS.geom.MultiPolygon=nh,qS.geom.Point=Dr,qS.geom.Polygon=Qr,qS.geom.Polygon.circular=$r,qS.geom.Polygon.fromCircle=en,qS.geom.Polygon.fromExtent=tn,qS.geom.SimpleGeometry=vr,qS.has.DEVICE_PIXEL_RATIO=ai,qS.has.GEOLOCATION=li,qS.has.TOUCH=ui,qS.inherits=function(t,e){t.prototype=Object.create(e.prototype),t.prototype.constructor=t},qS.interaction.DoubleClickZoom=Xs,qS.interaction.DragAndDrop=Ka,qS.interaction.DragBox=Ca,qS.interaction.DragPan=ca,qS.interaction.DragRotate=_a,qS.interaction.DragRotateAndZoom=qa,qS.interaction.DragZoom=Ia,qS.interaction.Draw=Xh,qS.interaction.Draw.createBox=function(){return function(t,e){var i=A(t),r=[[rt(i),nt(i),ut(i),lt(i),rt(i)]],n=e;return n?n.setCoordinates(r):n=new Qr(r),n}},qS.interaction.Draw.createRegularPolygon=function(s,a){return function(t,e){var i=t[0],r=t[1],n=Math.sqrt(fn(i,r)),o=e||en(new th(i),s);return rn(o,i,n,a||Math.atan((r[1]-i[1])/(r[0]-i[0]))),o}},qS.interaction.Draw.handleEvent=zh,qS.interaction.Extent=Zh,qS.interaction.Interaction=ks,qS.interaction.KeyboardPan=Pa,qS.interaction.KeyboardZoom=Ma,qS.interaction.Modify=sl,qS.interaction.MouseWheelZoom=Aa,qS.interaction.PinchRotate=ka,qS.interaction.PinchZoom=Ya,qS.interaction.Pointer=aa,qS.interaction.Pointer.handleEvent=la,qS.interaction.Select=gl,qS.interaction.Snap=vl,qS.interaction.Translate=El,qS.interaction.defaults=Ll,qS.layer.Base=gs,qS.layer.Group=Cs,qS.layer.Heatmap=ix,qS.layer.Image=rx,qS.layer.Tile=sx,qS.layer.Vector=lh,qS.layer.VectorTile=ax,qS.loadingstrategy.all=dh,qS.loadingstrategy.bbox=function(t,e){return[t]},qS.loadingstrategy.tile=function(s){return function(t,e){var i=s.getZForResolution(e),r=s.getTileRangeForExtentAndZ(t,i),n=[],o=[i,0,0];for(o[1]=r.minX;o[1]<=r.maxX;++o[1])for(o[2]=r.minY;o[2]<=r.maxY;++o[2])n.push(s.getTileCoordExtent(o));return n}},qS.proj.Projection=At,qS.proj.Units.METERS_PER_UNIT=Nt,qS.proj.addCoordinateTransforms=le,qS.proj.addEquivalentProjections=se,qS.proj.addProjection=re,qS.proj.equivalent=ue,qS.proj.fromLonLat=function(t,e){return de(t,"EPSG:4326",void 0!==e?e:"EPSG:3857")},qS.proj.get=ne,qS.proj.getPointResolution=oe,qS.proj.getTransform=pe,qS.proj.proj4.register=function(t){var e,i,r=Object.keys(t.defs),n=r.length;for(e=0;e<n;++e){var o=r[e];if(!ne(o)){var s=t.defs(o);re(new At({code:o,axisOrientation:s.axis,metersPerUnit:s.to_meter,units:s.units}))}}for(e=0;e<n;++e){var a=r[e],h=ne(a);for(i=0;i<n;++i){var l=r[i],u=ne(l);if(!te(a,l))if(t.defs[a]===t.defs[l])se([h,u]);else{var c=t(a,l);le(h,u,c.forward,c.inverse)}}}},qS.proj.toLonLat=function(t,e){var i=de(t,void 0!==e?e:"EPSG:3857","EPSG:4326"),r=i[0];return(r<-180||180<r)&&(i[0]=Ct(r+180,360)-180),i},qS.proj.transform=de,qS.proj.transformExtent=fe,qS.render.VectorContext=Fl,qS.render.canvas.labelCache=Li,qS.render.toContext=function(t,e){var i=t.canvas,r=e||{},n=r.pixelRatio||ai,o=r.size;o&&(i.width=o[0]*n,i.height=o[1]*n,i.style.width=o[0]+"px",i.style.height=o[1]+"px");var s=[0,0,i.width,i.height],a=Ce([1,0,0,1,0,0],n,n);return new Ml(t,n,s,a,0)},qS.renderer.canvas.ImageLayer=zl,qS.renderer.canvas.Map=Ul,qS.renderer.canvas.TileLayer=Kl,qS.renderer.canvas.VectorLayer=Ou,qS.renderer.canvas.VectorTileLayer=ju,qS.renderer.webgl.ImageLayer=Lp,qS.renderer.webgl.Map=bp,qS.renderer.webgl.TileLayer=Op,qS.renderer.webgl.VectorLayer=Np,qS.size.toSize=ws,qS.source.BingMaps=Ux,qS.source.CartoDB=Bx,qS.source.Cluster=Xx,qS.source.Image=Zx,qS.source.ImageArcGISRest=Qx,qS.source.ImageCanvas=$x,qS.source.ImageMapGuide=tS,qS.source.ImageStatic=eS,qS.source.ImageWMS=hS,qS.source.OSM=uS,qS.source.OSM.ATTRIBUTION=lS,qS.source.Raster=ES,qS.source.Source=fh,qS.source.Stamen=PS,qS.source.Tile=Mx,qS.source.TileArcGISRest=FS,qS.source.TileDebug=OS,qS.source.TileImage=Dx,qS.source.TileJSON=NS,qS.source.TileWMS=AS,qS.source.UTFGrid=kS,qS.source.Vector=Dh,qS.source.VectorTile=US,qS.source.WMTS=zS,qS.source.WMTS.optionsFromCapabilities=function(t,s){var e=dr(t.Contents.Layer,function(t,e,i){return t.Identifier==s.layer});if(null===e)return null;var i,a=t.Contents.TileMatrixSet;(i=1<e.TileMatrixSetLink.length?gr(e.TileMatrixSetLink,"projection"in s?function(e,t,i){var r=dr(a,function(t){return t.Identifier==e.TileMatrixSet}).SupportedCRS,n=ne(r.replace(/urn:ogc:def:crs:(\w+):(.*:)?(\w+)$/,"$1:$3"))||ne(r),o=ne(s.projection);return n&&o?ue(n,o):r==s.projection}:function(t,e,i){return t.TileMatrixSet==s.matrixSet}):0)<0&&(i=0);var r=e.TileMatrixSetLink[i].TileMatrixSet,n=e.TileMatrixSetLink[i].TileMatrixSetLimits,o=e.Format[0];"format"in s&&(o=s.format),(i=gr(e.Style,function(t,e,i){return"style"in s?t.Title==s.style:t.isDefault}))<0&&(i=0);var h=e.Style[i].Identifier,l={};"Dimension"in e&&e.Dimension.forEach(function(t,e,i){var r=t.Identifier,n=t.Default;void 0===n&&(n=t.Value[0]),l[r]=n});var u,c=dr(t.Contents.TileMatrixSet,function(t,e,i){return t.Identifier==r}),p=c.SupportedCRS;if(p&&(u=ne(p.replace(/urn:ogc:def:crs:(\w+):(.*:)?(\w+)$/,"$1:$3"))||ne(p)),"projection"in s){var d=ne(s.projection);d&&(u&&!ue(d,u)||(u=d))}var f,_,g=e.WGS84BoundingBox;if(void 0!==g){var y=ne("EPSG:4326").getExtent();_=g[0]==y[0]&&g[2]==y[2],f=fe(g,"EPSG:4326",u);var v=u.getExtent();v&&(Q(v,f)||(f=void 0))}var m=XS(c,f,n),x=[],S=s.requestEncoding;if(S=void 0!==S?S:"","OperationsMetadata"in t&&"GetTile"in t.OperationsMetadata)for(var C=t.OperationsMetadata.GetTile.DCP.HTTP.Get,E=0,T=C.length;E<T;++E)if(C[E].Constraint){var w=dr(C[E].Constraint,function(t){return"GetEncoding"==t.name}).AllowedValues.Value;if(""===S&&(S=w[0]),S!==YS.KVP)break;lr(w,YS.KVP)&&x.push(C[E].href)}else C[E].href&&(S=YS.KVP,x.push(C[E].href));return 0===x.length&&(S=YS.REST,e.ResourceURL.forEach(function(t){"tile"===t.resourceType&&(o=t.format,x.push(t.template))})),{urls:x,layer:s.layer,matrixSet:r,format:o,projection:u,requestEncoding:S,tileGrid:m,style:h,dimensions:l,wrapX:_,crossOrigin:s.crossOrigin}},qS.source.XYZ=Yx,qS.source.Zoomify=ZS,qS.sphere.getArea=function t(e,i){var r=i||{},n=r.radius||bt,o=r.projection||"EPSG:3857",s=e.getType();s!==Lt.GEOMETRY_COLLECTION&&(e=e.clone().transform(o,"EPSG:4326"));var a,h,l,u,c,p,d=0;switch(s){case Lt.POINT:case Lt.MULTI_POINT:case Lt.LINE_STRING:case Lt.MULTI_LINE_STRING:case Lt.LINEAR_RING:break;case Lt.POLYGON:for(a=e.getCoordinates(),d=Math.abs(Mt(a[0],n)),l=1,u=a.length;l<u;++l)d-=Math.abs(Mt(a[l],n));break;case Lt.MULTI_POLYGON:for(l=0,u=(a=e.getCoordinates()).length;l<u;++l)for(h=a[l],d+=Math.abs(Mt(h[0],n)),c=1,p=h.length;c<p;++c)d-=Math.abs(Mt(h[c],n));break;case Lt.GEOMETRY_COLLECTION:var f=e.getGeometries();for(l=0,u=f.length;l<u;++l)d+=t(f[l],i);break;default:throw new Error("Unsupported geometry type: "+s)}return d},qS.sphere.getDistance=Pt,qS.sphere.getLength=function t(e,i){var r=i||{},n=r.radius||bt,o=r.projection||"EPSG:3857",s=e.getType();s!==Lt.GEOMETRY_COLLECTION&&(e=e.clone().transform(o,"EPSG:4326"));var a,h,l,u,c,p,d=0;switch(s){case Lt.POINT:case Lt.MULTI_POINT:break;case Lt.LINE_STRING:case Lt.LINEAR_RING:d=Ft(a=e.getCoordinates(),n);break;case Lt.MULTI_LINE_STRING:case Lt.POLYGON:for(l=0,u=(a=e.getCoordinates()).length;l<u;++l)d+=Ft(a[l],n);break;case Lt.MULTI_POLYGON:for(l=0,u=(a=e.getCoordinates()).length;l<u;++l)for(c=0,p=(h=a[l]).length;c<p;++c)d+=Ft(h[c],n);break;case Lt.GEOMETRY_COLLECTION:var f=e.getGeometries();for(l=0,u=f.length;l<u;++l)d+=t(f[l],i);break;default:throw new Error("Unsupported geometry type: "+s)}return d},qS.style.AtlasManager=vp,qS.style.Circle=Xi,qS.style.Fill=zi,qS.style.Icon=Qf,qS.style.IconImageCache.shared=Al,qS.style.Image=Yi,qS.style.RegularShape=Bi,qS.style.Stroke=Vi,qS.style.Style=Wi,qS.style.Text=Ln,qS.tilegrid.TileGrid=wx,qS.tilegrid.WMTS=BS,qS.tilegrid.WMTS.createFromCapabilitiesMatrixSet=XS,qS.tilegrid.createXYZ=Lx,qS.xml.getAllTextContent=td,qS.xml.parse=rd}(); -//# sourceMappingURL=ol.js.map diff --git a/app/resources/views/map.blade.php b/app/resources/views/map.blade.php index 2ee8fba..5db8203 100644 --- a/app/resources/views/map.blade.php +++ b/app/resources/views/map.blade.php @@ -8,21 +8,23 @@ <title> Maps - MetaGer </title> - @if(isset($css)) - @foreach($css as $el) - <link href="{{$el}}" rel="stylesheet" type="text/css" /> - @endforeach + @if (isset($css)) + @foreach ($css as $el) + <link href="{{ $el }}" rel="stylesheet" type="text/css" /> + @endforeach @endif - <link rel="stylesheet" type="text/css" href="https://tileserver.metager.de/maplibre-gl.css" /> - <script src="https://tileserver.metager.de/maplibre-gl.js"></script> + <meta name="tileserverhost" content="{{ config('maps.tileserver.host') }}"> + <link rel="stylesheet" type="text/css" href="{{ config('maps.tileserver.host') }}/maplibre-gl.css" /> + <link rel="stylesheet" type="text/css" href="{{ config('maps.tileserver.host') }}/maplibre-gl-inspect.css" /> + <link rel="stylesheet" type="text/css" href="{{ config('maps.tileserver.host') }}/leaflet.css" /> + <script src="{{ config('maps.tileserver.host') }}/maplibre-gl.js"></script> + <script src="{{ config('maps.tileserver.host') }}/maplibre-gl-inspect.min.js"></script> + <script src="{{ config('maps.tileserver.host') }}/leaflet.js"></script> + <script src="{{ config('maps.tileserver.host') }}/leaflet-hash.js"></script> </head> <body> <main> - <figure id="hilfe" class="inactive"> - <iframe src=""></iframe> - <span class="close">✕</span> - </figure> @include('addons/search') @include('addons/navigation') @@ -49,7 +51,8 @@ if (gl && gl instanceof WebGLRenderingContext) { console.log("WebGL supported"); } else { - document.getElementsByTagName("body")[0].innerHTML = '<div style="text-align: center; margin-top: 40%; font-size: 18px;">WebGL is required to use MetaGer Maps. Please check your Browser Configuration.</div>'; + document.getElementsByTagName("body")[0].innerHTML = + '<div style="text-align: center; margin-top: 40%; font-size: 18px;">WebGL is required to use MetaGer Maps. Please check your Browser Configuration.</div>'; } canvas = undefined; </script> diff --git a/app/routes/web.php b/app/routes/web.php index 218b10b..8afa0e6 100644 --- a/app/routes/web.php +++ b/app/routes/web.php @@ -23,21 +23,21 @@ Route::get('/last-modified', function (Request $request) { //sleep(5); // List all Files in app, public, resources and routes - $appIterator = new RecursiveDirectoryIterator(app_path(), RecursiveDirectoryIterator::SKIP_DOTS); - $publicIterator = new RecursiveDirectoryIterator(public_path(), RecursiveDirectoryIterator::SKIP_DOTS); + $appIterator = new RecursiveDirectoryIterator(app_path(), RecursiveDirectoryIterator::SKIP_DOTS); + $publicIterator = new RecursiveDirectoryIterator(public_path(), RecursiveDirectoryIterator::SKIP_DOTS); $resourceIterator = new RecursiveDirectoryIterator(resource_path(), RecursiveDirectoryIterator::SKIP_DOTS); - $routesIterator = new RecursiveDirectoryIterator(base_path('routes'), RecursiveDirectoryIterator::SKIP_DOTS); - $iterator = new AppendIterator(); + $routesIterator = new RecursiveDirectoryIterator(base_path('routes'), RecursiveDirectoryIterator::SKIP_DOTS); + $iterator = new AppendIterator(); $iterator->append(new RecursiveIteratorIterator($appIterator)); $iterator->append(new RecursiveIteratorIterator($publicIterator)); $iterator->append(new RecursiveIteratorIterator($resourceIterator)); $iterator->append(new RecursiveIteratorIterator($routesIterator)); - $files = []; + $files = []; $maxTime = 0; - foreach ($iterator as $fileInfo) { + foreach($iterator as $fileInfo) { $mtime = filemtime($fileInfo->getPathname()); - if ($maxTime < $mtime) { + if($maxTime < $mtime) { $maxTime = $mtime; } $files[] = $mtime; @@ -51,25 +51,25 @@ Route::get('files/list', function (Request $request) { $imageIterator = new RecursiveDirectoryIterator(public_path('img'), RecursiveDirectoryIterator::SKIP_DOTS); - $jsIterator = new RecursiveDirectoryIterator(public_path('js'), RecursiveDirectoryIterator::SKIP_DOTS); - $cssIterator = new RecursiveDirectoryIterator(public_path('css'), RecursiveDirectoryIterator::SKIP_DOTS); + $jsIterator = new RecursiveDirectoryIterator(public_path('js'), RecursiveDirectoryIterator::SKIP_DOTS); + $cssIterator = new RecursiveDirectoryIterator(public_path('css'), RecursiveDirectoryIterator::SKIP_DOTS); $fontsIterator = new RecursiveDirectoryIterator(public_path('fonts'), RecursiveDirectoryIterator::SKIP_DOTS); - $iterator = new AppendIterator(); + $iterator = new AppendIterator(); $iterator->append(new RecursiveIteratorIterator($imageIterator)); $iterator->append(new RecursiveIteratorIterator($jsIterator)); $iterator->append(new RecursiveIteratorIterator($cssIterator)); $iterator->append(new RecursiveIteratorIterator($fontsIterator)); - $files = []; + $files = []; $delimiter = "MetaGerMaps/public"; - foreach ($iterator as $file) { - $filePath = $file->getPathname(); - $fileHash = hash_file('sha256', $filePath); - $pathname = substr($filePath, stripos($filePath, $delimiter) + strlen($delimiter)); + foreach($iterator as $file) { + $filePath = $file->getPathname(); + $fileHash = hash_file('sha256', $filePath); + $pathname = substr($filePath, stripos($filePath, $delimiter) + strlen($delimiter)); $files[$pathname] = $fileHash; } $files["/favicon.ico"] = hash_file('sha256', public_path("favicon.ico")); - $files["/"] = hash_file('sha256', resource_path('views/map.blade.php')); + $files["/"] = hash_file('sha256', resource_path('views/map.blade.php')); return Response::make(json_encode(["offline-data" => $files]), 200) ->header("Content-Type", "application/json"); @@ -85,15 +85,15 @@ Route::get('tile_cache/{z}/{x}/{y}.png', function ($z, $x, $y) { $socket = socket_create(AF_INET, SOCK_STREAM, SOL_TCP); - $fp = stream_socket_client("tcp://" . config("tileserver.TILESERVER_HOST") . ":" . config("tileserver.TILESERVER_PORT") . "/" . getmypid(), $errno, $errstr, 30); + $fp = stream_socket_client("tcp://".config("tileserver.TILESERVER_HOST").":".config("tileserver.TILESERVER_PORT")."/".getmypid(), $errno, $errstr, 30); #socket_connect($socket, env("TILESERVER_HOST") . "/" . getmypid(), env("TILESERVER_PORT")); - if (!$fp) { + if(!$fp) { abort(404); } else { fwrite($fp, "generate-tile;$z;$x;$y\n"); $content = ""; - while (!feof($fp)) { + while(!feof($fp)) { $content .= fgets($fp, 1024); } fclose($fp); @@ -116,11 +116,12 @@ }); }); +Route::get("search/reverse.php", [SearchController::class, "reverse"]); Route::group(['prefix' => 'reverse'], function () { Route::get('{lon}/{lat}', function ($lon, $lat) { - $link = config("maps.nominatim.host") . "/reverse.php?format=json&lat=$lat&lon=$lon&zoom=18&extratags=1&addressdetails=1&namedetails=1"; + $link = config("maps.nominatim.host")."/reverse.php?format=json&lat=$lat&lon=$lon&zoom=18&extratags=1&addressdetails=1&namedetails=1"; $resContent = file_get_contents($link); - $response = Response::make($resContent, 200); + $response = Response::make($resContent, 200); $response->header("Content-Type", "application/json"); return $response; }); @@ -156,16 +157,16 @@ Route::get('match/{vehicle}/{points}/{timestamp}/{radiuses}', [RoutingController::class, 'match']); Route::get('start/{vehicle}/{points?}', function ($vehicle, $points = "") { $waypoints = "[]"; - if ($points !== "") { + if($points !== "") { // Let's Convert - $points = explode(";", $points); + $points = explode(";", $points); $waypoints = "["; - foreach ($points as $index => $value) { - if ($value === "gps") { + foreach($points as $index => $value) { + if($value === "gps") { $waypoints .= '["gps"],'; } else { - $pos = explode(',', $value); - $waypoints .= "[" . $pos[0] . "," . $pos[1] . "],"; + $pos = explode(',', $value); + $waypoints .= "[".$pos[0].",".$pos[1]."],"; } } $waypoints = rtrim($waypoints, ","); @@ -175,8 +176,8 @@ ->with("vars", ["waypoints" => $waypoints, 'vehicle' => $vehicle]); }); Route::get('search/{search}', function ($search) { - $url = "https://tiles.metager.de/nominatim/search.php?q=" . urlencode($search) . "&limit=5&polygon_geojson=0&format=json&dedupe=1&extratags=1&addressdetails=1&namedetails=1"; - $content = file_get_contents($url); + $url = "https://tiles.metager.de/nominatim/search.php?q=".urlencode($search)."&limit=5&polygon_geojson=0&format=json&dedupe=1&extratags=1&addressdetails=1&namedetails=1"; + $content = file_get_contents($url); $response = Response::make($content, 200); $response->header('Content-Type', 'application/json'); return $response; diff --git a/app/webpack.mix.js b/app/webpack.mix.js index 3678776..594f17e 100644 --- a/app/webpack.mix.js +++ b/app/webpack.mix.js @@ -43,13 +43,8 @@ mix ], "public/js/lib.js" ); -if (mix.inProduction()) { - mix.babel(mapJsFiles, "public/js/map.js"); -} else { - mix - .scripts(mapJsFiles, "public/js/map-normal.js") - .babel("public/js/map-normal.js", "public/js/map.js"); -} +mix.scripts(mapJsFiles, "public/js/map.js"); + mix.scripts(["resources/js/turf.min.js"], "public/js/turf.min.js"); mix .styles( @@ -77,7 +72,6 @@ mix .styles( [ "resources/css/bootstrap.min.css", - "resources/css/ol.css", "resources/css/style.css", "resources/css/iframeSearch.css", ], diff --git a/build/fpm/Dockerfile b/build/fpm/Dockerfile index 9cab780..dfde02b 100644 --- a/build/fpm/Dockerfile +++ b/build/fpm/Dockerfile @@ -52,7 +52,7 @@ RUN installComposer && rm /usr/bin/installComposer USER mgmaps WORKDIR /html -VOLUME ["/mgmaps/.composer", "/html/vendor", "/html/bootstrap/cache"] +VOLUME ["/mgmaps/.composer"] CMD ["composer", "install"] FROM base as development @@ -75,7 +75,6 @@ ENTRYPOINT [ "/entrypoint.sh" ] CMD ["php-fpm7", "--nodaemonize"] USER mgmaps -VOLUME ["/html/vendor", "/html/bootstrap/cache"] FROM development as production diff --git a/docker-compose.yml b/docker-compose.yml index c8d2c25..e894def 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -14,6 +14,8 @@ services: image: ${IMAGE_NAME}/nginx:${IMAGE_TAG} ports: - 8080:8080 + extra_hosts: + - "host.docker.internal:host-gateway" working_dir: /html volumes: - ./app:/html @@ -30,7 +32,6 @@ services: image: ${IMAGE_NAME}/fpm:${IMAGE_TAG} volumes: - ./app:/html - - vendor:/html/vendor - bootstrap-cache:/html/bootstrap/cache assets: restart: unless-stopped @@ -57,10 +58,8 @@ services: volumes: - ./app:/html - composer-cache:/mgmaps/.composer - - vendor:/html/vendor - bootstrap-cache:/html/bootstrap/cache volumes: composer-cache: {} npm-cache: {} - vendor: {} bootstrap-cache: {} -- GitLab