Compare commits
105 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
7527eddbaf | ||
|
|
6854833fbd | ||
|
|
c8b90adfef | ||
|
|
d33a45dfa2 | ||
|
|
1cec149681 | ||
|
|
a629be0e2e | ||
|
|
6c32b280f5 | ||
|
|
787ab91eef | ||
|
|
5b539a75bb | ||
|
|
a6f80ef4b8 | ||
|
|
de42334b19 | ||
|
|
e4b1d6e1de | ||
|
|
cadc346de2 | ||
|
|
927a0a4627 | ||
|
|
d9cf8df052 | ||
|
|
2ff3682eff | ||
|
|
8836dd6e70 | ||
|
|
6ab0ed2df7 | ||
|
|
8dd3e7ebff | ||
|
|
7f71876dad | ||
|
|
54bea174ff | ||
|
|
9d37090e6b | ||
|
|
b42a214252 | ||
|
|
61d2506970 | ||
|
|
3bfbd47fdb | ||
|
|
4f5cc22ba0 | ||
|
|
a7205d8aec | ||
|
|
6d0fb4d74e | ||
|
|
d1185da6b1 | ||
|
|
6c4b30fa02 | ||
|
|
e2f8c01c42 | ||
|
|
ad7616abb2 | ||
|
|
56b08adef7 | ||
|
|
70162d7889 | ||
|
|
4c1be5967d | ||
|
|
d12cdc336c | ||
|
|
232f4975c4 | ||
|
|
45547eefbe | ||
|
|
086202cfdd | ||
|
|
3079924a3d | ||
|
|
7e812959e7 | ||
|
|
22aeb3612e | ||
|
|
6894bc8444 | ||
|
|
1620a11181 | ||
|
|
18ec8a487f | ||
|
|
329edc4ec6 | ||
|
|
7a5ad336c6 | ||
|
|
054dc81485 | ||
|
|
f63a856741 | ||
|
|
eb8a1845a5 | ||
|
|
5897cf55aa | ||
|
|
e46e0f85fb | ||
|
|
3fbc6fa361 | ||
|
|
e1336e1891 | ||
|
|
c30373963e | ||
|
|
96cb3d314f | ||
|
|
733167c612 | ||
|
|
84cc48a7bf | ||
|
|
c3d9946924 | ||
|
|
5e712ac88c | ||
|
|
9e94308cdc | ||
|
|
b8e3deb756 | ||
|
|
3e3104bbb1 | ||
|
|
56c5cef3f8 | ||
|
|
199fcb05e3 | ||
|
|
c42af7919e | ||
|
|
77d8d48b57 | ||
|
|
5cbae8c8f5 | ||
|
|
bf35b40b11 | ||
|
|
e5432f7cb5 | ||
|
|
2cf1fe5552 | ||
|
|
eb1a46cf7d | ||
|
|
a924cc4d11 | ||
|
|
5c99b6349c | ||
|
|
829569c6b5 | ||
|
|
e6d342dc96 | ||
|
|
8bfa1c45e7 | ||
|
|
bfcceac68f | ||
|
|
e812f2435e | ||
|
|
c4ddc62ab4 | ||
|
|
f117550694 | ||
|
|
dfda3e37a4 | ||
|
|
b5206cb354 | ||
|
|
90ba1140ac | ||
|
|
9cea85be80 | ||
|
|
e79211e0c1 | ||
|
|
ad23a9c9cd | ||
|
|
eafa5419c3 | ||
|
|
b529f0f0a0 | ||
|
|
c5c24f209a | ||
|
|
0381689fb6 | ||
|
|
89954ca5fc | ||
|
|
13f265b4e1 | ||
|
|
776ffa925f | ||
|
|
ada6b5640a | ||
|
|
33c197cf16 | ||
|
|
e0f250483d | ||
|
|
c4ee8518e1 | ||
|
|
d4b7bb7c57 | ||
|
|
a460cb3983 | ||
|
|
7f18033171 | ||
|
|
693ec7706e | ||
|
|
9081682286 | ||
|
|
9247dc9f41 | ||
|
|
4080e729df |
@@ -4,8 +4,11 @@
|
||||
|
||||
Welcome to [OpenLayers 3](http://openlayers.org/)!
|
||||
|
||||
## Examples
|
||||
Check out the [hosted examples](http://openlayers.org/en/master/examples/), the [workshop](http://openlayers.org/ol3-workshop/) or poke around the evolving [API docs](http://openlayers.org/en/master/apidoc/).
|
||||
|
||||
Please don't ask questions in the github issue tracker but use [the mailing list](https://groups.google.com/forum/#!forum/ol3-dev) instead.
|
||||
## Questions
|
||||
Please don't ask questions in the github issue tracker but use [stackoverflow with tag openlayers](http://stackoverflow.com/questions/tagged/openlayers) or [the mailing list](https://groups.google.com/forum/#!forum/ol3-dev) instead.
|
||||
|
||||
## Contributing
|
||||
Please see our guide on [contributing](CONTRIBUTING.md) if you're interested in getting involved.
|
||||
|
||||
@@ -1095,7 +1095,7 @@ class BeautifulStoneSoup(Tag, SGMLParser):
|
||||
p = self.tagStack[i]
|
||||
if (not p or p.name == name) and not isNestable:
|
||||
#Non-nestable tags get popped to the top or to their
|
||||
#last occurance.
|
||||
#last occurrence.
|
||||
popTo = name
|
||||
break
|
||||
if (nestingResetTriggers != None
|
||||
@@ -1242,14 +1242,14 @@ class BeautifulSoup(BeautifulStoneSoup):
|
||||
|
||||
* Tag nesting rules:
|
||||
|
||||
Most tags can't be nested at all. For instance, the occurance of
|
||||
Most tags can't be nested at all. For instance, the occurrence of
|
||||
a <p> tag should implicitly close the previous <p> tag.
|
||||
|
||||
<p>Para1<p>Para2
|
||||
should be transformed into:
|
||||
<p>Para1</p><p>Para2
|
||||
|
||||
Some tags can be nested arbitrarily. For instance, the occurance
|
||||
Some tags can be nested arbitrarily. For instance, the occurrence
|
||||
of a <blockquote> tag should _not_ implicitly close the previous
|
||||
<blockquote> tag.
|
||||
|
||||
|
||||
@@ -140,7 +140,7 @@
|
||||
|
||||
console.log('Capturing ' + lenHtmlFiles + ' example screenshots.');
|
||||
|
||||
// The main interval function that is executed regularily and renders a
|
||||
// The main interval function that is executed regularly and renders a
|
||||
// page to a file
|
||||
var interval = setInterval(function() {
|
||||
if (!loadInProgress && pageindex < lenHtmlFiles) {
|
||||
|
||||
2
build.py
2
build.py
@@ -804,7 +804,7 @@ Other less frequently used targets are:
|
||||
If no target is given, the build-target will be executed.
|
||||
|
||||
The above list is not complete, please see the source code for not-mentioned
|
||||
and only seldomly called targets.
|
||||
and only seldom called targets.
|
||||
'''
|
||||
|
||||
if __name__ == '__main__':
|
||||
|
||||
12
changelog/upgrade-notes.md
Normal file
12
changelog/upgrade-notes.md
Normal file
@@ -0,0 +1,12 @@
|
||||
## Upgrade notes
|
||||
|
||||
### v3.3.0
|
||||
|
||||
* The `ol.events.condition.mouseMove` function was replaced by `ol.events.condition.pointerMove` (see [#3281](https://github.com/openlayers/ol3/pull/3281)). For example, if you use `ol.events.condition.mouseMove` as the condition in a `Select` interaction then you now need to use `ol.events.condition.pointerMove`:
|
||||
|
||||
```js
|
||||
var selectInteraction = new ol.interaction.Select({
|
||||
condition: ol.events.condition.pointerMove
|
||||
// …
|
||||
});
|
||||
```
|
||||
51
changelog/v3.3.0.md
Normal file
51
changelog/v3.3.0.md
Normal file
@@ -0,0 +1,51 @@
|
||||
## Upgrade notes
|
||||
|
||||
* The `ol.events.condition.mouseMove` function was replaced by `ol.events.condition.pointerMove` (see [#3281](https://github.com/openlayers/ol3/pull/3281)). For example, if you use `ol.events.condition.mouseMove` as the condition in a `Select` interaction then you now need to use `ol.events.condition.pointerMove`:
|
||||
|
||||
```js
|
||||
var selectInteraction = new ol.interaction.Select({
|
||||
condition: ol.events.condition.pointerMove
|
||||
// …
|
||||
});
|
||||
```
|
||||
|
||||
## Overview of all changes
|
||||
|
||||
* [#3263](https://github.com/openlayers/ol3/pull/3263) - Support ArcGIS Rest Services ([@cwgrant](https://github.com/cwgrant))
|
||||
* [#3295](https://github.com/openlayers/ol3/pull/3295) - Add RESTful to WMTS GetCapabilities optionsFromCapabilities ([@sarametz](https://github.com/sarametz))
|
||||
* [#3304](https://github.com/openlayers/ol3/pull/3304) - Remove scale line inner padding ([@fredj](https://github.com/fredj))
|
||||
* [#3296](https://github.com/openlayers/ol3/pull/3296) - Add upgrade-notes.md file ([@elemoine](https://github.com/elemoine))
|
||||
* [#3303](https://github.com/openlayers/ol3/pull/3303) - Add constant for us-ft units ([@ahocevar](https://github.com/ahocevar))
|
||||
* [#3018](https://github.com/openlayers/ol3/pull/3018) - Add SelectEvent to interaction ([@bjornharrtell](https://github.com/bjornharrtell))
|
||||
* [#3301](https://github.com/openlayers/ol3/pull/3301) - Select interaction unit tests ([@bjornharrtell](https://github.com/bjornharrtell))
|
||||
* [#3298](https://github.com/openlayers/ol3/pull/3298) - Make ol.source.Source inherit from ol.Object ([@fredj](https://github.com/fredj))
|
||||
* [#3297](https://github.com/openlayers/ol3/pull/3297) - Add getters to ol.source.WMTS ([@fredj](https://github.com/fredj))
|
||||
* [#3281](https://github.com/openlayers/ol3/pull/3281) - Fix mouseMove event type comparison for IE10-11, pointermove ([@adube](https://github.com/adube))
|
||||
* [#3293](https://github.com/openlayers/ol3/pull/3293) - Add missing opacity option for ol.style.IconOptions ([@ahocevar](https://github.com/ahocevar))
|
||||
* [#3284](https://github.com/openlayers/ol3/pull/3284) - Fix jsdoc type for arrays of listening keys ([@fredj](https://github.com/fredj))
|
||||
* [#3278](https://github.com/openlayers/ol3/pull/3278) - Add goog.provide for ol.DrawEventType ([@elemoine](https://github.com/elemoine))
|
||||
* [#3272](https://github.com/openlayers/ol3/pull/3272) - Added getter function to return the wrapped source within the cluster ([@acanimal](https://github.com/acanimal))
|
||||
* [#3275](https://github.com/openlayers/ol3/pull/3275) - Add ol.layer.Heatmap#blur getter and setter ([@fredj](https://github.com/fredj))
|
||||
* [#3142](https://github.com/openlayers/ol3/pull/3142) - WMTS Get Cap document with updated WMTS.optionsFromCapabilities function ([@sarametz](https://github.com/sarametz))
|
||||
* [#3271](https://github.com/openlayers/ol3/pull/3271) - [wip] Fix misplaced comment blocks ([@fredj](https://github.com/fredj))
|
||||
* [#3273](https://github.com/openlayers/ol3/pull/3273) - Remove unused createGetTileIfLoadedFunction function. ([@tschaub](https://github.com/tschaub))
|
||||
* [#3270](https://github.com/openlayers/ol3/pull/3270) - Make ol.Overlay autoPan default to false ([@elemoine](https://github.com/elemoine))
|
||||
* [#3268](https://github.com/openlayers/ol3/pull/3268) - Fix autoPan in examples with ol.Overlay on hover ([@tsauerwein](https://github.com/tsauerwein))
|
||||
* [#3256](https://github.com/openlayers/ol3/pull/3256) - Add autoPan option to ol.Overlay ([@tsauerwein](https://github.com/tsauerwein))
|
||||
* [#3261](https://github.com/openlayers/ol3/pull/3261) - Fix forEachCorner extent, add TopLeft ([@adube](https://github.com/adube))
|
||||
* [#3260](https://github.com/openlayers/ol3/pull/3260) - Remove unused goog.require ([@fredj](https://github.com/fredj))
|
||||
* [#3246](https://github.com/openlayers/ol3/pull/3246) - Avoid creating unnecessary images in tile layers. ([@tschaub](https://github.com/tschaub))
|
||||
* [#3254](https://github.com/openlayers/ol3/pull/3254) - Use lineCap, lineJoin and miterLimit stroke properties in RegularShape ([@fredj](https://github.com/fredj))
|
||||
* [#3252](https://github.com/openlayers/ol3/pull/3252) - Avoid leaking global listenerSpy. ([@tschaub](https://github.com/tschaub))
|
||||
* [#3248](https://github.com/openlayers/ol3/pull/3248) - Add tile loading events to image tile sources. ([@tschaub](https://github.com/tschaub))
|
||||
* [#3240](https://github.com/openlayers/ol3/pull/3240) - Changes from the v3.2.x branch. ([@openlayers](https://github.com/openlayers))
|
||||
* [#3233](https://github.com/openlayers/ol3/pull/3233) - Four small fixes. ([@stweil](https://github.com/stweil))
|
||||
* [#3232](https://github.com/openlayers/ol3/pull/3232) - Fix typos found by codespell. ([@stweil](https://github.com/stweil))
|
||||
* [#3231](https://github.com/openlayers/ol3/pull/3231) - Make ol.layer.Heatmap#radius configurable ([@fredj](https://github.com/fredj))
|
||||
* [#3225](https://github.com/openlayers/ol3/pull/3225) - Respect attributions passed to TileJSON source. ([@tschaub](https://github.com/tschaub))
|
||||
* [#3223](https://github.com/openlayers/ol3/pull/3223) - Resize the canvas when the tile size changes. ([@tschaub](https://github.com/tschaub))
|
||||
* [#3224](https://github.com/openlayers/ol3/pull/3224) - Provide the ability to get the layer name from a MapQuest source ([@bartvde](https://github.com/bartvde))
|
||||
* [#3222](https://github.com/openlayers/ol3/pull/3222) - Add geodesic option for measure ([@bartvde](https://github.com/bartvde))
|
||||
* [#3221](https://github.com/openlayers/ol3/pull/3221) - Select the uppermost feature ([@fredj](https://github.com/fredj))
|
||||
* [#3211](https://github.com/openlayers/ol3/pull/3211) - Bing https logo fix. ([@photostu](https://github.com/photostu))
|
||||
* [#3215](https://github.com/openlayers/ol3/pull/3215) - Allow reuse of layer rendering code without creating a map. ([@tschaub](https://github.com/tschaub))
|
||||
@@ -21,7 +21,6 @@
|
||||
font-size: 10px;
|
||||
text-align: center;
|
||||
margin: 1px;
|
||||
padding: 0px 2px;
|
||||
}
|
||||
.ol-unsupported {
|
||||
display: none;
|
||||
|
||||
51
examples/arcgis-tiled.html
Normal file
51
examples/arcgis-tiled.html
Normal file
@@ -0,0 +1,51 @@
|
||||
<!doctype html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta http-equiv="X-UA-Compatible" content="chrome=1">
|
||||
<meta name="viewport" content="initial-scale=1.0, user-scalable=no, width=device-width">
|
||||
<link rel="stylesheet" href="../css/ol.css" type="text/css">
|
||||
<link rel="stylesheet" href="../resources/bootstrap/css/bootstrap.min.css" type="text/css">
|
||||
<link rel="stylesheet" href="../resources/layout.css" type="text/css">
|
||||
<link rel="stylesheet" href="../resources/bootstrap/css/bootstrap-responsive.min.css" type="text/css">
|
||||
<title>Tiled ArcGIS MapServer example</title>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<div class="navbar navbar-inverse navbar-fixed-top">
|
||||
<div class="navbar-inner">
|
||||
<div class="container">
|
||||
<a class="brand" href="./"><img src="../resources/logo.png"> OpenLayers 3 Examples</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="container-fluid">
|
||||
|
||||
<div class="row-fluid">
|
||||
<div class="span12">
|
||||
<div id="map" class="map"></div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="row-fluid">
|
||||
|
||||
<div class="span12">
|
||||
<h4 id="title">Tiled ArcGIS MapServer example</h4>
|
||||
<p id="shortdesc">Example of a tiled ArcGIS layer.</p>
|
||||
<div id="docs">
|
||||
<p>See the <a href="arcgis-tiled.js" target="_blank">arcgis-tiled.js source</a> to see how this is done.</p>
|
||||
</div>
|
||||
<div id="tags">arcgis, tile, tilelayer</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
<script src="../resources/jquery.min.js" type="text/javascript"></script>
|
||||
<script src="../resources/example-behaviour.js" type="text/javascript"></script>
|
||||
<script src="loader.js?id=arcgis-tiled" type="text/javascript"></script>
|
||||
|
||||
</body>
|
||||
</html>
|
||||
28
examples/arcgis-tiled.js
Normal file
28
examples/arcgis-tiled.js
Normal file
@@ -0,0 +1,28 @@
|
||||
goog.require('ol.Map');
|
||||
goog.require('ol.View');
|
||||
goog.require('ol.layer.Tile');
|
||||
goog.require('ol.source.MapQuest');
|
||||
goog.require('ol.source.TileArcGISRest');
|
||||
|
||||
var url = 'http://sampleserver1.arcgisonline.com/ArcGIS/rest/services/' +
|
||||
'Specialty/ESRI_StateCityHighway_USA/MapServer';
|
||||
|
||||
var layers = [
|
||||
new ol.layer.Tile({
|
||||
source: new ol.source.MapQuest({layer: 'sat'})
|
||||
}),
|
||||
new ol.layer.Tile({
|
||||
extent: [-13884991, 2870341, -7455066, 6338219],
|
||||
source: new ol.source.TileArcGISRest({
|
||||
url: url
|
||||
})
|
||||
})
|
||||
];
|
||||
var map = new ol.Map({
|
||||
layers: layers,
|
||||
target: 'map',
|
||||
view: new ol.View({
|
||||
center: [-10997148, 4569099],
|
||||
zoom: 4
|
||||
})
|
||||
});
|
||||
File diff suppressed because it is too large
Load Diff
@@ -29,7 +29,7 @@
|
||||
|
||||
<div class="row-fluid">
|
||||
|
||||
<div class="span12">
|
||||
<div class="span8">
|
||||
<h4 id="title">Earthquakes heatmap</h4>
|
||||
<p id="shortdesc">Demonstrates the use of a heatmap layer.</p>
|
||||
<div id="docs">
|
||||
@@ -40,8 +40,17 @@
|
||||
</div>
|
||||
<div id="tags">heatmap, kml, vector, style</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="span4">
|
||||
<form>
|
||||
<label>radius size</label>
|
||||
<input id="radius" type="range" min="1" max="50" step="1" value="5"/>
|
||||
<label>blur size</label>
|
||||
<input id="blur" type="range" min="1" max="50" step="1" value="15"/>
|
||||
</form>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<script src="../resources/jquery.min.js" type="text/javascript"></script>
|
||||
|
||||
@@ -5,6 +5,8 @@ goog.require('ol.layer.Tile');
|
||||
goog.require('ol.source.KML');
|
||||
goog.require('ol.source.Stamen');
|
||||
|
||||
var blur = $('#blur');
|
||||
var radius = $('#radius');
|
||||
|
||||
var vector = new ol.layer.Heatmap({
|
||||
source: new ol.source.KML({
|
||||
@@ -12,7 +14,8 @@ var vector = new ol.layer.Heatmap({
|
||||
projection: 'EPSG:3857',
|
||||
url: 'data/kml/2012_Earthquakes_Mag5.kml'
|
||||
}),
|
||||
radius: 5
|
||||
blur: parseInt(blur.val(), 10),
|
||||
radius: parseInt(radius.val(), 10)
|
||||
});
|
||||
|
||||
vector.getSource().on('addfeature', function(event) {
|
||||
@@ -38,3 +41,12 @@ var map = new ol.Map({
|
||||
zoom: 2
|
||||
})
|
||||
});
|
||||
|
||||
|
||||
blur.on('input', function() {
|
||||
vector.setBlur(parseInt(blur.val(), 10));
|
||||
});
|
||||
|
||||
radius.on('input', function() {
|
||||
vector.setRadius(parseInt(radius.val(), 10));
|
||||
});
|
||||
|
||||
@@ -75,10 +75,11 @@
|
||||
<option value="length">Length</option>
|
||||
<option value="area">Area</option>
|
||||
</select>
|
||||
<label class="checkbox"><input type="checkbox" id="geodesic"/>use geodesic measures</label>
|
||||
</form>
|
||||
|
||||
<div id="docs">
|
||||
<p><i>NOTE: Measure is done in simple way on projected plane. Earth
|
||||
<p><i>NOTE: If use geodesic measures is not checked, measure is done in simple way on projected plane. Earth
|
||||
curvature is not taken into account</i></p>
|
||||
<p>See the <a href="measure.js" target="_blank">measure.js source</a> to see how this is done.</p>
|
||||
</div>
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
goog.require('ol.Map');
|
||||
goog.require('ol.Overlay');
|
||||
goog.require('ol.Sphere');
|
||||
goog.require('ol.View');
|
||||
goog.require('ol.geom.LineString');
|
||||
goog.require('ol.geom.Polygon');
|
||||
@@ -7,6 +8,7 @@ goog.require('ol.interaction');
|
||||
goog.require('ol.interaction.Draw');
|
||||
goog.require('ol.layer.Tile');
|
||||
goog.require('ol.layer.Vector');
|
||||
goog.require('ol.proj');
|
||||
goog.require('ol.source.MapQuest');
|
||||
goog.require('ol.source.Vector');
|
||||
goog.require('ol.style.Circle');
|
||||
@@ -14,6 +16,9 @@ goog.require('ol.style.Fill');
|
||||
goog.require('ol.style.Stroke');
|
||||
goog.require('ol.style.Style');
|
||||
|
||||
|
||||
var wgs84Sphere = new ol.Sphere(6378137);
|
||||
|
||||
var raster = new ol.layer.Tile({
|
||||
source: new ol.source.MapQuest({layer: 'sat'})
|
||||
});
|
||||
@@ -135,6 +140,7 @@ var map = new ol.Map({
|
||||
map.on('pointermove', pointerMoveHandler);
|
||||
|
||||
var typeSelect = document.getElementById('type');
|
||||
var geodesicCheckbox = document.getElementById('geodesic');
|
||||
|
||||
var draw; // global so we can remove it later
|
||||
function addInteraction() {
|
||||
@@ -238,7 +244,19 @@ typeSelect.onchange = function(e) {
|
||||
* @return {string}
|
||||
*/
|
||||
var formatLength = function(line) {
|
||||
var length = Math.round(line.getLength() * 100) / 100;
|
||||
var length;
|
||||
if (geodesicCheckbox.checked) {
|
||||
var coordinates = line.getCoordinates();
|
||||
length = 0;
|
||||
var sourceProj = map.getView().getProjection();
|
||||
for (var i = 0, ii = coordinates.length - 1; i < ii; ++i) {
|
||||
var c1 = ol.proj.transform(coordinates[i], sourceProj, 'EPSG:4326');
|
||||
var c2 = ol.proj.transform(coordinates[i + 1], sourceProj, 'EPSG:4326');
|
||||
length += wgs84Sphere.haversineDistance(c1, c2);
|
||||
}
|
||||
} else {
|
||||
length = Math.round(line.getLength() * 100) / 100;
|
||||
}
|
||||
var output;
|
||||
if (length > 100) {
|
||||
output = (Math.round(length / 1000 * 100) / 100) +
|
||||
@@ -257,7 +275,16 @@ var formatLength = function(line) {
|
||||
* @return {string}
|
||||
*/
|
||||
var formatArea = function(polygon) {
|
||||
var area = polygon.getArea();
|
||||
var area;
|
||||
if (geodesicCheckbox.checked) {
|
||||
var sourceProj = map.getView().getProjection();
|
||||
var geom = /** @type {ol.geom.Polygon} */(polygon.clone().transform(
|
||||
sourceProj, 'EPSG:4326'));
|
||||
var coordinates = geom.getLinearRing(0).getCoordinates();
|
||||
area = Math.abs(wgs84Sphere.geodesicArea(coordinates));
|
||||
} else {
|
||||
area = polygon.getArea();
|
||||
}
|
||||
var output;
|
||||
if (area > 10000) {
|
||||
output = (Math.round(area / 1000000 * 100) / 100) +
|
||||
|
||||
@@ -29,9 +29,13 @@ closer.onclick = function() {
|
||||
/**
|
||||
* Create an overlay to anchor the popup to the map.
|
||||
*/
|
||||
var overlay = new ol.Overlay({
|
||||
element: container
|
||||
});
|
||||
var overlay = new ol.Overlay(/** @type {olx.OverlayOptions} */ ({
|
||||
element: container,
|
||||
autoPan: true,
|
||||
autoPanAnimation: {
|
||||
duration: 250
|
||||
}
|
||||
}));
|
||||
|
||||
|
||||
/**
|
||||
@@ -60,7 +64,7 @@ var map = new ol.Map({
|
||||
/**
|
||||
* Add a click handler to the map to render the popup.
|
||||
*/
|
||||
map.on('click', function(evt) {
|
||||
map.on('singleclick', function(evt) {
|
||||
var coordinate = evt.coordinate;
|
||||
var hdms = ol.coordinate.toStringHDMS(ol.proj.transform(
|
||||
coordinate, 'EPSG:3857', 'EPSG:4326'));
|
||||
|
||||
@@ -35,14 +35,16 @@
|
||||
<h4 id="title">Select features example</h4>
|
||||
<p id="shortdesc">Example of using the Select interaction. Choose between <code>Single-click</code>, <code>Click</code> and <code>Hover</code> as the event type for selection in the combobox below. When using <code>Single-click</code> or <code>Click</code> you can hold do <code>Shift</code> key to toggle the feature in the selection.</p>
|
||||
<p>Note: when <code>Single-click</code> is used double-clicks won't select features. This in contrast to <code>Click</code>, where a double-click will both select the feature and zoom the map (because of the <code>DoubleClickZoom</code> interaction). Note that <code>Single-click</code> is less responsive than <code>Click</code> because of the delay it uses to detect double-clicks.</p>
|
||||
<p>In this example, a listener is registered for the Select interaction's <code>select</code> event in order to update the selection status below.
|
||||
<form class="form-inline">
|
||||
<label>Action type </label>
|
||||
<select id="type">
|
||||
<option value="none" selected>None</option>
|
||||
<option value="singleclick">Single-click</option>
|
||||
<option value="click">Click</option>
|
||||
<option value="mousemove">Hover</option>
|
||||
<option value="pointermove">Hover</option>
|
||||
</select>
|
||||
<span id="status"> 0 selected features</span>
|
||||
</form>
|
||||
<div id="docs">
|
||||
<p>See the <a href="select-features.js" target="_blank">select-features.js source</a> to see how this is done.</p>
|
||||
|
||||
@@ -38,9 +38,9 @@ var selectClick = new ol.interaction.Select({
|
||||
condition: ol.events.condition.click
|
||||
});
|
||||
|
||||
// select interaction working on "mousemove"
|
||||
var selectMouseMove = new ol.interaction.Select({
|
||||
condition: ol.events.condition.mouseMove
|
||||
// select interaction working on "pointermove"
|
||||
var selectPointerMove = new ol.interaction.Select({
|
||||
condition: ol.events.condition.pointerMove
|
||||
});
|
||||
|
||||
var selectElement = document.getElementById('type');
|
||||
@@ -54,13 +54,18 @@ var changeInteraction = function() {
|
||||
select = selectSingleClick;
|
||||
} else if (value == 'click') {
|
||||
select = selectClick;
|
||||
} else if (value == 'mousemove') {
|
||||
select = selectMouseMove;
|
||||
} else if (value == 'pointermove') {
|
||||
select = selectPointerMove;
|
||||
} else {
|
||||
select = null;
|
||||
}
|
||||
if (select !== null) {
|
||||
map.addInteraction(select);
|
||||
select.on('select', function(e) {
|
||||
$('#status').html(' ' + e.target.getFeatures().getLength() +
|
||||
' selected features (last operation selected ' + e.selected.length +
|
||||
' and deselected ' + e.deselected.length + ' features)');
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
79
examples/tile-load-events.html
Normal file
79
examples/tile-load-events.html
Normal file
@@ -0,0 +1,79 @@
|
||||
<!doctype html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta http-equiv="X-UA-Compatible" content="chrome=1">
|
||||
<meta name="viewport" content="initial-scale=1.0, user-scalable=no, width=device-width">
|
||||
<link rel="stylesheet" href="../css/ol.css" type="text/css">
|
||||
<link rel="stylesheet" href="../resources/bootstrap/css/bootstrap.min.css" type="text/css">
|
||||
<link rel="stylesheet" href="../resources/layout.css" type="text/css">
|
||||
<link rel="stylesheet" href="../resources/bootstrap/css/bootstrap-responsive.min.css" type="text/css">
|
||||
<title>Tile load events example</title>
|
||||
<style>
|
||||
.map {
|
||||
background: #E0ECED;
|
||||
}
|
||||
.wrapper {
|
||||
position: relative;
|
||||
}
|
||||
#progress {
|
||||
position: absolute;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
height: 2px;
|
||||
background: rgba(0, 60, 136, 0.4);
|
||||
width: 0;
|
||||
transition: width 250ms;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<div class="navbar navbar-inverse navbar-fixed-top">
|
||||
<div class="navbar-inner">
|
||||
<div class="container">
|
||||
<a class="brand" href="./"><img src="../resources/logo.png"> OpenLayers 3 Examples</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="container-fluid">
|
||||
|
||||
<div class="row-fluid">
|
||||
<div class="span12 wrapper">
|
||||
<div id="map" class="map"></div>
|
||||
<div id="progress"></div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="row-fluid">
|
||||
|
||||
<div class="span12">
|
||||
<h4 id="title">Tile load events example</h4>
|
||||
<p id="shortdesc">Example using tile load events.</p>
|
||||
<div id="docs">
|
||||
<p>
|
||||
Image tile sources fire events related to tile loading. You can
|
||||
listen for <code>tileloadstart</code>, <code>tileloadend</code>,
|
||||
and <code>tileloaderror</code> type events to monitor tile loading
|
||||
progress. This example registers listeners for these events and
|
||||
renders a tile loading progress bar at the bottom of the map.
|
||||
</p>
|
||||
<p>
|
||||
See the <a href="tile-load-events.js" target="_blank">tile-load-events.js source</a>
|
||||
for more detail on how this is done.
|
||||
</p>
|
||||
</div>
|
||||
<div id="tags">tile, events, loading</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
<script src="../resources/jquery.min.js" type="text/javascript"></script>
|
||||
<script src="../resources/example-behaviour.js" type="text/javascript"></script>
|
||||
<script src="loader.js?id=tile-load-events" type="text/javascript"></script>
|
||||
|
||||
</body>
|
||||
</html>
|
||||
104
examples/tile-load-events.js
Normal file
104
examples/tile-load-events.js
Normal file
@@ -0,0 +1,104 @@
|
||||
goog.require('ol.Map');
|
||||
goog.require('ol.View');
|
||||
goog.require('ol.layer.Tile');
|
||||
goog.require('ol.source.TileJSON');
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Renders a progress bar.
|
||||
* @param {Element} el The target element.
|
||||
* @constructor
|
||||
*/
|
||||
function Progress(el) {
|
||||
this.el = el;
|
||||
this.loading = 0;
|
||||
this.loaded = 0;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Increment the count of loading tiles.
|
||||
*/
|
||||
Progress.prototype.addLoading = function() {
|
||||
if (this.loading === 0) {
|
||||
this.show();
|
||||
}
|
||||
++this.loading;
|
||||
this.update();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Increment the count of loaded tiles.
|
||||
*/
|
||||
Progress.prototype.addLoaded = function() {
|
||||
setTimeout(function() {
|
||||
++this.loaded;
|
||||
this.update();
|
||||
}.bind(this), 100);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Update the progress bar.
|
||||
*/
|
||||
Progress.prototype.update = function() {
|
||||
var width = (this.loaded / this.loading * 100).toFixed(1) + '%';
|
||||
this.el.style.width = width;
|
||||
if (this.loading === this.loaded) {
|
||||
this.loading = 0;
|
||||
this.loaded = 0;
|
||||
setTimeout(this.hide.bind(this), 500);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Show the progress bar.
|
||||
*/
|
||||
Progress.prototype.show = function() {
|
||||
this.el.style.visibility = 'visible';
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Hide the progress bar.
|
||||
*/
|
||||
Progress.prototype.hide = function() {
|
||||
if (this.loading === this.loaded) {
|
||||
this.el.style.visibility = 'hidden';
|
||||
this.el.style.width = 0;
|
||||
}
|
||||
};
|
||||
|
||||
var progress = new Progress(document.getElementById('progress'));
|
||||
|
||||
var source = new ol.source.TileJSON({
|
||||
url: 'http://api.tiles.mapbox.com/v3/mapbox.world-bright.jsonp',
|
||||
crossOrigin: 'anonymous'
|
||||
});
|
||||
|
||||
source.on('tileloadstart', function(event) {
|
||||
progress.addLoading();
|
||||
});
|
||||
|
||||
source.on('tileloadend', function(event) {
|
||||
progress.addLoaded();
|
||||
});
|
||||
source.on('tileloaderror', function(event) {
|
||||
progress.addLoaded();
|
||||
});
|
||||
|
||||
var map = new ol.Map({
|
||||
logo: false,
|
||||
layers: [
|
||||
new ol.layer.Tile({source: source})
|
||||
],
|
||||
renderer: exampleNS.getRendererFromQueryString(),
|
||||
target: 'map',
|
||||
view: new ol.View({
|
||||
center: [0, 0],
|
||||
zoom: 2
|
||||
})
|
||||
});
|
||||
@@ -12,7 +12,7 @@
|
||||
h2 {
|
||||
font-size: 1.5em;
|
||||
line-height: 15px;
|
||||
};
|
||||
}
|
||||
|
||||
.scale-cnt {
|
||||
margin: 5px;
|
||||
|
||||
51
examples/wmts-layer-from-capabilities.html
Normal file
51
examples/wmts-layer-from-capabilities.html
Normal file
@@ -0,0 +1,51 @@
|
||||
<!doctype html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta http-equiv="X-UA-Compatible" content="chrome=1">
|
||||
<meta name="viewport" content="initial-scale=1.0, user-scalable=no, width=device-width">
|
||||
<link rel="stylesheet" href="../css/ol.css" type="text/css">
|
||||
<link rel="stylesheet" href="../resources/bootstrap/css/bootstrap.min.css" type="text/css">
|
||||
<link rel="stylesheet" href="../resources/layout.css" type="text/css">
|
||||
<link rel="stylesheet" href="../resources/bootstrap/css/bootstrap-responsive.min.css" type="text/css">
|
||||
<title>WMTS Layer example from capabilities </title>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<div class="navbar navbar-inverse navbar-fixed-top">
|
||||
<div class="navbar-inner">
|
||||
<div class="container">
|
||||
<a class="brand" href="./"><img src="../resources/logo.png"> OpenLayers 3 Examples</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="container-fluid">
|
||||
|
||||
<div class="row-fluid">
|
||||
<div class="span12">
|
||||
<div id="map" class="map"></div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="row-fluid">
|
||||
|
||||
<div class="span12">
|
||||
<h4 id="title">WMTS Capabilities example</h4>
|
||||
<p id="shortdesc">Example of a WMTS source created from a WMTS capabilities document.</p>
|
||||
<div id="docs">
|
||||
<p>See the <a href="wmts-layer-from-capabilities.js" target="_blank">wmts-layer-from-capabilities.js source</a> to see how this is done.</p>
|
||||
</div>
|
||||
<div id="tags">wmts, capabilities, getcapabilities</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
<script src="../resources/jquery.min.js" type="text/javascript"></script>
|
||||
<script src="../resources/example-behaviour.js" type="text/javascript"></script>
|
||||
<script src="loader.js?id=wmts-layer-from-capabilities" type="text/javascript"></script>
|
||||
|
||||
</body>
|
||||
</html>
|
||||
37
examples/wmts-layer-from-capabilities.js
Normal file
37
examples/wmts-layer-from-capabilities.js
Normal file
@@ -0,0 +1,37 @@
|
||||
goog.require('ol.Map');
|
||||
goog.require('ol.View');
|
||||
goog.require('ol.format.WMTSCapabilities');
|
||||
goog.require('ol.layer.Tile');
|
||||
goog.require('ol.proj');
|
||||
goog.require('ol.source.OSM');
|
||||
goog.require('ol.source.WMTS');
|
||||
|
||||
var parser = new ol.format.WMTSCapabilities();
|
||||
var map;
|
||||
|
||||
$.ajax('data/WMTSCapabilities.xml').then(function(response) {
|
||||
var result = parser.read(response);
|
||||
var options = ol.source.WMTS.optionsFromCapabilities(result,
|
||||
{layer: 'layer-7328', matrixSet: 'EPSG:3857'});
|
||||
|
||||
var projection = ol.proj.get('EPSG:3857');
|
||||
var projectionExtent = projection.getExtent();
|
||||
map = new ol.Map({
|
||||
layers: [
|
||||
new ol.layer.Tile({
|
||||
source: new ol.source.OSM(),
|
||||
opacity: 0.7
|
||||
}),
|
||||
new ol.layer.Tile({
|
||||
opacity: 1,
|
||||
extent: projectionExtent,
|
||||
source: new ol.source.WMTS(options)
|
||||
})
|
||||
],
|
||||
target: 'map',
|
||||
view: new ol.View({
|
||||
center: [19412406.33, -5050500.21],
|
||||
zoom: 5
|
||||
})
|
||||
});
|
||||
});
|
||||
@@ -210,6 +210,17 @@ oli.render.Event.prototype.vectorContext;
|
||||
oli.source;
|
||||
|
||||
|
||||
/**
|
||||
* @interface
|
||||
*/
|
||||
oli.source.TileEvent = function() {};
|
||||
|
||||
|
||||
/**
|
||||
* @type {ol.Tile}
|
||||
*/
|
||||
oli.source.TileEvent.prototype.tile;
|
||||
|
||||
|
||||
/**
|
||||
* @interface
|
||||
|
||||
143
externs/olx.js
143
externs/olx.js
@@ -310,7 +310,10 @@ olx.MapOptions.prototype.view;
|
||||
* position: (ol.Coordinate|undefined),
|
||||
* positioning: (ol.OverlayPositioning|string|undefined),
|
||||
* stopEvent: (boolean|undefined),
|
||||
* insertFirst: (boolean|undefined)}}
|
||||
* insertFirst: (boolean|undefined),
|
||||
* autoPan: (boolean|undefined),
|
||||
* autoPanAnimation: (olx.animation.PanOptions|undefined),
|
||||
* autoPanMargin: (number|undefined)}}
|
||||
* @api stable
|
||||
*/
|
||||
olx.OverlayOptions;
|
||||
@@ -376,6 +379,35 @@ olx.OverlayOptions.prototype.stopEvent;
|
||||
olx.OverlayOptions.prototype.insertFirst;
|
||||
|
||||
|
||||
/**
|
||||
* If set to `true` the map is panned when calling `setPosition`, so that the
|
||||
* overlay is entirely visible in the current viewport.
|
||||
* The default is `false`.
|
||||
* @type {boolean|undefined}
|
||||
* @api
|
||||
*/
|
||||
olx.OverlayOptions.prototype.autoPan;
|
||||
|
||||
|
||||
/**
|
||||
* The options used to create a `ol.animation.pan` animation. This animation
|
||||
* is only used when `autoPan` is enabled. By default the default options for
|
||||
* `ol.animation.pan` are used. If set to `null` the panning is not animated.
|
||||
* @type {olx.animation.PanOptions|undefined}
|
||||
* @api
|
||||
*/
|
||||
olx.OverlayOptions.prototype.autoPanAnimation;
|
||||
|
||||
|
||||
/**
|
||||
* The margin (in pixels) between the overlay and the borders of the map when
|
||||
* autopanning. The default is `20`.
|
||||
* @type {number|undefined}
|
||||
* @api
|
||||
*/
|
||||
olx.OverlayOptions.prototype.autoPanMargin;
|
||||
|
||||
|
||||
/**
|
||||
* Object literal with config options for the projection.
|
||||
* @typedef {{code: string,
|
||||
@@ -4978,9 +5010,97 @@ olx.source.ServerVectorOptions.prototype.logo;
|
||||
*/
|
||||
olx.source.ServerVectorOptions.prototype.projection;
|
||||
|
||||
/**
|
||||
* @typedef {{attributions: (Array.<ol.Attribution>|undefined),
|
||||
* params: (Object.<string, *>|undefined),
|
||||
* logo: (string|olx.LogoOptions|undefined),
|
||||
* tileGrid: (ol.tilegrid.TileGrid|undefined),
|
||||
* projection: ol.proj.ProjectionLike,
|
||||
* tileLoadFunction: (ol.TileLoadFunctionType|undefined),
|
||||
* url: (string|undefined),
|
||||
* urls: (Array.<string>|undefined)}}
|
||||
* @api
|
||||
*/
|
||||
olx.source.TileArcGISRestOptions;
|
||||
|
||||
/**
|
||||
* @typedef {{crossOrigin: (null|string|undefined),
|
||||
* Attributions.
|
||||
* @type {Array.<ol.Attribution>|undefined}
|
||||
* @api
|
||||
*/
|
||||
olx.source.TileArcGISRestOptions.prototype.attributions;
|
||||
|
||||
|
||||
/**
|
||||
* ArcGIS Rest parameters. This field is optional. Service defaults will be
|
||||
* used for any fields not specified. `FORMAT` is `PNG32` by default. `F` is `IMAGE` by
|
||||
* default. `TRANSPARENT` is `true` by default. `BBOX, `SIZE`, `BBOXSR`,
|
||||
* and `IMAGESR` will be set dynamically. Set `LAYERS` to
|
||||
* override the default service layer visibility. See
|
||||
* {@link http://resources.arcgis.com/en/help/arcgis-rest-api/index.html#/Export_Map/02r3000000v7000000/}
|
||||
* for further reference.
|
||||
* @type {Object.<string,*>|undefined}
|
||||
* @api
|
||||
*/
|
||||
olx.source.TileArcGISRestOptions.prototype.params;
|
||||
|
||||
|
||||
/**
|
||||
* Logo.
|
||||
* @type {string|olx.LogoOptions|undefined}
|
||||
* @api
|
||||
*/
|
||||
olx.source.TileArcGISRestOptions.prototype.logo;
|
||||
|
||||
|
||||
/**
|
||||
* Tile grid. Base this on the resolutions, tilesize and extent supported by the
|
||||
* server.
|
||||
* If this is not defined, a default grid will be used: if there is a projection
|
||||
* extent, the grid will be based on that; if not, a grid based on a global
|
||||
* extent with origin at 0,0 will be used.
|
||||
* @type {ol.tilegrid.TileGrid|undefined}
|
||||
* @api
|
||||
*/
|
||||
olx.source.TileArcGISRestOptions.prototype.tileGrid;
|
||||
|
||||
/**
|
||||
* Projection.
|
||||
* @type {ol.proj.ProjectionLike}
|
||||
* @api
|
||||
*/
|
||||
olx.source.TileArcGISRestOptions.prototype.projection;
|
||||
|
||||
|
||||
/**
|
||||
* Optional function to load a tile given a URL.
|
||||
* @type {ol.TileLoadFunctionType|undefined}
|
||||
* @api
|
||||
*/
|
||||
olx.source.TileArcGISRestOptions.prototype.tileLoadFunction;
|
||||
|
||||
|
||||
/**
|
||||
* ArcGIS Rest service URL for a Map Service or Image Service. The
|
||||
* url should include /MapServer or /ImageServer.
|
||||
* @type {string|undefined}
|
||||
* @api
|
||||
*/
|
||||
olx.source.TileArcGISRestOptions.prototype.url;
|
||||
|
||||
|
||||
/**
|
||||
* ArcGIS Rest service urls. Use this instead of `url` when the ArcGIS Service supports multiple
|
||||
* urls for export requests.
|
||||
* @type {Array.<string>|undefined}
|
||||
* @api
|
||||
*/
|
||||
olx.source.TileArcGISRestOptions.prototype.urls;
|
||||
|
||||
|
||||
/**
|
||||
* @typedef {{attributions: (Array.<ol.Attribution>|undefined),
|
||||
* crossOrigin: (null|string|undefined),
|
||||
* tileLoadFunction: (ol.TileLoadFunctionType|undefined),
|
||||
* url: string,
|
||||
* wrapX: (boolean|undefined)}}
|
||||
@@ -4989,6 +5109,16 @@ olx.source.ServerVectorOptions.prototype.projection;
|
||||
olx.source.TileJSONOptions;
|
||||
|
||||
|
||||
/**
|
||||
* Optional attributions for the source. If provided, these will be used
|
||||
* instead of any attribution data advertised by the server. If not provided,
|
||||
* any attributions advertised by the server will be used.
|
||||
* @type {Array.<ol.Attribution>|undefined}
|
||||
* @api stable
|
||||
*/
|
||||
olx.source.TileJSONOptions.prototype.attributions;
|
||||
|
||||
|
||||
/**
|
||||
* The `crossOrigin` attribute for loaded images. Note that you must provide a
|
||||
* `crossOrigin` value if you are using the WebGL renderer or if you want to
|
||||
@@ -5789,6 +5919,7 @@ olx.style.FillOptions.prototype.color;
|
||||
* img: (Image|undefined),
|
||||
* offset: (Array.<number>|undefined),
|
||||
* offsetOrigin: (ol.style.IconOrigin|undefined),
|
||||
* opacity: (number|undefined),
|
||||
* scale: (number|undefined),
|
||||
* snapToPixel: (boolean|undefined),
|
||||
* rotateWithView: (boolean|undefined),
|
||||
@@ -5878,6 +6009,14 @@ olx.style.IconOptions.prototype.offset;
|
||||
olx.style.IconOptions.prototype.offsetOrigin;
|
||||
|
||||
|
||||
/**
|
||||
* Opacity of the icon. Default is `1`.
|
||||
* @type {number|undefined}
|
||||
* @api
|
||||
*/
|
||||
olx.style.IconOptions.prototype.opacity;
|
||||
|
||||
|
||||
/**
|
||||
* Scale.
|
||||
* @type {number|undefined}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "openlayers",
|
||||
"version": "3.2.1",
|
||||
"version": "3.3.0",
|
||||
"description": "Build tools and sources for developing OpenLayers based mapping applications",
|
||||
"keywords": [
|
||||
"map",
|
||||
|
||||
@@ -216,7 +216,7 @@ ol.Collection.prototype.push = function(elem) {
|
||||
|
||||
|
||||
/**
|
||||
* Removes the first occurence of elem from the collection.
|
||||
* Removes the first occurrence of elem from the collection.
|
||||
* @param {T} elem Element.
|
||||
* @return {T|undefined} The removed element or undefined if elem was not found.
|
||||
* @api stable
|
||||
|
||||
@@ -159,7 +159,7 @@ ol.coordinate.degreesToStringHDMS_ = function(degrees, hemispheres) {
|
||||
* 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} Formated coordinate.
|
||||
* @return {string} Formatted coordinate.
|
||||
* @api stable
|
||||
*/
|
||||
ol.coordinate.format = function(coordinate, template, opt_fractionDigits) {
|
||||
|
||||
@@ -28,7 +28,7 @@ ol.DeviceOrientationProperty = {
|
||||
*
|
||||
* Many new computers, and especially mobile phones
|
||||
* and tablets, provide hardware support for device orientation. Web
|
||||
* developers targetting mobile devices will be especially interested in this
|
||||
* developers targeting mobile devices will be especially interested in this
|
||||
* class.
|
||||
*
|
||||
* Device orientation data are relative to a common starting point. For mobile
|
||||
|
||||
@@ -158,7 +158,7 @@ ol.dom.setOpacity = function(element, value) {
|
||||
var alpha;
|
||||
|
||||
if (goog.userAgent.VERSION == '8.0') {
|
||||
regex = /progid:DXImageTransform\.Microsoft\.Alpha\(.*?\)/i,
|
||||
regex = /progid:DXImageTransform\.Microsoft\.Alpha\(.*?\)/i;
|
||||
alpha = 'progid:DXImageTransform.Microsoft.Alpha(Opacity=' +
|
||||
(value * 100) + ')';
|
||||
} else {
|
||||
@@ -298,3 +298,35 @@ ol.dom.transformElement2D =
|
||||
// content size.
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* 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}
|
||||
*/
|
||||
ol.dom.outerWidth = function(element) {
|
||||
var width = element.offsetWidth;
|
||||
var style = element.currentStyle || window.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}
|
||||
*/
|
||||
ol.dom.outerHeight = function(element) {
|
||||
var height = element.offsetHeight;
|
||||
var style = element.currentStyle || window.getComputedStyle(element);
|
||||
height += parseInt(style.marginTop, 10) + parseInt(style.marginBottom, 10);
|
||||
|
||||
return height;
|
||||
};
|
||||
|
||||
@@ -66,16 +66,6 @@ ol.events.condition.click = function(mapBrowserEvent) {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event.
|
||||
* @return {boolean} True if the browser event is a `mousemove` event.
|
||||
* @api
|
||||
*/
|
||||
ol.events.condition.mouseMove = function(mapBrowserEvent) {
|
||||
return mapBrowserEvent.originalEvent.type == 'mousemove';
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Always false.
|
||||
* @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event.
|
||||
@@ -86,6 +76,16 @@ ol.events.condition.mouseMove = function(mapBrowserEvent) {
|
||||
ol.events.condition.never = goog.functions.FALSE;
|
||||
|
||||
|
||||
/**
|
||||
* @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';
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.MapBrowserEvent} mapBrowserEvent Map browser event.
|
||||
* @return {boolean} True if the event is a map `singleclick` event.
|
||||
|
||||
@@ -463,7 +463,7 @@ ol.extent.forEachCorner = function(extent, callback, opt_this) {
|
||||
if (val) {
|
||||
return val;
|
||||
}
|
||||
val = callback.call(opt_this, ol.extent.getBottomRight(extent));
|
||||
val = callback.call(opt_this, ol.extent.getTopLeft(extent));
|
||||
if (val) {
|
||||
return val;
|
||||
}
|
||||
|
||||
@@ -51,7 +51,7 @@ ol.Image = function(extent, resolution, pixelRatio, attributions, src,
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Array.<number>}
|
||||
* @type {Array.<goog.events.Key>}
|
||||
*/
|
||||
this.imageListenerKeys_ = null;
|
||||
|
||||
|
||||
@@ -50,7 +50,7 @@ ol.ImageTile = function(tileCoord, state, src, crossOrigin, tileLoadFunction) {
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Array.<number>}
|
||||
* @type {Array.<goog.events.Key>}
|
||||
*/
|
||||
this.imageListenerKeys_ = null;
|
||||
|
||||
@@ -64,6 +64,15 @@ ol.ImageTile = function(tileCoord, state, src, crossOrigin, tileLoadFunction) {
|
||||
goog.inherits(ol.ImageTile, ol.Tile);
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.ImageTile.prototype.disposeInternal = function() {
|
||||
this.unlistenImage_();
|
||||
goog.base(this, 'disposeInternal');
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
* @api
|
||||
@@ -136,6 +145,7 @@ ol.ImageTile.prototype.handleImageLoad_ = function() {
|
||||
ol.ImageTile.prototype.load = function() {
|
||||
if (this.state == ol.TileState.IDLE) {
|
||||
this.state = ol.TileState.LOADING;
|
||||
this.changed();
|
||||
goog.asserts.assert(goog.isNull(this.imageListenerKeys_));
|
||||
this.imageListenerKeys_ = [
|
||||
goog.events.listenOnce(this.image_, goog.events.EventType.ERROR,
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
goog.provide('ol.DrawEvent');
|
||||
goog.provide('ol.DrawEventType');
|
||||
goog.provide('ol.interaction.Draw');
|
||||
|
||||
goog.require('goog.asserts');
|
||||
|
||||
@@ -3,6 +3,7 @@ goog.provide('ol.interaction.Select');
|
||||
goog.require('goog.array');
|
||||
goog.require('goog.asserts');
|
||||
goog.require('goog.events');
|
||||
goog.require('goog.events.Event');
|
||||
goog.require('goog.functions');
|
||||
goog.require('ol.CollectionEventType');
|
||||
goog.require('ol.Feature');
|
||||
@@ -13,6 +14,51 @@ goog.require('ol.interaction.Interaction');
|
||||
goog.require('ol.style.Style');
|
||||
|
||||
|
||||
/**
|
||||
* @enum {string}
|
||||
*/
|
||||
ol.SelectEventType = {
|
||||
/**
|
||||
* Triggered when feature(s) has been (de)selected.
|
||||
* @event ol.SelectEvent#select
|
||||
* @api
|
||||
*/
|
||||
SELECT: 'select'
|
||||
};
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @classdesc
|
||||
* Events emitted by {@link ol.interaction.Select} instances are instances of
|
||||
* this type.
|
||||
*
|
||||
* @param {string} type The event type.
|
||||
* @param {Array.<ol.Feature>} selected Selected features.
|
||||
* @param {Array.<ol.Feature>} deselected Deselected features.
|
||||
* @extends {goog.events.Event}
|
||||
* @constructor
|
||||
*/
|
||||
ol.SelectEvent = function(type, selected, deselected) {
|
||||
goog.base(this, type);
|
||||
|
||||
/**
|
||||
* Selected features array.
|
||||
* @type {Array.<ol.Feature>}
|
||||
* @api
|
||||
*/
|
||||
this.selected = selected;
|
||||
|
||||
/**
|
||||
* Deselected features array.
|
||||
* @type {Array.<ol.Feature>}
|
||||
* @api
|
||||
*/
|
||||
this.deselected = deselected;
|
||||
};
|
||||
goog.inherits(ol.SelectEvent, goog.events.Event);
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @classdesc
|
||||
@@ -140,6 +186,7 @@ ol.interaction.Select.handleEvent = function(mapBrowserEvent) {
|
||||
var features = this.featureOverlay_.getFeatures();
|
||||
var /** @type {Array.<ol.Feature>} */ deselected = [];
|
||||
var /** @type {Array.<ol.Feature>} */ selected = [];
|
||||
var change = false;
|
||||
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
|
||||
@@ -156,7 +203,9 @@ ol.interaction.Select.handleEvent = function(mapBrowserEvent) {
|
||||
features.item(0) == selected[0]) {
|
||||
// No change
|
||||
} else {
|
||||
change = true;
|
||||
if (features.getLength() !== 0) {
|
||||
deselected = Array.prototype.concat(features.getArray());
|
||||
features.clear();
|
||||
}
|
||||
if (this.multi_) {
|
||||
@@ -189,8 +238,15 @@ ol.interaction.Select.handleEvent = function(mapBrowserEvent) {
|
||||
features.remove(deselected[i]);
|
||||
}
|
||||
features.extend(selected);
|
||||
if (selected.length > 0 || deselected.length > 0) {
|
||||
change = true;
|
||||
}
|
||||
}
|
||||
return ol.events.condition.mouseMove(mapBrowserEvent);
|
||||
if (change) {
|
||||
this.dispatchEvent(
|
||||
new ol.SelectEvent(ol.SelectEventType.SELECT, selected, deselected));
|
||||
}
|
||||
return ol.events.condition.pointerMove(mapBrowserEvent);
|
||||
};
|
||||
|
||||
|
||||
|
||||
@@ -16,7 +16,9 @@ goog.require('ol.style.Style');
|
||||
* @enum {string}
|
||||
*/
|
||||
ol.layer.HeatmapLayerProperty = {
|
||||
GRADIENT: 'gradient'
|
||||
BLUR: 'blur',
|
||||
GRADIENT: 'gradient',
|
||||
RADIUS: 'radius'
|
||||
};
|
||||
|
||||
|
||||
@@ -52,6 +54,24 @@ ol.layer.Heatmap = function(opt_options) {
|
||||
*/
|
||||
this.gradient_ = null;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {number}
|
||||
*/
|
||||
this.shadow_ = goog.isDef(options.shadow) ? options.shadow : 250;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {string|undefined}
|
||||
*/
|
||||
this.circleImage_ = undefined;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Array.<Array.<ol.style.Style>>}
|
||||
*/
|
||||
this.styleCache_ = null;
|
||||
|
||||
goog.events.listen(this,
|
||||
ol.Object.getChangeEventType(ol.layer.HeatmapLayerProperty.GRADIENT),
|
||||
this.handleGradientChanged_, false, this);
|
||||
@@ -59,15 +79,16 @@ ol.layer.Heatmap = function(opt_options) {
|
||||
this.setGradient(goog.isDef(options.gradient) ?
|
||||
options.gradient : ol.layer.Heatmap.DEFAULT_GRADIENT);
|
||||
|
||||
var circle = ol.layer.Heatmap.createCircle_(
|
||||
goog.isDef(options.radius) ? options.radius : 8,
|
||||
goog.isDef(options.blur) ? options.blur : 15,
|
||||
goog.isDef(options.shadow) ? options.shadow : 250);
|
||||
this.setBlur(goog.isDef(options.blur) ? options.blur : 15);
|
||||
|
||||
/**
|
||||
* @type {Array.<Array.<ol.style.Style>>}
|
||||
*/
|
||||
var styleCache = new Array(256);
|
||||
this.setRadius(goog.isDef(options.radius) ? options.radius : 8);
|
||||
|
||||
goog.events.listen(this, [
|
||||
ol.Object.getChangeEventType(ol.layer.HeatmapLayerProperty.BLUR),
|
||||
ol.Object.getChangeEventType(ol.layer.HeatmapLayerProperty.RADIUS)
|
||||
], this.handleStyleChanged_, false, this);
|
||||
|
||||
this.handleStyleChanged_();
|
||||
|
||||
var weight = goog.isDef(options.weight) ? options.weight : 'weight';
|
||||
var weightFunction;
|
||||
@@ -80,25 +101,27 @@ ol.layer.Heatmap = function(opt_options) {
|
||||
}
|
||||
goog.asserts.assert(goog.isFunction(weightFunction));
|
||||
|
||||
this.setStyle(function(feature, resolution) {
|
||||
this.setStyle(goog.bind(function(feature, resolution) {
|
||||
goog.asserts.assert(!goog.isNull(this.styleCache_));
|
||||
goog.asserts.assert(goog.isDef(this.circleImage_));
|
||||
var weight = weightFunction(feature);
|
||||
var opacity = goog.isDef(weight) ? goog.math.clamp(weight, 0, 1) : 1;
|
||||
// cast to 8 bits
|
||||
var index = (255 * opacity) | 0;
|
||||
var style = styleCache[index];
|
||||
var style = this.styleCache_[index];
|
||||
if (!goog.isDef(style)) {
|
||||
style = [
|
||||
new ol.style.Style({
|
||||
image: new ol.style.Icon({
|
||||
opacity: opacity,
|
||||
src: circle
|
||||
src: this.circleImage_
|
||||
})
|
||||
})
|
||||
];
|
||||
styleCache[index] = style;
|
||||
this.styleCache_[index] = style;
|
||||
}
|
||||
return style;
|
||||
});
|
||||
}, this));
|
||||
|
||||
// For performance reasons, don't sort the features before rendering.
|
||||
// The render order is not relevant for a heatmap representation.
|
||||
@@ -142,27 +165,41 @@ ol.layer.Heatmap.createGradient_ = function(colors) {
|
||||
|
||||
|
||||
/**
|
||||
* @param {number} radius Radius size in pixel.
|
||||
* @param {number} blur Blur size in pixel.
|
||||
* @param {number} shadow Shadow offset size in pixel.
|
||||
* @return {string}
|
||||
* @private
|
||||
*/
|
||||
ol.layer.Heatmap.createCircle_ = function(radius, blur, shadow) {
|
||||
ol.layer.Heatmap.prototype.createCircle_ = function() {
|
||||
var radius = this.getRadius();
|
||||
var blur = this.getBlur();
|
||||
goog.asserts.assert(goog.isDef(radius) && goog.isDef(blur));
|
||||
var halfSize = radius + blur + 1;
|
||||
var size = 2 * halfSize;
|
||||
var context = ol.dom.createCanvasContext2D(size, size);
|
||||
context.shadowOffsetX = context.shadowOffsetY = shadow;
|
||||
context.shadowOffsetX = context.shadowOffsetY = this.shadow_;
|
||||
context.shadowBlur = blur;
|
||||
context.shadowColor = '#000';
|
||||
context.beginPath();
|
||||
var center = halfSize - shadow;
|
||||
var center = halfSize - this.shadow_;
|
||||
context.arc(center, center, radius, 0, Math.PI * 2, true);
|
||||
context.fill();
|
||||
return context.canvas.toDataURL();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {number} Blur size in pixels.
|
||||
* @api
|
||||
* @observable
|
||||
*/
|
||||
ol.layer.Heatmap.prototype.getBlur = function() {
|
||||
return /** @type {number} */ (this.get(ol.layer.HeatmapLayerProperty.BLUR));
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.layer.Heatmap.prototype,
|
||||
'getBlur',
|
||||
ol.layer.Heatmap.prototype.getBlur);
|
||||
|
||||
|
||||
/**
|
||||
* @return {Array.<string>} Colors.
|
||||
* @api
|
||||
@@ -178,6 +215,20 @@ goog.exportProperty(
|
||||
ol.layer.Heatmap.prototype.getGradient);
|
||||
|
||||
|
||||
/**
|
||||
* @return {number} Radius size in pixel.
|
||||
* @api
|
||||
* @observable
|
||||
*/
|
||||
ol.layer.Heatmap.prototype.getRadius = function() {
|
||||
return /** @type {number} */ (this.get(ol.layer.HeatmapLayerProperty.RADIUS));
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.layer.Heatmap.prototype,
|
||||
'getRadius',
|
||||
ol.layer.Heatmap.prototype.getRadius);
|
||||
|
||||
|
||||
/**
|
||||
* @private
|
||||
*/
|
||||
@@ -186,12 +237,23 @@ ol.layer.Heatmap.prototype.handleGradientChanged_ = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @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) {
|
||||
goog.asserts.assert(event.type == ol.render.EventType.RENDER);
|
||||
goog.asserts.assert(!goog.isNull(this.gradient_));
|
||||
var context = event.context;
|
||||
var canvas = context.canvas;
|
||||
var image = context.getImageData(0, 0, canvas.width, canvas.height);
|
||||
@@ -209,6 +271,20 @@ ol.layer.Heatmap.prototype.handleRender_ = function(event) {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {number} blur Blur size in pixels.
|
||||
* @api
|
||||
* @observable
|
||||
*/
|
||||
ol.layer.Heatmap.prototype.setBlur = function(blur) {
|
||||
this.set(ol.layer.HeatmapLayerProperty.BLUR, blur);
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.layer.Heatmap.prototype,
|
||||
'setBlur',
|
||||
ol.layer.Heatmap.prototype.setBlur);
|
||||
|
||||
|
||||
/**
|
||||
* @param {Array.<string>} colors Gradient.
|
||||
* @api
|
||||
@@ -221,3 +297,17 @@ goog.exportProperty(
|
||||
ol.layer.Heatmap.prototype,
|
||||
'setGradient',
|
||||
ol.layer.Heatmap.prototype.setGradient);
|
||||
|
||||
|
||||
/**
|
||||
* @param {number} radius Radius size in pixel.
|
||||
* @api
|
||||
* @observable
|
||||
*/
|
||||
ol.layer.Heatmap.prototype.setRadius = function(radius) {
|
||||
this.set(ol.layer.HeatmapLayerProperty.RADIUS, radius);
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.layer.Heatmap.prototype,
|
||||
'setRadius',
|
||||
ol.layer.Heatmap.prototype.setRadius);
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
// FIXME recheck layer/map projection compatability when projection changes
|
||||
// FIXME recheck layer/map projection compatibility when projection changes
|
||||
// FIXME layer renderers should skip when they can't reproject
|
||||
// FIXME add tilt and height?
|
||||
|
||||
|
||||
@@ -156,7 +156,7 @@ ol.MapBrowserEventHandler = function(map) {
|
||||
this.dragging_ = false;
|
||||
|
||||
/**
|
||||
* @type {Array.<number>}
|
||||
* @type {Array.<goog.events.Key>}
|
||||
* @private
|
||||
*/
|
||||
this.dragListenerKeys_ = null;
|
||||
|
||||
@@ -11,6 +11,9 @@ goog.require('ol.Coordinate');
|
||||
goog.require('ol.Map');
|
||||
goog.require('ol.MapEventType');
|
||||
goog.require('ol.Object');
|
||||
goog.require('ol.animation');
|
||||
goog.require('ol.dom');
|
||||
goog.require('ol.extent');
|
||||
|
||||
|
||||
/**
|
||||
@@ -90,6 +93,26 @@ ol.Overlay = function(options) {
|
||||
this.element_ = goog.dom.createElement(goog.dom.TagName.DIV);
|
||||
this.element_.style.position = 'absolute';
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {boolean}
|
||||
*/
|
||||
this.autoPan_ = goog.isDef(options.autoPan) ? options.autoPan : false;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {olx.animation.PanOptions}
|
||||
*/
|
||||
this.autoPanAnimation_ = goog.isDef(options.autoPanAnimation) ?
|
||||
options.autoPanAnimation : /** @type {olx.animation.PanOptions} */ ({});
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {number}
|
||||
*/
|
||||
this.autoPanMargin_ = goog.isDef(options.autoPanMargin) ?
|
||||
options.autoPanMargin : 20;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {{bottom_: string,
|
||||
@@ -291,6 +314,9 @@ ol.Overlay.prototype.handleOffsetChanged = function() {
|
||||
*/
|
||||
ol.Overlay.prototype.handlePositionChanged = function() {
|
||||
this.updatePixelPosition_();
|
||||
if (goog.isDef(this.get(ol.OverlayProperty.POSITION)) && this.autoPan_) {
|
||||
this.panIntoView_();
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -364,6 +390,89 @@ goog.exportProperty(
|
||||
ol.Overlay.prototype.setPosition);
|
||||
|
||||
|
||||
/**
|
||||
* Pan the map so that the overlay is entirely visible in the current viewport
|
||||
* (if necessary).
|
||||
* @private
|
||||
*/
|
||||
ol.Overlay.prototype.panIntoView_ = function() {
|
||||
goog.asserts.assert(this.autoPan_);
|
||||
var map = this.getMap();
|
||||
|
||||
if (!goog.isDef(map) || goog.isNull(map.getTargetElement())) {
|
||||
return;
|
||||
}
|
||||
|
||||
var mapRect = this.getRect_(map.getTargetElement(), map.getSize());
|
||||
var element = this.getElement();
|
||||
goog.asserts.assert(!goog.isNull(element) && goog.isDef(element));
|
||||
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 = map.getView().getCenter();
|
||||
goog.asserts.assert(goog.isDef(center));
|
||||
var centerPx = map.getPixelFromCoordinate(center);
|
||||
var newCenterPx = [
|
||||
centerPx[0] + delta[0],
|
||||
centerPx[1] + delta[1]
|
||||
];
|
||||
|
||||
if (!goog.isNull(this.autoPanAnimation_)) {
|
||||
this.autoPanAnimation_.source = center;
|
||||
map.beforeRender(ol.animation.pan(this.autoPanAnimation_));
|
||||
}
|
||||
map.getView().setCenter(map.getCoordinateFromPixel(newCenterPx));
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* 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}
|
||||
* @private
|
||||
*/
|
||||
ol.Overlay.prototype.getRect_ = function(element, size) {
|
||||
goog.asserts.assert(!goog.isNull(element) && goog.isDef(element));
|
||||
goog.asserts.assert(goog.isDef(size));
|
||||
|
||||
var offset = goog.style.getPageOffset(element);
|
||||
return [
|
||||
offset.x,
|
||||
offset.y,
|
||||
offset.x + size[0],
|
||||
offset.y + size[1]
|
||||
];
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Set the positioning for this overlay.
|
||||
* @param {ol.OverlayPositioning} positioning how the overlay is
|
||||
|
||||
@@ -187,7 +187,7 @@ ol.pointer.TouchSource.prototype.touchToPointer_ =
|
||||
// Touch identifiers can start at 0.
|
||||
// Add 2 to the touch identifier for compatibility.
|
||||
e.pointerId = inTouch.identifier + 2;
|
||||
// TODO: check if this is neccessary?
|
||||
// TODO: check if this is necessary?
|
||||
//e.target = findTarget(e);
|
||||
e.bubbles = true;
|
||||
e.cancelable = true;
|
||||
|
||||
@@ -32,7 +32,8 @@ ol.proj.Units = {
|
||||
DEGREES: 'degrees',
|
||||
FEET: 'ft',
|
||||
METERS: 'm',
|
||||
PIXELS: 'pixels'
|
||||
PIXELS: 'pixels',
|
||||
USFEET: 'us-ft'
|
||||
};
|
||||
|
||||
|
||||
@@ -47,6 +48,7 @@ ol.proj.METERS_PER_UNIT[ol.proj.Units.DEGREES] =
|
||||
2 * Math.PI * ol.sphere.NORMAL.radius / 360;
|
||||
ol.proj.METERS_PER_UNIT[ol.proj.Units.FEET] = 0.3048;
|
||||
ol.proj.METERS_PER_UNIT[ol.proj.Units.METERS] = 1;
|
||||
ol.proj.METERS_PER_UNIT[ol.proj.Units.USFEET] = 1200 / 3937;
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -9,7 +9,6 @@ goog.require('ol.dom');
|
||||
goog.require('ol.extent');
|
||||
goog.require('ol.layer.Image');
|
||||
goog.require('ol.proj');
|
||||
goog.require('ol.renderer.Map');
|
||||
goog.require('ol.renderer.canvas.Layer');
|
||||
goog.require('ol.source.ImageVector');
|
||||
goog.require('ol.vec.Mat4');
|
||||
@@ -19,12 +18,11 @@ goog.require('ol.vec.Mat4');
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.renderer.canvas.Layer}
|
||||
* @param {ol.renderer.Map} mapRenderer Map renderer.
|
||||
* @param {ol.layer.Image} imageLayer Single image layer.
|
||||
*/
|
||||
ol.renderer.canvas.ImageLayer = function(mapRenderer, imageLayer) {
|
||||
ol.renderer.canvas.ImageLayer = function(imageLayer) {
|
||||
|
||||
goog.base(this, mapRenderer, imageLayer);
|
||||
goog.base(this, imageLayer);
|
||||
|
||||
/**
|
||||
* @private
|
||||
@@ -88,7 +86,9 @@ ol.renderer.canvas.ImageLayer.prototype.forEachLayerAtPixel =
|
||||
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 = this.getMap().getCoordinateFromPixel(pixel);
|
||||
var coordinate = pixel.slice();
|
||||
ol.vec.Mat4.multVec2(
|
||||
frameState.pixelToCoordinateMatrix, coordinate, coordinate);
|
||||
var hasFeature = this.forEachFeatureAtCoordinate(
|
||||
coordinate, frameState, goog.functions.TRUE, this);
|
||||
|
||||
|
||||
@@ -17,12 +17,11 @@ goog.require('ol.vec.Mat4');
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.renderer.Layer}
|
||||
* @param {ol.renderer.Map} mapRenderer Map renderer.
|
||||
* @param {ol.layer.Layer} layer Layer.
|
||||
*/
|
||||
ol.renderer.canvas.Layer = function(mapRenderer, layer) {
|
||||
ol.renderer.canvas.Layer = function(layer) {
|
||||
|
||||
goog.base(this, mapRenderer, layer);
|
||||
goog.base(this, layer);
|
||||
|
||||
/**
|
||||
* @private
|
||||
|
||||
@@ -77,11 +77,11 @@ goog.inherits(ol.renderer.canvas.Map, ol.renderer.Map);
|
||||
*/
|
||||
ol.renderer.canvas.Map.prototype.createLayerRenderer = function(layer) {
|
||||
if (ol.ENABLE_IMAGE && layer instanceof ol.layer.Image) {
|
||||
return new ol.renderer.canvas.ImageLayer(this, layer);
|
||||
return new ol.renderer.canvas.ImageLayer(layer);
|
||||
} else if (ol.ENABLE_TILE && layer instanceof ol.layer.Tile) {
|
||||
return new ol.renderer.canvas.TileLayer(this, layer);
|
||||
return new ol.renderer.canvas.TileLayer(layer);
|
||||
} else if (ol.ENABLE_VECTOR && layer instanceof ol.layer.Vector) {
|
||||
return new ol.renderer.canvas.VectorLayer(this, layer);
|
||||
return new ol.renderer.canvas.VectorLayer(layer);
|
||||
} else {
|
||||
goog.asserts.fail();
|
||||
return null;
|
||||
|
||||
@@ -13,7 +13,6 @@ goog.require('ol.TileState');
|
||||
goog.require('ol.dom');
|
||||
goog.require('ol.extent');
|
||||
goog.require('ol.layer.Tile');
|
||||
goog.require('ol.renderer.Map');
|
||||
goog.require('ol.renderer.canvas.Layer');
|
||||
goog.require('ol.tilecoord');
|
||||
goog.require('ol.vec.Mat4');
|
||||
@@ -23,12 +22,11 @@ goog.require('ol.vec.Mat4');
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.renderer.canvas.Layer}
|
||||
* @param {ol.renderer.Map} mapRenderer Map renderer.
|
||||
* @param {ol.layer.Tile} tileLayer Tile layer.
|
||||
*/
|
||||
ol.renderer.canvas.TileLayer = function(mapRenderer, tileLayer) {
|
||||
ol.renderer.canvas.TileLayer = function(tileLayer) {
|
||||
|
||||
goog.base(this, mapRenderer, tileLayer);
|
||||
goog.base(this, tileLayer);
|
||||
|
||||
/**
|
||||
* @private
|
||||
@@ -72,6 +70,12 @@ ol.renderer.canvas.TileLayer = function(mapRenderer, tileLayer) {
|
||||
*/
|
||||
this.renderedCanvasZ_ = NaN;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {number}
|
||||
*/
|
||||
this.renderedTileSize_ = NaN;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.TileRange}
|
||||
@@ -230,9 +234,11 @@ ol.renderer.canvas.TileLayer.prototype.prepareFrame =
|
||||
context = this.context_;
|
||||
if (this.canvasSize_[0] < canvasWidth ||
|
||||
this.canvasSize_[1] < canvasHeight ||
|
||||
this.renderedTileSize_ !== tilePixelSize ||
|
||||
(this.canvasTooBig_ && (this.canvasSize_[0] > canvasWidth ||
|
||||
this.canvasSize_[1] > canvasHeight))) {
|
||||
// Canvas is too small, resize it. We never shrink the canvas, unless
|
||||
// Canvas is too small or tileSize has changed, resize it.
|
||||
// We never shrink the canvas, unless
|
||||
// we know that the current canvas size exceeds the maximum size
|
||||
canvas.width = canvasWidth;
|
||||
canvas.height = canvasHeight;
|
||||
@@ -259,6 +265,7 @@ ol.renderer.canvas.TileLayer.prototype.prepareFrame =
|
||||
minY = tileRange.minY -
|
||||
Math.floor((canvasTileRangeHeight - tileRange.getHeight()) / 2);
|
||||
this.renderedCanvasZ_ = z;
|
||||
this.renderedTileSize_ = tilePixelSize;
|
||||
this.renderedCanvasTileRange_ = new ol.TileRange(
|
||||
minX, minX + canvasTileRangeWidth - 1,
|
||||
minY, minY + canvasTileRangeHeight - 1);
|
||||
@@ -280,11 +287,7 @@ ol.renderer.canvas.TileLayer.prototype.prepareFrame =
|
||||
/** @type {Array.<ol.Tile>} */
|
||||
var tilesToClear = [];
|
||||
|
||||
var getTileIfLoaded = this.createGetTileIfLoadedFunction(function(tile) {
|
||||
return !goog.isNull(tile) && tile.getState() == ol.TileState.LOADED;
|
||||
}, tileSource, pixelRatio, projection);
|
||||
var findLoadedTiles = goog.bind(tileSource.findLoadedTiles, tileSource,
|
||||
tilesToDrawByZ, getTileIfLoaded);
|
||||
var findLoadedTiles = this.createLoadedTileFinder(tileSource, tilesToDrawByZ);
|
||||
|
||||
var useInterimTilesOnError = tileLayer.getUseInterimTilesOnError();
|
||||
|
||||
|
||||
@@ -17,12 +17,11 @@ goog.require('ol.renderer.vector');
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.renderer.canvas.Layer}
|
||||
* @param {ol.renderer.Map} mapRenderer Map renderer.
|
||||
* @param {ol.layer.Vector} vectorLayer Vector layer.
|
||||
*/
|
||||
ol.renderer.canvas.VectorLayer = function(mapRenderer, vectorLayer) {
|
||||
ol.renderer.canvas.VectorLayer = function(vectorLayer) {
|
||||
|
||||
goog.base(this, mapRenderer, vectorLayer);
|
||||
goog.base(this, vectorLayer);
|
||||
|
||||
/**
|
||||
* @private
|
||||
|
||||
@@ -18,14 +18,13 @@ goog.require('ol.vec.Mat4');
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.renderer.dom.Layer}
|
||||
* @param {ol.renderer.Map} mapRenderer Map renderer.
|
||||
* @param {ol.layer.Image} imageLayer Image layer.
|
||||
*/
|
||||
ol.renderer.dom.ImageLayer = function(mapRenderer, imageLayer) {
|
||||
ol.renderer.dom.ImageLayer = function(imageLayer) {
|
||||
var target = goog.dom.createElement(goog.dom.TagName.DIV);
|
||||
target.style.position = 'absolute';
|
||||
|
||||
goog.base(this, mapRenderer, imageLayer, target);
|
||||
goog.base(this, imageLayer, target);
|
||||
|
||||
/**
|
||||
* The last rendered image.
|
||||
|
||||
@@ -8,13 +8,12 @@ goog.require('ol.renderer.Layer');
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.renderer.Layer}
|
||||
* @param {ol.renderer.Map} mapRenderer Map renderer.
|
||||
* @param {ol.layer.Layer} layer Layer.
|
||||
* @param {!Element} target Target.
|
||||
*/
|
||||
ol.renderer.dom.Layer = function(mapRenderer, layer, target) {
|
||||
ol.renderer.dom.Layer = function(layer, target) {
|
||||
|
||||
goog.base(this, mapRenderer, layer);
|
||||
goog.base(this, layer);
|
||||
|
||||
/**
|
||||
* @type {!Element}
|
||||
|
||||
@@ -112,12 +112,12 @@ ol.renderer.dom.Map.prototype.disposeInternal = function() {
|
||||
ol.renderer.dom.Map.prototype.createLayerRenderer = function(layer) {
|
||||
var layerRenderer;
|
||||
if (ol.ENABLE_IMAGE && layer instanceof ol.layer.Image) {
|
||||
layerRenderer = new ol.renderer.dom.ImageLayer(this, layer);
|
||||
layerRenderer = new ol.renderer.dom.ImageLayer(layer);
|
||||
} else if (ol.ENABLE_TILE && layer instanceof ol.layer.Tile) {
|
||||
layerRenderer = new ol.renderer.dom.TileLayer(this, layer);
|
||||
layerRenderer = new ol.renderer.dom.TileLayer(layer);
|
||||
} else if (!(ol.LEGACY_IE_SUPPORT && ol.IS_LEGACY_IE) &&
|
||||
ol.ENABLE_VECTOR && layer instanceof ol.layer.Vector) {
|
||||
layerRenderer = new ol.renderer.dom.VectorLayer(this, layer);
|
||||
layerRenderer = new ol.renderer.dom.VectorLayer(layer);
|
||||
} else {
|
||||
goog.asserts.fail();
|
||||
return null;
|
||||
|
||||
@@ -30,10 +30,9 @@ goog.require('ol.vec.Mat4');
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.renderer.dom.Layer}
|
||||
* @param {ol.renderer.Map} mapRenderer Map renderer.
|
||||
* @param {ol.layer.Tile} tileLayer Tile layer.
|
||||
*/
|
||||
ol.renderer.dom.TileLayer = function(mapRenderer, tileLayer) {
|
||||
ol.renderer.dom.TileLayer = function(tileLayer) {
|
||||
|
||||
var target = goog.dom.createElement(goog.dom.TagName.DIV);
|
||||
target.style.position = 'absolute';
|
||||
@@ -44,7 +43,7 @@ ol.renderer.dom.TileLayer = function(mapRenderer, tileLayer) {
|
||||
target.style.height = '100%';
|
||||
}
|
||||
|
||||
goog.base(this, mapRenderer, tileLayer, target);
|
||||
goog.base(this, tileLayer, target);
|
||||
|
||||
/**
|
||||
* @private
|
||||
@@ -129,11 +128,7 @@ ol.renderer.dom.TileLayer.prototype.prepareFrame =
|
||||
var tilesToDrawByZ = {};
|
||||
tilesToDrawByZ[z] = {};
|
||||
|
||||
var getTileIfLoaded = this.createGetTileIfLoadedFunction(function(tile) {
|
||||
return !goog.isNull(tile) && tile.getState() == ol.TileState.LOADED;
|
||||
}, tileSource, pixelRatio, projection);
|
||||
var findLoadedTiles = goog.bind(tileSource.findLoadedTiles, tileSource,
|
||||
tilesToDrawByZ, getTileIfLoaded);
|
||||
var findLoadedTiles = this.createLoadedTileFinder(tileSource, tilesToDrawByZ);
|
||||
|
||||
var useInterimTilesOnError = tileLayer.getUseInterimTilesOnError();
|
||||
|
||||
|
||||
@@ -21,10 +21,9 @@ goog.require('ol.vec.Mat4');
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.renderer.dom.Layer}
|
||||
* @param {ol.renderer.Map} mapRenderer Map renderer.
|
||||
* @param {ol.layer.Vector} vectorLayer Vector layer.
|
||||
*/
|
||||
ol.renderer.dom.VectorLayer = function(mapRenderer, vectorLayer) {
|
||||
ol.renderer.dom.VectorLayer = function(vectorLayer) {
|
||||
|
||||
/**
|
||||
* @private
|
||||
@@ -39,7 +38,7 @@ ol.renderer.dom.VectorLayer = function(mapRenderer, vectorLayer) {
|
||||
target.style.maxWidth = 'none';
|
||||
target.style.position = 'absolute';
|
||||
|
||||
goog.base(this, mapRenderer, vectorLayer, target);
|
||||
goog.base(this, vectorLayer, target);
|
||||
|
||||
/**
|
||||
* @private
|
||||
|
||||
@@ -6,6 +6,7 @@ goog.require('goog.events');
|
||||
goog.require('goog.events.EventType');
|
||||
goog.require('goog.functions');
|
||||
goog.require('ol.ImageState');
|
||||
goog.require('ol.Observable');
|
||||
goog.require('ol.TileRange');
|
||||
goog.require('ol.TileState');
|
||||
goog.require('ol.layer.Layer');
|
||||
@@ -13,27 +14,21 @@ goog.require('ol.source.Source');
|
||||
goog.require('ol.source.State');
|
||||
goog.require('ol.source.Tile');
|
||||
goog.require('ol.tilecoord');
|
||||
goog.require('ol.vec.Mat4');
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {goog.Disposable}
|
||||
* @param {ol.renderer.Map} mapRenderer Map renderer.
|
||||
* @extends {ol.Observable}
|
||||
* @param {ol.layer.Layer} layer Layer.
|
||||
* @suppress {checkStructDictInheritance}
|
||||
* @struct
|
||||
*/
|
||||
ol.renderer.Layer = function(mapRenderer, layer) {
|
||||
ol.renderer.Layer = function(layer) {
|
||||
|
||||
goog.base(this);
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.renderer.Map}
|
||||
*/
|
||||
this.mapRenderer_ = mapRenderer;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.layer.Layer}
|
||||
@@ -42,7 +37,7 @@ ol.renderer.Layer = function(mapRenderer, layer) {
|
||||
|
||||
|
||||
};
|
||||
goog.inherits(ol.renderer.Layer, goog.Disposable);
|
||||
goog.inherits(ol.renderer.Layer, ol.Observable);
|
||||
|
||||
|
||||
/**
|
||||
@@ -67,7 +62,10 @@ ol.renderer.Layer.prototype.forEachFeatureAtCoordinate = goog.nullFunction;
|
||||
*/
|
||||
ol.renderer.Layer.prototype.forEachLayerAtPixel =
|
||||
function(pixel, frameState, callback, thisArg) {
|
||||
var coordinate = this.getMap().getCoordinateFromPixel(pixel);
|
||||
var coordinate = pixel.slice();
|
||||
ol.vec.Mat4.multVec2(
|
||||
frameState.pixelToCoordinateMatrix, coordinate, coordinate);
|
||||
|
||||
var hasFeature = this.forEachFeatureAtCoordinate(
|
||||
coordinate, frameState, goog.functions.TRUE, this);
|
||||
|
||||
@@ -87,6 +85,34 @@ ol.renderer.Layer.prototype.forEachLayerAtPixel =
|
||||
ol.renderer.Layer.prototype.hasFeatureAtCoordinate = goog.functions.FALSE;
|
||||
|
||||
|
||||
/**
|
||||
* Create a function that adds loaded tiles to the tile lookup.
|
||||
* @param {ol.source.Tile} source Tile source.
|
||||
* @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, tiles) {
|
||||
return (
|
||||
/**
|
||||
* @param {number} zoom Zoom level.
|
||||
* @param {ol.TileRange} tileRange Tile range.
|
||||
* @return {boolean} The tile range is fully loaded.
|
||||
*/
|
||||
function(zoom, tileRange) {
|
||||
return source.forEachLoadedTile(zoom, tileRange, function(tile) {
|
||||
if (!tiles[zoom]) {
|
||||
tiles[zoom] = {};
|
||||
}
|
||||
tiles[zoom][tile.tileCoord.toString()] = tile;
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @protected
|
||||
* @return {ol.layer.Layer} Layer.
|
||||
@@ -96,24 +122,6 @@ ol.renderer.Layer.prototype.getLayer = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @protected
|
||||
* @return {ol.Map} Map.
|
||||
*/
|
||||
ol.renderer.Layer.prototype.getMap = function() {
|
||||
return this.mapRenderer_.getMap();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @protected
|
||||
* @return {ol.renderer.Map} Map renderer.
|
||||
*/
|
||||
ol.renderer.Layer.prototype.getMapRenderer = function() {
|
||||
return this.mapRenderer_;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Handle changes in image state.
|
||||
* @param {goog.events.Event} event Image change event.
|
||||
@@ -161,7 +169,7 @@ ol.renderer.Layer.prototype.loadImage = function(image) {
|
||||
ol.renderer.Layer.prototype.renderIfReadyAndVisible = function() {
|
||||
var layer = this.getLayer();
|
||||
if (layer.getVisible() && layer.getSourceState() == ol.source.State.READY) {
|
||||
this.getMap().render();
|
||||
this.changed();
|
||||
}
|
||||
};
|
||||
|
||||
@@ -251,32 +259,6 @@ ol.renderer.Layer.prototype.updateUsedTiles =
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {function(ol.Tile): boolean} isLoadedFunction Function to
|
||||
* determine if the tile is loaded.
|
||||
* @param {ol.source.Tile} tileSource Tile source.
|
||||
* @param {number} pixelRatio Pixel ratio.
|
||||
* @param {ol.proj.Projection} projection Projection.
|
||||
* @protected
|
||||
* @return {function(number, number, number): ol.Tile} Returns a tile if it is
|
||||
* loaded.
|
||||
*/
|
||||
ol.renderer.Layer.prototype.createGetTileIfLoadedFunction =
|
||||
function(isLoadedFunction, tileSource, pixelRatio, projection) {
|
||||
return (
|
||||
/**
|
||||
* @param {number} z Z.
|
||||
* @param {number} x X.
|
||||
* @param {number} y Y.
|
||||
* @return {ol.Tile} Tile.
|
||||
*/
|
||||
function(z, x, y) {
|
||||
var tile = tileSource.getTile(z, x, y, pixelRatio, projection);
|
||||
return isLoadedFunction(tile) ? tile : null;
|
||||
});
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Coordinate} center Center.
|
||||
* @param {number} resolution Resolution.
|
||||
|
||||
@@ -4,6 +4,8 @@ goog.provide('ol.renderer.Map');
|
||||
goog.require('goog.Disposable');
|
||||
goog.require('goog.asserts');
|
||||
goog.require('goog.dispose');
|
||||
goog.require('goog.events');
|
||||
goog.require('goog.events.EventType');
|
||||
goog.require('goog.functions');
|
||||
goog.require('goog.object');
|
||||
goog.require('goog.vec.Mat4');
|
||||
@@ -56,6 +58,12 @@ ol.renderer.Map = function(container, map) {
|
||||
*/
|
||||
this.layerRenderers_ = {};
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Object.<string, goog.events.Key>}
|
||||
*/
|
||||
this.layerRendererListeners_ = {};
|
||||
|
||||
};
|
||||
goog.inherits(ol.renderer.Map, goog.Disposable);
|
||||
|
||||
@@ -84,9 +92,7 @@ ol.renderer.Map.prototype.calculateMatrices2D = function(frameState) {
|
||||
* @protected
|
||||
* @return {ol.renderer.Layer} layerRenderer Layer renderer.
|
||||
*/
|
||||
ol.renderer.Map.prototype.createLayerRenderer = function(layer) {
|
||||
return new ol.renderer.Layer(this, layer);
|
||||
};
|
||||
ol.renderer.Map.prototype.createLayerRenderer = goog.abstractMethod;
|
||||
|
||||
|
||||
/**
|
||||
@@ -256,6 +262,10 @@ ol.renderer.Map.prototype.getLayerRenderer = function(layer) {
|
||||
} else {
|
||||
var layerRenderer = this.createLayerRenderer(layer);
|
||||
this.layerRenderers_[layerKey] = layerRenderer;
|
||||
this.layerRendererListeners_[layerKey] = goog.events.listen(layerRenderer,
|
||||
goog.events.EventType.CHANGE, this.handleLayerRendererChange_,
|
||||
false, this);
|
||||
|
||||
return layerRenderer;
|
||||
}
|
||||
};
|
||||
@@ -295,6 +305,15 @@ ol.renderer.Map.prototype.getMap = function() {
|
||||
ol.renderer.Map.prototype.getType = goog.abstractMethod;
|
||||
|
||||
|
||||
/**
|
||||
* 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.
|
||||
@@ -304,6 +323,11 @@ ol.renderer.Map.prototype.removeLayerRendererByKey_ = function(layerKey) {
|
||||
goog.asserts.assert(layerKey in this.layerRenderers_);
|
||||
var layerRenderer = this.layerRenderers_[layerKey];
|
||||
delete this.layerRenderers_[layerKey];
|
||||
|
||||
goog.asserts.assert(layerKey in this.layerRendererListeners_);
|
||||
goog.events.unlistenByKey(this.layerRendererListeners_[layerKey]);
|
||||
delete this.layerRendererListeners_[layerKey];
|
||||
|
||||
return layerRenderer;
|
||||
};
|
||||
|
||||
|
||||
@@ -22,7 +22,7 @@ goog.require('ol.webgl.Context');
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.renderer.webgl.Layer}
|
||||
* @param {ol.renderer.Map} mapRenderer Map renderer.
|
||||
* @param {ol.renderer.webgl.Map} mapRenderer Map renderer.
|
||||
* @param {ol.layer.Image} imageLayer Tile layer.
|
||||
*/
|
||||
ol.renderer.webgl.ImageLayer = function(mapRenderer, imageLayer) {
|
||||
@@ -64,7 +64,7 @@ ol.renderer.webgl.ImageLayer.prototype.createTexture_ = function(image) {
|
||||
// http://learningwebgl.com/blog/?p=2101
|
||||
|
||||
var imageElement = image.getImage();
|
||||
var gl = this.getWebGLMapRenderer().getGL();
|
||||
var gl = this.mapRenderer.getGL();
|
||||
|
||||
return ol.webgl.Context.createTexture(
|
||||
gl, imageElement, goog.webgl.CLAMP_TO_EDGE, goog.webgl.CLAMP_TO_EDGE);
|
||||
@@ -100,7 +100,7 @@ ol.renderer.webgl.ImageLayer.prototype.forEachFeatureAtCoordinate =
|
||||
ol.renderer.webgl.ImageLayer.prototype.prepareFrame =
|
||||
function(frameState, layerState, context) {
|
||||
|
||||
var gl = this.getWebGLMapRenderer().getGL();
|
||||
var gl = this.mapRenderer.getGL();
|
||||
|
||||
var viewState = frameState.viewState;
|
||||
var viewCenter = viewState.center;
|
||||
@@ -155,7 +155,7 @@ ol.renderer.webgl.ImageLayer.prototype.prepareFrame =
|
||||
if (!goog.isNull(image)) {
|
||||
goog.asserts.assert(!goog.isNull(texture));
|
||||
|
||||
var canvas = this.getWebGLMapRenderer().getContext().getCanvas();
|
||||
var canvas = this.mapRenderer.getContext().getCanvas();
|
||||
|
||||
this.updateProjectionMatrix_(canvas.width, canvas.height,
|
||||
viewCenter, viewResolution, viewRotation, image.getExtent());
|
||||
@@ -235,7 +235,9 @@ ol.renderer.webgl.ImageLayer.prototype.forEachLayerAtPixel =
|
||||
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 = this.getMap().getCoordinateFromPixel(pixel);
|
||||
var coordinate = pixel.slice();
|
||||
ol.vec.Mat4.multVec2(
|
||||
frameState.pixelToCoordinateMatrix, coordinate, coordinate);
|
||||
var hasFeature = this.forEachFeatureAtCoordinate(
|
||||
coordinate, frameState, goog.functions.TRUE, this);
|
||||
|
||||
|
||||
@@ -18,12 +18,18 @@ goog.require('ol.webgl.Context');
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.renderer.Layer}
|
||||
* @param {ol.renderer.Map} mapRenderer Map renderer.
|
||||
* @param {ol.renderer.webgl.Map} mapRenderer Map renderer.
|
||||
* @param {ol.layer.Layer} layer Layer.
|
||||
*/
|
||||
ol.renderer.webgl.Layer = function(mapRenderer, layer) {
|
||||
|
||||
goog.base(this, mapRenderer, layer);
|
||||
goog.base(this, layer);
|
||||
|
||||
/**
|
||||
* @protected
|
||||
* @type {ol.renderer.webgl.Map}
|
||||
*/
|
||||
this.mapRenderer = mapRenderer;
|
||||
|
||||
/**
|
||||
* @private
|
||||
@@ -96,8 +102,7 @@ goog.inherits(ol.renderer.webgl.Layer, ol.renderer.Layer);
|
||||
ol.renderer.webgl.Layer.prototype.bindFramebuffer =
|
||||
function(frameState, framebufferDimension) {
|
||||
|
||||
var mapRenderer = this.getWebGLMapRenderer();
|
||||
var gl = mapRenderer.getGL();
|
||||
var gl = this.mapRenderer.getGL();
|
||||
|
||||
if (!goog.isDef(this.framebufferDimension) ||
|
||||
this.framebufferDimension != framebufferDimension) {
|
||||
@@ -248,15 +253,6 @@ ol.renderer.webgl.Layer.prototype.dispatchComposeEvent_ =
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @protected
|
||||
* @return {ol.renderer.webgl.Map} MapRenderer.
|
||||
*/
|
||||
ol.renderer.webgl.Layer.prototype.getWebGLMapRenderer = function() {
|
||||
return /** @type {ol.renderer.webgl.Map} */ (this.getMapRenderer());
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {!goog.vec.Mat4.Number} Matrix.
|
||||
*/
|
||||
|
||||
@@ -25,7 +25,7 @@ goog.require('ol.webgl.Buffer');
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.renderer.webgl.Layer}
|
||||
* @param {ol.renderer.Map} mapRenderer Map renderer.
|
||||
* @param {ol.renderer.webgl.Map} mapRenderer Map renderer.
|
||||
* @param {ol.layer.Tile} tileLayer Tile layer.
|
||||
*/
|
||||
ol.renderer.webgl.TileLayer = function(mapRenderer, tileLayer) {
|
||||
@@ -88,13 +88,47 @@ goog.inherits(ol.renderer.webgl.TileLayer, ol.renderer.webgl.Layer);
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.webgl.TileLayer.prototype.disposeInternal = function() {
|
||||
var mapRenderer = this.getWebGLMapRenderer();
|
||||
var context = mapRenderer.getContext();
|
||||
var context = this.mapRenderer.getContext();
|
||||
context.deleteBuffer(this.renderArrayBuffer_);
|
||||
goog.base(this, 'disposeInternal');
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Create a function that adds loaded tiles to the tile lookup.
|
||||
* @param {ol.source.Tile} source Tile source.
|
||||
* @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.webgl.TileLayer.prototype.createLoadedTileFinder =
|
||||
function(source, 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) {
|
||||
return source.forEachLoadedTile(zoom, tileRange, function(tile) {
|
||||
var loaded = mapRenderer.isTileTextureLoaded(tile);
|
||||
if (loaded) {
|
||||
if (!tiles[zoom]) {
|
||||
tiles[zoom] = {};
|
||||
}
|
||||
tiles[zoom][tile.tileCoord.toString()] = tile;
|
||||
}
|
||||
return loaded;
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
@@ -110,7 +144,7 @@ ol.renderer.webgl.TileLayer.prototype.handleWebGLContextLost = function() {
|
||||
ol.renderer.webgl.TileLayer.prototype.prepareFrame =
|
||||
function(frameState, layerState, context) {
|
||||
|
||||
var mapRenderer = this.getWebGLMapRenderer();
|
||||
var mapRenderer = this.mapRenderer;
|
||||
var gl = context.getGL();
|
||||
|
||||
var viewState = frameState.viewState;
|
||||
@@ -191,12 +225,8 @@ ol.renderer.webgl.TileLayer.prototype.prepareFrame =
|
||||
var tilesToDrawByZ = {};
|
||||
tilesToDrawByZ[z] = {};
|
||||
|
||||
var getTileIfLoaded = this.createGetTileIfLoadedFunction(function(tile) {
|
||||
return !goog.isNull(tile) && tile.getState() == ol.TileState.LOADED &&
|
||||
mapRenderer.isTileTextureLoaded(tile);
|
||||
}, tileSource, pixelRatio, projection);
|
||||
var findLoadedTiles = goog.bind(tileSource.findLoadedTiles, tileSource,
|
||||
tilesToDrawByZ, getTileIfLoaded);
|
||||
var findLoadedTiles = this.createLoadedTileFinder(
|
||||
tileSource, tilesToDrawByZ);
|
||||
|
||||
var useInterimTilesOnError = tileLayer.getUseInterimTilesOnError();
|
||||
var allTilesLoaded = true;
|
||||
@@ -337,11 +367,10 @@ ol.renderer.webgl.TileLayer.prototype.forEachLayerAtPixel =
|
||||
if (goog.isNull(this.framebuffer)) {
|
||||
return undefined;
|
||||
}
|
||||
var mapSize = this.getMap().getSize();
|
||||
|
||||
var pixelOnMapScaled = [
|
||||
pixel[0] / mapSize[0],
|
||||
(mapSize[1] - pixel[1]) / mapSize[1]];
|
||||
pixel[0] / frameState.size[0],
|
||||
(frameState.size[1] - pixel[1]) / frameState.size[1]];
|
||||
|
||||
var pixelOnFrameBufferScaled = [0, 0];
|
||||
ol.vec.Mat4.multVec2(
|
||||
@@ -350,7 +379,7 @@ ol.renderer.webgl.TileLayer.prototype.forEachLayerAtPixel =
|
||||
pixelOnFrameBufferScaled[0] * this.framebufferDimension,
|
||||
pixelOnFrameBufferScaled[1] * this.framebufferDimension];
|
||||
|
||||
var gl = this.getWebGLMapRenderer().getContext().getGL();
|
||||
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,
|
||||
|
||||
@@ -9,13 +9,14 @@ goog.require('ol.layer.Vector');
|
||||
goog.require('ol.render.webgl.ReplayGroup');
|
||||
goog.require('ol.renderer.vector');
|
||||
goog.require('ol.renderer.webgl.Layer');
|
||||
goog.require('ol.vec.Mat4');
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.renderer.webgl.Layer}
|
||||
* @param {ol.renderer.Map} mapRenderer Map renderer.
|
||||
* @param {ol.renderer.webgl.Map} mapRenderer Map renderer.
|
||||
* @param {ol.layer.Vector} vectorLayer Vector layer.
|
||||
*/
|
||||
ol.renderer.webgl.VectorLayer = function(mapRenderer, vectorLayer) {
|
||||
@@ -94,8 +95,7 @@ ol.renderer.webgl.VectorLayer.prototype.composeFrame =
|
||||
ol.renderer.webgl.VectorLayer.prototype.disposeInternal = function() {
|
||||
var replayGroup = this.replayGroup_;
|
||||
if (!goog.isNull(replayGroup)) {
|
||||
var mapRenderer = this.getWebGLMapRenderer();
|
||||
var context = mapRenderer.getContext();
|
||||
var context = this.mapRenderer.getContext();
|
||||
replayGroup.getDeleteResourcesFunction(context)();
|
||||
this.replayGroup_ = null;
|
||||
}
|
||||
@@ -111,8 +111,7 @@ ol.renderer.webgl.VectorLayer.prototype.forEachFeatureAtCoordinate =
|
||||
if (goog.isNull(this.replayGroup_) || goog.isNull(this.layerState_)) {
|
||||
return undefined;
|
||||
} else {
|
||||
var mapRenderer = this.getWebGLMapRenderer();
|
||||
var context = mapRenderer.getContext();
|
||||
var context = this.mapRenderer.getContext();
|
||||
var viewState = frameState.viewState;
|
||||
var layer = this.getLayer();
|
||||
var layerState = this.layerState_;
|
||||
@@ -147,8 +146,7 @@ ol.renderer.webgl.VectorLayer.prototype.hasFeatureAtCoordinate =
|
||||
if (goog.isNull(this.replayGroup_) || goog.isNull(this.layerState_)) {
|
||||
return false;
|
||||
} else {
|
||||
var mapRenderer = this.getWebGLMapRenderer();
|
||||
var context = mapRenderer.getContext();
|
||||
var context = this.mapRenderer.getContext();
|
||||
var viewState = frameState.viewState;
|
||||
var layerState = this.layerState_;
|
||||
return this.replayGroup_.hasFeatureAtCoordinate(coordinate,
|
||||
@@ -165,7 +163,9 @@ ol.renderer.webgl.VectorLayer.prototype.hasFeatureAtCoordinate =
|
||||
*/
|
||||
ol.renderer.webgl.VectorLayer.prototype.forEachLayerAtPixel =
|
||||
function(pixel, frameState, callback, thisArg) {
|
||||
var coordinate = this.getMap().getCoordinateFromPixel(pixel);
|
||||
var coordinate = pixel.slice();
|
||||
ol.vec.Mat4.multVec2(
|
||||
frameState.pixelToCoordinateMatrix, coordinate, coordinate);
|
||||
var hasFeature = this.hasFeatureAtCoordinate(coordinate, frameState);
|
||||
|
||||
if (hasFeature) {
|
||||
|
||||
@@ -98,6 +98,9 @@ ol.source.BingMaps.prototype.handleImageryMetadataResponse =
|
||||
}
|
||||
|
||||
var brandLogoUri = response.brandLogoUri;
|
||||
if (ol.IS_HTTPS && 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];
|
||||
goog.asserts.assert(resource.imageWidth == resource.imageHeight);
|
||||
|
||||
@@ -59,6 +59,16 @@ ol.source.Cluster = function(options) {
|
||||
goog.inherits(ol.source.Cluster, ol.source.Vector);
|
||||
|
||||
|
||||
/**
|
||||
* Get a reference to the wrapped source.
|
||||
* @return {ol.source.Vector} Source.
|
||||
* @api
|
||||
*/
|
||||
ol.source.Cluster.prototype.getSource = function() {
|
||||
return this.source_;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
|
||||
@@ -178,6 +178,7 @@ ol.source.ImageVector.prototype.forEachFeatureAtCoordinate = function(
|
||||
|
||||
|
||||
/**
|
||||
* Get a reference to the wrapped source.
|
||||
* @return {ol.source.Vector} Source.
|
||||
* @api
|
||||
*/
|
||||
|
||||
@@ -24,10 +24,17 @@ ol.source.MapQuest = function(opt_options) {
|
||||
|
||||
var layerConfig = ol.source.MapQuestConfig[options.layer];
|
||||
|
||||
/**
|
||||
* Layer. Possible values are `osm`, `sat`, and `hyb`.
|
||||
* @type {string}
|
||||
* @private
|
||||
*/
|
||||
this.layer_ = options.layer;
|
||||
|
||||
var protocol = ol.IS_HTTPS ? 'https:' : 'http:';
|
||||
var url = goog.isDef(options.url) ? options.url :
|
||||
protocol + '//otile{1-4}-s.mqcdn.com/tiles/1.0.0/' +
|
||||
options.layer + '/{z}/{x}/{y}.jpg';
|
||||
this.layer_ + '/{z}/{x}/{y}.jpg';
|
||||
|
||||
goog.base(this, {
|
||||
attributions: layerConfig.attributions,
|
||||
@@ -81,3 +88,12 @@ ol.source.MapQuestConfig = {
|
||||
]
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {string} Layer.
|
||||
* @api
|
||||
*/
|
||||
ol.source.MapQuest.prototype.getLayer = function() {
|
||||
return this.layer_;
|
||||
};
|
||||
|
||||
@@ -3,7 +3,7 @@ goog.provide('ol.source.State');
|
||||
|
||||
goog.require('goog.events.EventType');
|
||||
goog.require('ol.Attribution');
|
||||
goog.require('ol.Observable');
|
||||
goog.require('ol.Object');
|
||||
goog.require('ol.proj');
|
||||
|
||||
|
||||
@@ -37,7 +37,7 @@ ol.source.SourceOptions;
|
||||
* Base class for {@link ol.layer.Layer} sources.
|
||||
*
|
||||
* @constructor
|
||||
* @extends {ol.Observable}
|
||||
* @extends {ol.Object}
|
||||
* @fires change Triggered when the state of the source changes.
|
||||
* @param {ol.source.SourceOptions} options Source options.
|
||||
* @api stable
|
||||
@@ -73,7 +73,7 @@ ol.source.Source = function(options) {
|
||||
options.state : ol.source.State.READY;
|
||||
|
||||
};
|
||||
goog.inherits(ol.source.Source, ol.Observable);
|
||||
goog.inherits(ol.source.Source, ol.Object);
|
||||
|
||||
|
||||
/**
|
||||
|
||||
218
src/ol/source/tilearcgisrestsource.js
Normal file
218
src/ol/source/tilearcgisrestsource.js
Normal file
@@ -0,0 +1,218 @@
|
||||
goog.provide('ol.source.TileArcGISRest');
|
||||
|
||||
goog.require('goog.array');
|
||||
goog.require('goog.asserts');
|
||||
goog.require('goog.math');
|
||||
goog.require('goog.object');
|
||||
goog.require('goog.string');
|
||||
goog.require('goog.uri.utils');
|
||||
goog.require('ol');
|
||||
goog.require('ol.TileCoord');
|
||||
goog.require('ol.TileUrlFunction');
|
||||
goog.require('ol.extent');
|
||||
goog.require('ol.proj');
|
||||
goog.require('ol.source.TileImage');
|
||||
goog.require('ol.tilecoord');
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @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 = goog.isDef(opt_options) ? opt_options : {};
|
||||
|
||||
var params = goog.isDef(options.params) ? options.params : {};
|
||||
|
||||
goog.base(this, {
|
||||
attributions: options.attributions,
|
||||
logo: options.logo,
|
||||
projection: options.projection,
|
||||
tileGrid: options.tileGrid,
|
||||
tileLoadFunction: options.tileLoadFunction,
|
||||
tileUrlFunction: goog.bind(this.tileUrlFunction_, this)
|
||||
});
|
||||
|
||||
var urls = options.urls;
|
||||
if (!goog.isDef(urls) && goog.isDef(options.url)) {
|
||||
urls = ol.TileUrlFunction.expandUrl(options.url);
|
||||
}
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {!Array.<string>}
|
||||
*/
|
||||
this.urls_ = goog.isDefAndNotNull(urls) ? urls : [];
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Object}
|
||||
*/
|
||||
this.params_ = params;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.Extent}
|
||||
*/
|
||||
this.tmpExtent_ = ol.extent.createEmpty();
|
||||
|
||||
};
|
||||
goog.inherits(ol.source.TileArcGISRest, ol.source.TileImage);
|
||||
|
||||
|
||||
/**
|
||||
* 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 {number} 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 (goog.array.isEmpty(urls)) {
|
||||
return undefined;
|
||||
}
|
||||
|
||||
// ArcGIS Server only wants the numeric portion of the projection ID.
|
||||
var srid = projection.getCode().split(':').pop();
|
||||
|
||||
params['SIZE'] = tileSize + ',' + tileSize;
|
||||
params['BBOX'] = tileExtent.join(',');
|
||||
params['BBOXSR'] = srid;
|
||||
params['IMAGESR'] = srid;
|
||||
|
||||
var url;
|
||||
if (urls.length == 1) {
|
||||
url = urls[0];
|
||||
} else {
|
||||
var index = goog.math.modulo(ol.tilecoord.hash(tileCoord), urls.length);
|
||||
url = urls[index];
|
||||
}
|
||||
|
||||
if (!goog.string.endsWith(url, '/')) {
|
||||
url = url + '/';
|
||||
}
|
||||
|
||||
// If a MapServer, use export. If an ImageServer, use exportImage.
|
||||
if (goog.string.endsWith(url, 'MapServer/')) {
|
||||
url = url + 'export';
|
||||
}
|
||||
else if (goog.string.endsWith(url, 'ImageServer/')) {
|
||||
url = url + 'exportImage';
|
||||
}
|
||||
else {
|
||||
goog.asserts.fail('Unknown Rest Service', url);
|
||||
}
|
||||
|
||||
return goog.uri.utils.appendParamsFromMap(url, params);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Return the URLs used for this ArcGIS source.
|
||||
* @return {!Array.<string>} URLs.
|
||||
* @api stable
|
||||
*/
|
||||
ol.source.TileArcGISRest.prototype.getUrls = function() {
|
||||
return this.urls_;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {string|undefined} url URL.
|
||||
* @api stable
|
||||
*/
|
||||
ol.source.TileArcGISRest.prototype.setUrl = function(url) {
|
||||
var urls = goog.isDef(url) ? ol.TileUrlFunction.expandUrl(url) : null;
|
||||
this.setUrls(urls);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {Array.<string>|undefined} urls URLs.
|
||||
* @api stable
|
||||
*/
|
||||
ol.source.TileArcGISRest.prototype.setUrls = function(urls) {
|
||||
this.urls_ = goog.isDefAndNotNull(urls) ? urls : [];
|
||||
this.changed();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.TileCoord} tileCoord Tile coordinate.
|
||||
* @param {number} pixelRatio Pixel ratio.
|
||||
* @param {ol.proj.Projection} projection Projection.
|
||||
* @return {string|undefined} Tile URL.
|
||||
* @private
|
||||
*/
|
||||
ol.source.TileArcGISRest.prototype.tileUrlFunction_ =
|
||||
function(tileCoord, pixelRatio, projection) {
|
||||
|
||||
var tileGrid = this.getTileGrid();
|
||||
if (goog.isNull(tileGrid)) {
|
||||
tileGrid = this.getTileGridForProjection(projection);
|
||||
}
|
||||
|
||||
if (tileGrid.getResolutions().length <= tileCoord[0]) {
|
||||
return undefined;
|
||||
}
|
||||
|
||||
var tileExtent = tileGrid.getTileCoordExtent(
|
||||
tileCoord, this.tmpExtent_);
|
||||
var tileSize = tileGrid.getTileSize(tileCoord[0]);
|
||||
|
||||
if (pixelRatio != 1) {
|
||||
tileSize = (tileSize * pixelRatio + 0.5) | 0;
|
||||
}
|
||||
|
||||
// Apply default params and override with user specified values.
|
||||
var baseParams = {
|
||||
'F': 'image',
|
||||
'FORMAT': 'PNG32',
|
||||
'TRANSPARENT': true
|
||||
};
|
||||
goog.object.extend(baseParams, this.params_);
|
||||
|
||||
return this.getRequestUrl_(tileCoord, tileSize, tileExtent,
|
||||
pixelRatio, projection, baseParams);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Update the user-provided params.
|
||||
* @param {Object} params Params.
|
||||
* @api stable
|
||||
*/
|
||||
ol.source.TileArcGISRest.prototype.updateParams = function(params) {
|
||||
goog.object.extend(this.params_, params);
|
||||
this.changed();
|
||||
};
|
||||
@@ -1,7 +1,6 @@
|
||||
goog.provide('ol.source.TileDebug');
|
||||
|
||||
goog.require('ol.Tile');
|
||||
goog.require('ol.TileCache');
|
||||
goog.require('ol.TileCoord');
|
||||
goog.require('ol.TileState');
|
||||
goog.require('ol.dom');
|
||||
@@ -89,42 +88,20 @@ ol.source.TileDebug = function(options) {
|
||||
tileGrid: options.tileGrid
|
||||
});
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.TileCache}
|
||||
*/
|
||||
this.tileCache_ = new ol.TileCache();
|
||||
|
||||
};
|
||||
goog.inherits(ol.source.TileDebug, ol.source.Tile);
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.source.TileDebug.prototype.canExpireCache = function() {
|
||||
return this.tileCache_.canExpireCache();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.source.TileDebug.prototype.expireCache = function(usedTiles) {
|
||||
this.tileCache_.expireCache(usedTiles);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.source.TileDebug.prototype.getTile = function(z, x, y) {
|
||||
var tileCoordKey = this.getKeyZXY(z, x, y);
|
||||
if (this.tileCache_.containsKey(tileCoordKey)) {
|
||||
return /** @type {!ol.DebugTile_} */ (this.tileCache_.get(tileCoordKey));
|
||||
if (this.tileCache.containsKey(tileCoordKey)) {
|
||||
return /** @type {!ol.DebugTile_} */ (this.tileCache.get(tileCoordKey));
|
||||
} else {
|
||||
var tile = new ol.DebugTile_([z, x, y], this.tileGrid);
|
||||
this.tileCache_.set(tileCoordKey, tile);
|
||||
this.tileCache.set(tileCoordKey, tile);
|
||||
return tile;
|
||||
}
|
||||
};
|
||||
|
||||
@@ -1,8 +1,9 @@
|
||||
goog.provide('ol.source.TileImage');
|
||||
|
||||
goog.require('goog.asserts');
|
||||
goog.require('goog.events');
|
||||
goog.require('goog.events.EventType');
|
||||
goog.require('ol.ImageTile');
|
||||
goog.require('ol.TileCache');
|
||||
goog.require('ol.TileCoord');
|
||||
goog.require('ol.TileLoadFunctionType');
|
||||
goog.require('ol.TileState');
|
||||
@@ -17,6 +18,7 @@ goog.require('ol.source.Tile');
|
||||
* Base class for sources providing images divided into a tile grid.
|
||||
*
|
||||
* @constructor
|
||||
* @fires ol.source.TileEvent
|
||||
* @extends {ol.source.Tile}
|
||||
* @param {olx.source.TileImageOptions} options Image tile options.
|
||||
* @api
|
||||
@@ -50,12 +52,6 @@ ol.source.TileImage = function(options) {
|
||||
this.crossOrigin =
|
||||
goog.isDef(options.crossOrigin) ? options.crossOrigin : null;
|
||||
|
||||
/**
|
||||
* @protected
|
||||
* @type {ol.TileCache}
|
||||
*/
|
||||
this.tileCache = new ol.TileCache();
|
||||
|
||||
/**
|
||||
* @protected
|
||||
* @type {ol.TileLoadFunctionType}
|
||||
@@ -84,22 +80,6 @@ ol.source.TileImage.defaultTileLoadFunction = function(imageTile, src) {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.source.TileImage.prototype.canExpireCache = function() {
|
||||
return this.tileCache.canExpireCache();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.source.TileImage.prototype.expireCache = function(usedTiles) {
|
||||
this.tileCache.expireCache(usedTiles);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
@@ -118,6 +98,9 @@ ol.source.TileImage.prototype.getTile =
|
||||
goog.isDef(tileUrl) ? tileUrl : '',
|
||||
this.crossOrigin,
|
||||
this.tileLoadFunction);
|
||||
goog.events.listen(tile, goog.events.EventType.CHANGE,
|
||||
this.handleTileChange_, false, this);
|
||||
|
||||
this.tileCache.set(tileCoordKey, tile);
|
||||
return tile;
|
||||
}
|
||||
@@ -142,6 +125,30 @@ ol.source.TileImage.prototype.getTileUrlFunction = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Handle tile change events.
|
||||
* @param {goog.events.Event} event Event.
|
||||
* @private
|
||||
*/
|
||||
ol.source.TileImage.prototype.handleTileChange_ = function(event) {
|
||||
var tile = /** @type {ol.Tile} */ (event.target);
|
||||
switch (tile.getState()) {
|
||||
case ol.TileState.LOADING:
|
||||
this.dispatchEvent(
|
||||
new ol.source.TileEvent(ol.source.TileEventType.TILELOADSTART, tile));
|
||||
break;
|
||||
case ol.TileState.LOADED:
|
||||
this.dispatchEvent(
|
||||
new ol.source.TileEvent(ol.source.TileEventType.TILELOADEND, tile));
|
||||
break;
|
||||
case ol.TileState.ERROR:
|
||||
this.dispatchEvent(
|
||||
new ol.source.TileEvent(ol.source.TileEventType.TILELOADERROR, tile));
|
||||
break;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.TileLoadFunctionType} tileLoadFunction Tile load function.
|
||||
* @api
|
||||
|
||||
@@ -33,6 +33,7 @@ goog.require('ol.tilegrid.XYZ');
|
||||
ol.source.TileJSON = function(options) {
|
||||
|
||||
goog.base(this, {
|
||||
attributions: options.attributions,
|
||||
crossOrigin: options.crossOrigin,
|
||||
projection: ol.proj.get('EPSG:3857'),
|
||||
state: ol.source.State.LOADING,
|
||||
@@ -87,7 +88,8 @@ ol.source.TileJSON.prototype.handleTileJSONResponse = function(tileJSON) {
|
||||
}),
|
||||
ol.TileUrlFunction.createFromTemplates(tileJSON.tiles));
|
||||
|
||||
if (goog.isDef(tileJSON.attribution)) {
|
||||
if (goog.isDef(tileJSON.attribution) &&
|
||||
goog.isNull(this.getAttributions())) {
|
||||
var attributionExtent = goog.isDef(extent) ?
|
||||
extent : epsg4326Projection.getExtent();
|
||||
/** @type {Object.<string, Array.<ol.TileRange>>} */
|
||||
|
||||
@@ -1,10 +1,12 @@
|
||||
goog.provide('ol.source.Tile');
|
||||
goog.provide('ol.source.TileOptions');
|
||||
|
||||
goog.require('goog.functions');
|
||||
goog.require('goog.events.Event');
|
||||
goog.require('ol.Attribution');
|
||||
goog.require('ol.Extent');
|
||||
goog.require('ol.TileCache');
|
||||
goog.require('ol.TileRange');
|
||||
goog.require('ol.TileState');
|
||||
goog.require('ol.source.Source');
|
||||
goog.require('ol.tilecoord');
|
||||
goog.require('ol.tilegrid.TileGrid');
|
||||
@@ -64,6 +66,12 @@ ol.source.Tile = function(options) {
|
||||
*/
|
||||
this.tileGrid = goog.isDef(options.tileGrid) ? options.tileGrid : null;
|
||||
|
||||
/**
|
||||
* @protected
|
||||
* @type {ol.TileCache}
|
||||
*/
|
||||
this.tileCache = new ol.TileCache();
|
||||
|
||||
};
|
||||
goog.inherits(ol.source.Tile, ol.source.Source);
|
||||
|
||||
@@ -71,51 +79,47 @@ goog.inherits(ol.source.Tile, ol.source.Source);
|
||||
/**
|
||||
* @return {boolean} Can expire cache.
|
||||
*/
|
||||
ol.source.Tile.prototype.canExpireCache = goog.functions.FALSE;
|
||||
ol.source.Tile.prototype.canExpireCache = function() {
|
||||
return this.tileCache.canExpireCache();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {Object.<string, ol.TileRange>} usedTiles Used tiles.
|
||||
*/
|
||||
ol.source.Tile.prototype.expireCache = goog.abstractMethod;
|
||||
ol.source.Tile.prototype.expireCache = function(usedTiles) {
|
||||
this.tileCache.expireCache(usedTiles);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Look for loaded tiles over a given tile range and zoom level. Adds
|
||||
* properties to the provided lookup representing key/tile pairs for already
|
||||
* loaded tiles.
|
||||
*
|
||||
* @param {Object.<number, Object.<string, ol.Tile>>} loadedTilesByZ A lookup of
|
||||
* loaded tiles by zoom level.
|
||||
* @param {function(number, number, number): ol.Tile} getTileIfLoaded A function
|
||||
* that returns the tile only if it is fully loaded.
|
||||
* @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.findLoadedTiles = function(loadedTilesByZ,
|
||||
getTileIfLoaded, z, tileRange) {
|
||||
// FIXME this could be more efficient about filling partial holes
|
||||
var fullyCovered = true;
|
||||
var tile, tileCoordKey, x, y;
|
||||
for (x = tileRange.minX; x <= tileRange.maxX; ++x) {
|
||||
for (y = tileRange.minY; y <= tileRange.maxY; ++y) {
|
||||
ol.source.Tile.prototype.forEachLoadedTile = function(z, tileRange, callback) {
|
||||
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 = this.getKeyZXY(z, x, y);
|
||||
if (loadedTilesByZ[z] && loadedTilesByZ[z][tileCoordKey]) {
|
||||
continue;
|
||||
}
|
||||
tile = getTileIfLoaded(z, x, y);
|
||||
if (!goog.isNull(tile)) {
|
||||
if (!loadedTilesByZ[z]) {
|
||||
loadedTilesByZ[z] = {};
|
||||
loaded = false;
|
||||
if (this.tileCache.containsKey(tileCoordKey)) {
|
||||
tile = /** @type {!ol.Tile} */ (this.tileCache.get(tileCoordKey));
|
||||
loaded = tile.getState() === ol.TileState.LOADED;
|
||||
if (loaded) {
|
||||
loaded = (callback(tile) !== false);
|
||||
}
|
||||
loadedTilesByZ[z][tileCoordKey] = tile;
|
||||
} else {
|
||||
fullyCovered = false;
|
||||
}
|
||||
if (!loaded) {
|
||||
covered = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
return fullyCovered;
|
||||
return covered;
|
||||
};
|
||||
|
||||
|
||||
@@ -206,3 +210,59 @@ ol.source.Tile.prototype.getTilePixelSize =
|
||||
* @param {number} y Tile coordinate y.
|
||||
*/
|
||||
ol.source.Tile.prototype.useTile = goog.nullFunction;
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @classdesc
|
||||
* Events emitted by {@link ol.source.Tile} instances are instances of this
|
||||
* type.
|
||||
*
|
||||
* @constructor
|
||||
* @extends {goog.events.Event}
|
||||
* @implements {oli.source.TileEvent}
|
||||
* @param {string} type Type.
|
||||
* @param {ol.Tile} tile The tile.
|
||||
*/
|
||||
ol.source.TileEvent = function(type, tile) {
|
||||
|
||||
goog.base(this, type);
|
||||
|
||||
/**
|
||||
* The tile related to the event.
|
||||
* @type {ol.Tile}
|
||||
* @api
|
||||
*/
|
||||
this.tile = tile;
|
||||
|
||||
};
|
||||
goog.inherits(ol.source.TileEvent, goog.events.Event);
|
||||
|
||||
|
||||
/**
|
||||
* @enum {string}
|
||||
*/
|
||||
ol.source.TileEventType = {
|
||||
|
||||
/**
|
||||
* Triggered when a tile starts loading.
|
||||
* @event ol.source.TileEvent#tileloadstart
|
||||
* @api
|
||||
*/
|
||||
TILELOADSTART: 'tileloadstart',
|
||||
|
||||
/**
|
||||
* Triggered when a tile finishes loading.
|
||||
* @event ol.source.TileEvent#tileloadend
|
||||
* @api
|
||||
*/
|
||||
TILELOADEND: 'tileloadend',
|
||||
|
||||
/**
|
||||
* Triggered if tile loading results in an error.
|
||||
* @event ol.source.TileEvent#tileloaderror
|
||||
* @api
|
||||
*/
|
||||
TILELOADERROR: 'tileloaderror'
|
||||
|
||||
};
|
||||
|
||||
@@ -7,7 +7,6 @@ goog.require('goog.events.EventType');
|
||||
goog.require('goog.net.Jsonp');
|
||||
goog.require('ol.Attribution');
|
||||
goog.require('ol.Tile');
|
||||
goog.require('ol.TileCache');
|
||||
goog.require('ol.TileState');
|
||||
goog.require('ol.TileUrlFunction');
|
||||
goog.require('ol.extent');
|
||||
@@ -46,12 +45,6 @@ ol.source.TileUTFGrid = function(options) {
|
||||
*/
|
||||
this.tileUrlFunction_ = ol.TileUrlFunction.nullTileUrlFunction;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {!ol.TileCache}
|
||||
*/
|
||||
this.tileCache_ = new ol.TileCache();
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {string|undefined}
|
||||
@@ -64,22 +57,6 @@ ol.source.TileUTFGrid = function(options) {
|
||||
goog.inherits(ol.source.TileUTFGrid, ol.source.Tile);
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.source.TileUTFGrid.prototype.canExpireCache = function() {
|
||||
return this.tileCache_.canExpireCache();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.source.TileUTFGrid.prototype.expireCache = function(usedTiles) {
|
||||
this.tileCache_.expireCache(usedTiles);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {string|undefined} The template from TileJSON.
|
||||
* @api
|
||||
@@ -195,8 +172,8 @@ ol.source.TileUTFGrid.prototype.handleTileJSONResponse = function(tileJSON) {
|
||||
ol.source.TileUTFGrid.prototype.getTile =
|
||||
function(z, x, y, pixelRatio, projection) {
|
||||
var tileCoordKey = this.getKeyZXY(z, x, y);
|
||||
if (this.tileCache_.containsKey(tileCoordKey)) {
|
||||
return /** @type {!ol.Tile} */ (this.tileCache_.get(tileCoordKey));
|
||||
if (this.tileCache.containsKey(tileCoordKey)) {
|
||||
return /** @type {!ol.Tile} */ (this.tileCache.get(tileCoordKey));
|
||||
} else {
|
||||
goog.asserts.assert(projection);
|
||||
var tileCoord = [z, x, y];
|
||||
@@ -207,7 +184,7 @@ ol.source.TileUTFGrid.prototype.getTile =
|
||||
goog.isDef(tileUrl) ? tileUrl : '',
|
||||
this.tileGrid.getTileCoordExtent(tileCoord),
|
||||
this.preemptive_);
|
||||
this.tileCache_.set(tileCoordKey, tile);
|
||||
this.tileCache.set(tileCoordKey, tile);
|
||||
return tile;
|
||||
}
|
||||
};
|
||||
@@ -218,8 +195,8 @@ ol.source.TileUTFGrid.prototype.getTile =
|
||||
*/
|
||||
ol.source.TileUTFGrid.prototype.useTile = function(z, x, y) {
|
||||
var tileCoordKey = this.getKeyZXY(z, x, y);
|
||||
if (this.tileCache_.containsKey(tileCoordKey)) {
|
||||
this.tileCache_.get(tileCoordKey);
|
||||
if (this.tileCache.containsKey(tileCoordKey)) {
|
||||
this.tileCache.get(tileCoordKey);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -5,6 +5,7 @@ goog.require('goog.array');
|
||||
goog.require('goog.asserts');
|
||||
goog.require('goog.math');
|
||||
goog.require('goog.object');
|
||||
goog.require('goog.string');
|
||||
goog.require('goog.uri.utils');
|
||||
goog.require('ol.TileUrlFunction');
|
||||
goog.require('ol.TileUrlFunctionType');
|
||||
@@ -40,8 +41,17 @@ ol.source.WMTS = function(options) {
|
||||
|
||||
// TODO: add support for TileMatrixLimits
|
||||
|
||||
var version = goog.isDef(options.version) ? options.version : '1.0.0';
|
||||
var format = goog.isDef(options.format) ? options.format : 'image/jpeg';
|
||||
/**
|
||||
* @private
|
||||
* @type {string}
|
||||
*/
|
||||
this.version_ = goog.isDef(options.version) ? options.version : '1.0.0';
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {string}
|
||||
*/
|
||||
this.format_ = goog.isDef(options.format) ? options.format : 'image/jpeg';
|
||||
|
||||
/**
|
||||
* @private
|
||||
@@ -56,6 +66,24 @@ ol.source.WMTS = function(options) {
|
||||
this.coordKeyPrefix_ = '';
|
||||
this.resetCoordKeyPrefix_();
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {string}
|
||||
*/
|
||||
this.layer_ = options.layer;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {string}
|
||||
*/
|
||||
this.matrixSet_ = options.matrixSet;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {string}
|
||||
*/
|
||||
this.style_ = options.style;
|
||||
|
||||
// FIXME: should we guess this requestEncoding from options.url(s)
|
||||
// structure? that would mean KVP only if a template is not provided.
|
||||
var requestEncoding = goog.isDef(options.requestEncoding) ?
|
||||
@@ -66,18 +94,20 @@ ol.source.WMTS = function(options) {
|
||||
// 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': options.layer,
|
||||
'Style': options.style,
|
||||
'TileMatrixSet': options.matrixSet
|
||||
'layer': this.layer_,
|
||||
'style': this.style_,
|
||||
'tilematrixset': this.matrixSet_
|
||||
};
|
||||
|
||||
if (requestEncoding == ol.source.WMTSRequestEncoding.KVP) {
|
||||
goog.object.extend(context, {
|
||||
'Service': 'WMTS',
|
||||
'Request': 'GetTile',
|
||||
'Version': version,
|
||||
'Format': format
|
||||
'Version': this.version_,
|
||||
'Format': this.format_
|
||||
});
|
||||
}
|
||||
|
||||
@@ -96,7 +126,7 @@ ol.source.WMTS = function(options) {
|
||||
template = (requestEncoding == ol.source.WMTSRequestEncoding.KVP) ?
|
||||
goog.uri.utils.appendParamsFromMap(template, context) :
|
||||
template.replace(/\{(\w+?)\}/g, function(m, p) {
|
||||
return (p in context) ? context[p] : m;
|
||||
return (p.toLowerCase() in context) ? context[p.toLowerCase()] : m;
|
||||
});
|
||||
|
||||
return (
|
||||
@@ -204,6 +234,15 @@ ol.source.WMTS.prototype.getDimensions = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {string} Format.
|
||||
* @api
|
||||
*/
|
||||
ol.source.WMTS.prototype.getFormat = function() {
|
||||
return this.format_;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
@@ -212,6 +251,42 @@ ol.source.WMTS.prototype.getKeyZXY = function(z, x, y) {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {string} Layer.
|
||||
* @api
|
||||
*/
|
||||
ol.source.WMTS.prototype.getLayer = function() {
|
||||
return this.layer_;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {string} MatrixSet.
|
||||
* @api
|
||||
*/
|
||||
ol.source.WMTS.prototype.getMatrixSet = function() {
|
||||
return this.matrixSet_;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {string} Style.
|
||||
* @api
|
||||
*/
|
||||
ol.source.WMTS.prototype.getStyle = function() {
|
||||
return this.style_;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {string} Version.
|
||||
* @api
|
||||
*/
|
||||
ol.source.WMTS.prototype.getVersion = function() {
|
||||
return this.version_;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @private
|
||||
*/
|
||||
@@ -239,90 +314,149 @@ ol.source.WMTS.prototype.updateDimensions = function(dimensions) {
|
||||
|
||||
/**
|
||||
* @param {Object} wmtsCap An object representing the capabilities document.
|
||||
* @param {string} layer The layer identifier.
|
||||
* @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.
|
||||
* @return {olx.source.WMTSOptions} WMTS source options object.
|
||||
* @api
|
||||
*/
|
||||
ol.source.WMTS.optionsFromCapabilities = function(wmtsCap, layer) {
|
||||
ol.source.WMTS.optionsFromCapabilities = function(wmtsCap, config) {
|
||||
|
||||
/* jshint -W069 */
|
||||
|
||||
// TODO: add support for TileMatrixLimits
|
||||
goog.asserts.assert(!goog.isNull(config['layer']));
|
||||
|
||||
var layers = wmtsCap['contents']['layers'];
|
||||
var layers = wmtsCap['Contents']['Layer'];
|
||||
var l = goog.array.find(layers, function(elt, index, array) {
|
||||
return elt['identifier'] == layer;
|
||||
return elt['Identifier'] == config['layer'];
|
||||
});
|
||||
goog.asserts.assert(!goog.isNull(l));
|
||||
goog.asserts.assert(l['tileMatrixSetLinks'].length > 0);
|
||||
var matrixSet = /** @type {string} */
|
||||
(l['tileMatrixSetLinks'][0]['tileMatrixSet']);
|
||||
var format = /** @type {string} */ (l['formats'][0]);
|
||||
var idx = goog.array.findIndex(l['styles'], function(elt, index, array) {
|
||||
return elt['isDefault'];
|
||||
|
||||
goog.asserts.assert(l['TileMatrixSetLink'].length > 0);
|
||||
var idx, matrixSet;
|
||||
if (l['TileMatrixSetLink'].length > 1) {
|
||||
idx = goog.array.findIndex(l['TileMatrixSetLink'],
|
||||
function(elt, index, array) {
|
||||
return elt['TileMatrixSet'] == config['matrixSet'];
|
||||
});
|
||||
} else if (goog.isDef(config['projection'])) {
|
||||
idx = goog.array.findIndex(l['TileMatrixSetLink'],
|
||||
function(elt, index, array) {
|
||||
return elt['TileMatrixSet']['SupportedCRS'].replace(
|
||||
/urn:ogc:def:crs:(\w+):(.*:)?(\w+)$/, '$1:$3'
|
||||
) == config['projection'];
|
||||
});
|
||||
} else {
|
||||
idx = 0;
|
||||
}
|
||||
if (idx < 0) {
|
||||
idx = 0;
|
||||
}
|
||||
matrixSet = /** @type {string} */
|
||||
(l['TileMatrixSetLink'][idx]['TileMatrixSet']);
|
||||
|
||||
goog.asserts.assert(!goog.isNull(matrixSet));
|
||||
|
||||
var format = /** @type {string} */ (l['Format'][0]);
|
||||
if (goog.isDef(config['format'])) {
|
||||
format = config['format'];
|
||||
}
|
||||
idx = goog.array.findIndex(l['Style'], function(elt, index, array) {
|
||||
if (goog.isDef(config['style'])) {
|
||||
return elt['Title'] == config['style'];
|
||||
} else {
|
||||
return elt['isDefault'];
|
||||
}
|
||||
});
|
||||
if (idx < 0) {
|
||||
idx = 0;
|
||||
}
|
||||
var style = /** @type {string} */ (l['styles'][idx]['identifier']);
|
||||
var style = /** @type {string} */ (l['Style'][idx]['Identifier']);
|
||||
|
||||
var dimensions = {};
|
||||
goog.array.forEach(l['dimensions'], function(elt, index, array) {
|
||||
var key = elt['identifier'];
|
||||
var value = elt['default'];
|
||||
if (goog.isDef(value)) {
|
||||
goog.asserts.assert(goog.array.contains(elt['values'], value));
|
||||
} else {
|
||||
value = elt['values'][0];
|
||||
}
|
||||
goog.asserts.assert(goog.isDef(value));
|
||||
dimensions[key] = value;
|
||||
});
|
||||
if (goog.isDef(l['Dimension'])) {
|
||||
goog.array.forEach(l['Dimension'], function(elt, index, array) {
|
||||
var key = elt['Identifier'];
|
||||
var value = elt['default'];
|
||||
if (goog.isDef(value)) {
|
||||
goog.asserts.assert(goog.array.contains(elt['values'], value));
|
||||
} else {
|
||||
value = elt['values'][0];
|
||||
}
|
||||
goog.asserts.assert(goog.isDef(value));
|
||||
dimensions[key] = value;
|
||||
});
|
||||
}
|
||||
|
||||
var matrixSets = wmtsCap['contents']['tileMatrixSets'];
|
||||
goog.asserts.assert(matrixSet in matrixSets);
|
||||
var matrixSetObj = matrixSets[matrixSet];
|
||||
var matrixSets = wmtsCap['Contents']['TileMatrixSet'];
|
||||
var matrixSetObj = goog.array.find(matrixSets, function(elt, index, array) {
|
||||
return elt['Identifier'] == matrixSet;
|
||||
});
|
||||
goog.asserts.assert(!goog.isNull(matrixSetObj));
|
||||
|
||||
var tileGrid = ol.tilegrid.WMTS.createFromCapabilitiesMatrixSet(
|
||||
matrixSetObj);
|
||||
|
||||
var projection = ol.proj.get(matrixSetObj['supportedCRS']);
|
||||
|
||||
var gets = wmtsCap['operationsMetadata']['GetTile']['dcp']['http']['get'];
|
||||
var encodings = goog.object.getKeys(
|
||||
gets[0]['constraints']['GetEncoding']['allowedValues']);
|
||||
goog.asserts.assert(encodings.length > 0);
|
||||
|
||||
var urls;
|
||||
var requestEncoding;
|
||||
switch (encodings[0]) {
|
||||
case 'REST':
|
||||
case 'RESTful':
|
||||
// The OGC documentation is not clear if we should use REST or RESTful,
|
||||
// ArcGis use RESTful, and OpenLayers use REST.
|
||||
requestEncoding = ol.source.WMTSRequestEncoding.REST;
|
||||
goog.asserts.assert(l['resourceUrls'].hasOwnProperty('tile'));
|
||||
goog.asserts.assert(l['resourceUrls']['tile'].hasOwnProperty(format));
|
||||
urls = /** @type {Array.<string>} */
|
||||
(l['resourceUrls']['tile'][format]);
|
||||
break;
|
||||
case 'KVP':
|
||||
requestEncoding = ol.source.WMTSRequestEncoding.KVP;
|
||||
urls = [];
|
||||
goog.array.forEach(gets, function(elt, index, array) {
|
||||
if (elt['constraints']['GetEncoding']['allowedValues'].hasOwnProperty(
|
||||
ol.source.WMTSRequestEncoding.KVP)) {
|
||||
urls.push(/** @type {string} */ (elt['url']));
|
||||
}
|
||||
});
|
||||
goog.asserts.assert(urls.length > 0);
|
||||
break;
|
||||
default:
|
||||
goog.asserts.fail();
|
||||
var projection;
|
||||
if (goog.isDef(config['projection'])) {
|
||||
projection = ol.proj.get(config['projection']);
|
||||
} else {
|
||||
projection = ol.proj.get(matrixSetObj['SupportedCRS'].replace(
|
||||
/urn:ogc:def:crs:(\w+):(.*:)?(\w+)$/, '$1:$3'));
|
||||
}
|
||||
|
||||
/** @type {!Array.<string>} */
|
||||
var urls = [];
|
||||
var requestEncoding = config['requestEncoding'];
|
||||
requestEncoding = goog.isDef(requestEncoding) ? requestEncoding : '';
|
||||
|
||||
goog.asserts.assert(
|
||||
goog.array.contains(['REST', 'RESTful', 'KVP', ''], requestEncoding));
|
||||
|
||||
if (!wmtsCap['OperationsMetadata'].hasOwnProperty('GetTile') ||
|
||||
goog.string.startsWith(requestEncoding, 'REST')) {
|
||||
// Add REST tile resource url
|
||||
requestEncoding = ol.source.WMTSRequestEncoding.REST;
|
||||
goog.array.forEach(l['ResourceURL'], function(elt, index, array) {
|
||||
if (elt['resourceType'] == 'tile') {
|
||||
format = elt['format'];
|
||||
urls.push(/** @type {string} */ (elt['template']));
|
||||
}
|
||||
});
|
||||
} else {
|
||||
var gets = wmtsCap['OperationsMetadata']['GetTile']['DCP']['HTTP']['Get'];
|
||||
|
||||
var constraint = goog.array.find(gets[0]['Constraint'],
|
||||
function(elt, index, array) {
|
||||
return elt['name'] == 'GetEncoding';
|
||||
});
|
||||
var encodings = constraint['AllowedValues']['Value'];
|
||||
if (encodings.length > 0 && goog.array.contains(encodings, 'KVP')) {
|
||||
requestEncoding = ol.source.WMTSRequestEncoding.KVP;
|
||||
urls.push(/** @type {string} */ (gets[0]['href']));
|
||||
|
||||
}
|
||||
}
|
||||
goog.asserts.assert(urls.length > 0);
|
||||
|
||||
return {
|
||||
urls: urls,
|
||||
layer: layer,
|
||||
layer: config['layer'],
|
||||
matrixSet: matrixSet,
|
||||
format: format,
|
||||
projection: projection,
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
* @license
|
||||
* Latitude/longitude spherical geodesy formulae taken from
|
||||
* http://www.movable-type.co.uk/scripts/latlong.html
|
||||
* Licenced under CC-BY-3.0.
|
||||
* Licensed under CC-BY-3.0.
|
||||
*/
|
||||
|
||||
// FIXME add intersection of two paths given start points and bearings
|
||||
@@ -57,6 +57,36 @@ ol.Sphere.prototype.cosineDistance = function(c1, c2) {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Returns the geodesic area for a list of coordinates.
|
||||
*
|
||||
* [Reference](http://trs-new.jpl.nasa.gov/dspace/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) {
|
||||
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 += goog.math.toRadians(x2 - x1) *
|
||||
(2 + Math.sin(goog.math.toRadians(y1)) +
|
||||
Math.sin(goog.math.toRadians(y2)));
|
||||
x1 = x2;
|
||||
y1 = y2;
|
||||
}
|
||||
return area * this.radius * this.radius / 2.0;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Returns the distance of c3 from the great circle path defined by c1 and c2.
|
||||
*
|
||||
@@ -110,6 +140,7 @@ ol.Sphere.prototype.finalBearing = function(c1, c2) {
|
||||
* @param {ol.Coordinate} c1 Coordinate 1.
|
||||
* @param {ol.Coordinate} c2 Coordinate 2.
|
||||
* @return {number} Haversine distance.
|
||||
* @api
|
||||
*/
|
||||
ol.Sphere.prototype.haversineDistance = function(c1, c2) {
|
||||
var lat1 = goog.math.toRadians(c1[1]);
|
||||
|
||||
@@ -377,7 +377,7 @@ ol.style.IconImage_ = function(image, src, crossOrigin, imageState) {
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Array.<number>}
|
||||
* @type {Array.<goog.events.Key>}
|
||||
*/
|
||||
this.imageListenerKeys_ = null;
|
||||
|
||||
|
||||
@@ -278,8 +278,15 @@ ol.style.RegularShape.prototype.unlistenImageChange = goog.nullFunction;
|
||||
|
||||
|
||||
/**
|
||||
* @typedef {{strokeStyle: (string|undefined), strokeWidth: number,
|
||||
* size: number, lineDash: Array.<number>}}
|
||||
* @typedef {{
|
||||
* strokeStyle: (string|undefined),
|
||||
* strokeWidth: number,
|
||||
* size: number,
|
||||
* lineCap: string,
|
||||
* lineDash: Array.<number>,
|
||||
* lineJoin: string,
|
||||
* miterLimit: number
|
||||
* }}
|
||||
*/
|
||||
ol.style.RegularShape.RenderOptions;
|
||||
|
||||
@@ -290,6 +297,9 @@ ol.style.RegularShape.RenderOptions;
|
||||
*/
|
||||
ol.style.RegularShape.prototype.render_ = function(atlasManager) {
|
||||
var imageSize;
|
||||
var lineCap = '';
|
||||
var lineJoin = '';
|
||||
var miterLimit = 0;
|
||||
var lineDash = null;
|
||||
var strokeStyle;
|
||||
var strokeWidth = 0;
|
||||
@@ -304,6 +314,18 @@ ol.style.RegularShape.prototype.render_ = function(atlasManager) {
|
||||
if (!ol.has.CANVAS_LINE_DASH) {
|
||||
lineDash = null;
|
||||
}
|
||||
lineJoin = this.stroke_.getLineJoin();
|
||||
if (!goog.isDef(lineJoin)) {
|
||||
lineJoin = ol.render.canvas.defaultLineJoin;
|
||||
}
|
||||
lineCap = this.stroke_.getLineCap();
|
||||
if (!goog.isDef(lineCap)) {
|
||||
lineCap = ol.render.canvas.defaultLineCap;
|
||||
}
|
||||
miterLimit = this.stroke_.getMiterLimit();
|
||||
if (!goog.isDef(miterLimit)) {
|
||||
miterLimit = ol.render.canvas.defaultMiterLimit;
|
||||
}
|
||||
}
|
||||
|
||||
var size = 2 * (this.radius_ + strokeWidth) + 1;
|
||||
@@ -313,7 +335,10 @@ ol.style.RegularShape.prototype.render_ = function(atlasManager) {
|
||||
strokeStyle: strokeStyle,
|
||||
strokeWidth: strokeWidth,
|
||||
size: size,
|
||||
lineDash: lineDash
|
||||
lineCap: lineCap,
|
||||
lineDash: lineDash,
|
||||
lineJoin: lineJoin,
|
||||
miterLimit: miterLimit
|
||||
};
|
||||
|
||||
if (!goog.isDef(atlasManager)) {
|
||||
@@ -373,7 +398,7 @@ ol.style.RegularShape.prototype.render_ = function(atlasManager) {
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @param {ol.style.Circle.RenderOptions} renderOptions
|
||||
* @param {ol.style.RegularShape.RenderOptions} renderOptions
|
||||
* @param {CanvasRenderingContext2D} context
|
||||
* @param {number} x The origin for the symbol (x).
|
||||
* @param {number} y The origin for the symbol (y).
|
||||
@@ -407,6 +432,9 @@ ol.style.RegularShape.prototype.draw_ = function(renderOptions, context, x, y) {
|
||||
if (!goog.isNull(renderOptions.lineDash)) {
|
||||
context.setLineDash(renderOptions.lineDash);
|
||||
}
|
||||
context.lineCap = renderOptions.lineCap;
|
||||
context.lineJoin = renderOptions.lineJoin;
|
||||
context.miterLimit = renderOptions.miterLimit;
|
||||
context.stroke();
|
||||
}
|
||||
context.closePath();
|
||||
|
||||
@@ -64,6 +64,7 @@ ol.tilegrid.WMTS.prototype.getMatrixIds = function() {
|
||||
* @param {Object} matrixSet An object representing a matrixSet in the
|
||||
* capabilities document.
|
||||
* @return {ol.tilegrid.WMTS} WMTS tileGrid instance.
|
||||
* @api
|
||||
*/
|
||||
ol.tilegrid.WMTS.createFromCapabilitiesMatrixSet =
|
||||
function(matrixSet) {
|
||||
@@ -77,16 +78,20 @@ ol.tilegrid.WMTS.createFromCapabilitiesMatrixSet =
|
||||
/** @type {!Array.<number>} */
|
||||
var tileSizes = [];
|
||||
|
||||
var supportedCRSPropName = 'supportedCRS';
|
||||
var matrixIdsPropName = 'matrixIds';
|
||||
var identifierPropName = 'identifier';
|
||||
var scaleDenominatorPropName = 'scaleDenominator';
|
||||
var topLeftCornerPropName = 'topLeftCorner';
|
||||
var tileWidthPropName = 'tileWidth';
|
||||
var tileHeightPropName = 'tileHeight';
|
||||
var supportedCRSPropName = 'SupportedCRS';
|
||||
var matrixIdsPropName = 'TileMatrix';
|
||||
var identifierPropName = 'Identifier';
|
||||
var scaleDenominatorPropName = 'ScaleDenominator';
|
||||
var topLeftCornerPropName = 'TopLeftCorner';
|
||||
var tileWidthPropName = 'TileWidth';
|
||||
var tileHeightPropName = 'TileHeight';
|
||||
|
||||
var projection = ol.proj.get(matrixSet[supportedCRSPropName]);
|
||||
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';
|
||||
|
||||
goog.array.sort(matrixSet[matrixIdsPropName], function(a, b) {
|
||||
return b[scaleDenominatorPropName] - a[scaleDenominatorPropName];
|
||||
@@ -95,7 +100,12 @@ ol.tilegrid.WMTS.createFromCapabilitiesMatrixSet =
|
||||
goog.array.forEach(matrixSet[matrixIdsPropName],
|
||||
function(elt, index, array) {
|
||||
matrixIds.push(elt[identifierPropName]);
|
||||
origins.push(elt[topLeftCornerPropName]);
|
||||
if (switchOriginXY) {
|
||||
origins.push([elt[topLeftCornerPropName][1],
|
||||
elt[topLeftCornerPropName][0]]);
|
||||
} else {
|
||||
origins.push(elt[topLeftCornerPropName]);
|
||||
}
|
||||
resolutions.push(elt[scaleDenominatorPropName] * 0.28E-3 /
|
||||
metersPerUnit);
|
||||
var tileWidth = elt[tileWidthPropName];
|
||||
|
||||
@@ -4,6 +4,7 @@ goog.provide('ol.TileQueue');
|
||||
goog.require('goog.events');
|
||||
goog.require('goog.events.EventType');
|
||||
goog.require('ol.Coordinate');
|
||||
goog.require('ol.TileState');
|
||||
goog.require('ol.structs.PriorityQueue');
|
||||
|
||||
|
||||
@@ -67,11 +68,17 @@ ol.TileQueue.prototype.getTilesLoading = function() {
|
||||
|
||||
|
||||
/**
|
||||
* @param {goog.events.Event} event Event.
|
||||
* @protected
|
||||
*/
|
||||
ol.TileQueue.prototype.handleTileChange = function() {
|
||||
--this.tilesLoading_;
|
||||
this.tileChangeCallback_();
|
||||
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) {
|
||||
--this.tilesLoading_;
|
||||
this.tileChangeCallback_();
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -85,7 +92,7 @@ ol.TileQueue.prototype.loadMoreTiles = function(maxTotalLoading, maxNewLoads) {
|
||||
var i, tile;
|
||||
for (i = 0; i < newLoads; ++i) {
|
||||
tile = /** @type {ol.Tile} */ (this.dequeue()[0]);
|
||||
goog.events.listenOnce(tile, goog.events.EventType.CHANGE,
|
||||
goog.events.listen(tile, goog.events.EventType.CHANGE,
|
||||
this.handleTileChange, false, this);
|
||||
tile.load();
|
||||
}
|
||||
|
||||
@@ -72,7 +72,7 @@ function getSymbols(patterns, callback) {
|
||||
/**
|
||||
* Generate a list of symbol names given a list of patterns. Patterns may
|
||||
* include a * wildcard at the end of the string, in which case all symbol names
|
||||
* that start with the preceeding string will be matched (e.g 'foo.Bar#*' will
|
||||
* that start with the preceding string will be matched (e.g 'foo.Bar#*' will
|
||||
* match all symbol names that start with 'foo.Bar#').
|
||||
*
|
||||
* @param {Array.<string>} patterns A list of symbol names to match. Wildcards
|
||||
|
||||
@@ -11,7 +11,7 @@ var googRegEx = /^goog\..*$/;
|
||||
|
||||
/**
|
||||
* Read the symbols from info file.
|
||||
* @param {funciton(Error, Array.<string>, Array.<Object>)} callback Called
|
||||
* @param {function(Error, Array.<string>, Array.<Object>)} callback Called
|
||||
* with the patterns and symbols (or any error).
|
||||
*/
|
||||
function getInfo(callback) {
|
||||
|
||||
@@ -220,7 +220,7 @@ describe('ol.format.GPX', function() {
|
||||
expect(serialized).to.xmleql(ol.xml.parse(text));
|
||||
});
|
||||
|
||||
it('can tranform, read and write a trk with a trkseg', function() {
|
||||
it('can transform, read and write a trk with a trkseg', function() {
|
||||
var text =
|
||||
'<gpx xmlns="http://www.topografix.com/GPX/1/1">' +
|
||||
' <trk>' +
|
||||
|
||||
@@ -919,7 +919,7 @@ describe('ol.format.KML', function() {
|
||||
expect(g.getGeometries()).to.be.empty();
|
||||
});
|
||||
|
||||
it('can read heterogenous GeometryCollection geometries', function() {
|
||||
it('can read heterogeneous GeometryCollection geometries', function() {
|
||||
var text =
|
||||
'<kml xmlns="http://earth.google.com/kml/2.2">' +
|
||||
' <Placemark>' +
|
||||
@@ -2407,7 +2407,7 @@ describe('ol.format.KML', function() {
|
||||
expect(features).to.have.length(50);
|
||||
});
|
||||
|
||||
it('creates features with heterogenous geometry collections', function() {
|
||||
it('creates features with heterogeneous geometry collections', function() {
|
||||
// FIXME decide if we should instead create features with multiple geoms
|
||||
var feature = features[0];
|
||||
expect(feature).to.be.an(ol.Feature);
|
||||
|
||||
@@ -4,7 +4,7 @@ describe('ol.format.Polyline', function() {
|
||||
|
||||
var format;
|
||||
var points;
|
||||
var flatPoints, encodedFlatPoints;
|
||||
var flatPoints, encodedFlatPoints, flippedFlatPoints;
|
||||
var floats, smallFloats, encodedFloats;
|
||||
var signedIntegers, encodedSignedIntegers;
|
||||
var unsignedIntegers, encodedUnsignedIntegers;
|
||||
|
||||
1
test/spec/ol/format/wkt/illinois.wkt
Normal file
1
test/spec/ol/format/wkt/illinois.wkt
Normal file
File diff suppressed because one or more lines are too long
@@ -28,12 +28,10 @@ access interface to some TileMatrixSets</ows:Abstract>
|
||||
<ows:Address>
|
||||
<ows:DeliveryPoint>Fac Ciencies UAB</ows:DeliveryPoint>
|
||||
<ows:City>Bellaterra</ows:City>
|
||||
<ows:AdministrativeArea>Barcelona
|
||||
</ows:AdministrativeArea>
|
||||
<ows:AdministrativeArea>Barcelona</ows:AdministrativeArea>
|
||||
<ows:PostalCode>08193</ows:PostalCode>
|
||||
<ows:Country>Spain</ows:Country>
|
||||
<ows:ElectronicMailAddress>joan.maso@uab.cat
|
||||
</ows:ElectronicMailAddress>
|
||||
<ows:ElectronicMailAddress>joan.maso@uab.cat</ows:ElectronicMailAddress>
|
||||
</ows:Address>
|
||||
</ows:ContactInfo>
|
||||
</ows:ServiceContact>
|
||||
@@ -70,8 +68,7 @@ access interface to some TileMatrixSets</ows:Abstract>
|
||||
<Contents>
|
||||
<Layer>
|
||||
<ows:Title>Blue Marble Next Generation</ows:Title>
|
||||
<ows:Abstract>Blue Marble Next Generation NASA Product
|
||||
</ows:Abstract>
|
||||
<ows:Abstract>Blue Marble Next Generation NASA Product</ows:Abstract>
|
||||
<ows:WGS84BoundingBox>
|
||||
<ows:LowerCorner>-180 -90</ows:LowerCorner>
|
||||
<ows:UpperCorner>180 90</ows:UpperCorner>
|
||||
@@ -84,8 +81,7 @@ access interface to some TileMatrixSets</ows:Abstract>
|
||||
</Style>
|
||||
<Style>
|
||||
<ows:Title>Thick And Red</ows:Title>
|
||||
<ows:Abstract>Specify this style if you want your maps to have thick red coastlines.
|
||||
</ows:Abstract>
|
||||
<ows:Abstract>Specify this style if you want your maps to have thick red coastlines.</ows:Abstract>
|
||||
<ows:Identifier>thickAndRed</ows:Identifier>
|
||||
</Style>
|
||||
<Format>image/jpeg</Format>
|
||||
@@ -93,15 +89,206 @@ access interface to some TileMatrixSets</ows:Abstract>
|
||||
<TileMatrixSetLink>
|
||||
<TileMatrixSet>BigWorldPixel</TileMatrixSet>
|
||||
</TileMatrixSetLink>
|
||||
<TileMatrixSetLink>
|
||||
<TileMatrixSet>google3857</TileMatrixSet>
|
||||
</TileMatrixSetLink>
|
||||
<ResourceURL format="image/png" resourceType="tile" template="http://www.example.com/wmts/coastlines/{TileMatrix}/{TileRow}/{TileCol}.png"/>
|
||||
<ResourceURL format="application/gml+xml; version=3.1" resourceType="FeatureInfo" template="http://www.example.com/wmts/coastlines/{TileMatrixSet}/{TileMatrix}/{TileRow}/{TileCol}/{J}/{I}.xml"/>
|
||||
</Layer>
|
||||
<TileMatrixSet>
|
||||
<!-- -180 85.05112878 -->
|
||||
<ows:Identifier>google3857</ows:Identifier>
|
||||
<ows:BoundingBox crs="urn:ogc:def:crs:EPSG:6.18:3:3857">
|
||||
<ows:LowerCorner>1799448.394855 6124949.747770</ows:LowerCorner>
|
||||
<ows:UpperCorner>1848250.442089 6162571.828177</ows:UpperCorner>
|
||||
</ows:BoundingBox>
|
||||
<ows:SupportedCRS>urn:ogc:def:crs:EPSG:6.18:3:3857</ows:SupportedCRS>
|
||||
<WellKnownScaleSet>urn:ogc:def:wkss:OGC:1.0:GoogleMapsCompatible</WellKnownScaleSet>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>0</ows:Identifier>
|
||||
<ScaleDenominator>559082264.029</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>1</MatrixWidth>
|
||||
<MatrixHeight>1</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>1</ows:Identifier>
|
||||
<ScaleDenominator>279541132.015</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>2</MatrixWidth>
|
||||
<MatrixHeight>2</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>2</ows:Identifier>
|
||||
<ScaleDenominator>139770566.007</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>4</MatrixWidth>
|
||||
<MatrixHeight>4</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>3</ows:Identifier>
|
||||
<ScaleDenominator>69885283.0036</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>8</MatrixWidth>
|
||||
<MatrixHeight>8</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>4</ows:Identifier>
|
||||
<ScaleDenominator>34942641.5018</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>16</MatrixWidth>
|
||||
<MatrixHeight>16</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>5</ows:Identifier>
|
||||
<ScaleDenominator>17471320.7509</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>32</MatrixWidth>
|
||||
<MatrixHeight>32</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>6</ows:Identifier>
|
||||
<ScaleDenominator>8735660.37545</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>64</MatrixWidth>
|
||||
<MatrixHeight>64</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>7</ows:Identifier>
|
||||
<ScaleDenominator>4367830.18773</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>128</MatrixWidth>
|
||||
<MatrixHeight>128</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>8</ows:Identifier>
|
||||
<ScaleDenominator>2183915.09386</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>256</MatrixWidth>
|
||||
<MatrixHeight>256</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>9</ows:Identifier>
|
||||
<ScaleDenominator>1091957.54693</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>512</MatrixWidth>
|
||||
<MatrixHeight>512</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>10</ows:Identifier>
|
||||
<ScaleDenominator>545978.773466</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>1024</MatrixWidth>
|
||||
<MatrixHeight>1024</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>11</ows:Identifier>
|
||||
<ScaleDenominator>272989.386733</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>2048</MatrixWidth>
|
||||
<MatrixHeight>2048</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>12</ows:Identifier>
|
||||
<ScaleDenominator>136494.693366</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>4096</MatrixWidth>
|
||||
<MatrixHeight>4096</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>13</ows:Identifier>
|
||||
<ScaleDenominator>68247.3466832</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>8192</MatrixWidth>
|
||||
<MatrixHeight>8192</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>14</ows:Identifier>
|
||||
<ScaleDenominator>34123.6733416</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>16384</MatrixWidth>
|
||||
<MatrixHeight>16384</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>15</ows:Identifier>
|
||||
<ScaleDenominator>17061.8366708</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>32768</MatrixWidth>
|
||||
<MatrixHeight>32768</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>16</ows:Identifier>
|
||||
<ScaleDenominator>8530.91833540</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>65536</MatrixWidth>
|
||||
<MatrixHeight>65536</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>17</ows:Identifier>
|
||||
<ScaleDenominator>4265.45916770</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>131072</MatrixWidth>
|
||||
<MatrixHeight>131072</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>18</ows:Identifier>
|
||||
<ScaleDenominator>2132.72958385</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>262144</MatrixWidth>
|
||||
<MatrixHeight>262144</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>19</ows:Identifier>
|
||||
<ScaleDenominator>1066.36479193</ScaleDenominator>
|
||||
<TopLeftCorner>-20037508.3428 20037508.3428</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>524288</MatrixWidth>
|
||||
<MatrixHeight>524288</MatrixHeight>
|
||||
</TileMatrix>
|
||||
</TileMatrixSet>
|
||||
<TileMatrixSet>
|
||||
<ows:Identifier>BigWorldPixel</ows:Identifier>
|
||||
<ows:SupportedCRS>urn:ogc:def:crs:OGC:1.3:CRS84
|
||||
</ows:SupportedCRS>
|
||||
<WellKnownScaleSet>urn:ogc:def:wkss:OGC:1.0:GlobalCRS84Pixel
|
||||
</WellKnownScaleSet>
|
||||
<ows:SupportedCRS>urn:ogc:def:crs:OGC:1.3:CRS84</ows:SupportedCRS>
|
||||
<WellKnownScaleSet>urn:ogc:def:wkss:OGC:1.0:GlobalCRS84Pixel</WellKnownScaleSet>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>10000m</ows:Identifier>
|
||||
<ScaleDenominator>33130800.83133142</ScaleDenominator>
|
||||
@@ -158,27 +345,27 @@ access interface to some TileMatrixSets</ows:Abstract>
|
||||
</TileMatrix>
|
||||
</TileMatrixSet>
|
||||
<TileMatrixSet>
|
||||
<ows:Identifier>BigWorld</ows:Identifier>
|
||||
<ows:SupportedCRS>urn:ogc:def:crs:OGC:1.3:CRS84</ows:SupportedCRS>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>1e6</ows:Identifier>
|
||||
<ScaleDenominator>1e6</ScaleDenominator>
|
||||
<TopLeftCorner>-180 84</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>60000</MatrixWidth>
|
||||
<MatrixHeight>50000</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>2.5e6</ows:Identifier>
|
||||
<ScaleDenominator>2.5e6</ScaleDenominator>
|
||||
<TopLeftCorner>-180 84</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>9000</MatrixWidth>
|
||||
<MatrixHeight>7000</MatrixHeight>
|
||||
</TileMatrix>
|
||||
</TileMatrixSet>
|
||||
<ows:Identifier>BigWorld</ows:Identifier>
|
||||
<ows:SupportedCRS>urn:ogc:def:crs:OGC:1.3:CRS84</ows:SupportedCRS>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>1e6</ows:Identifier>
|
||||
<ScaleDenominator>1e6</ScaleDenominator>
|
||||
<TopLeftCorner>-180 84</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>60000</MatrixWidth>
|
||||
<MatrixHeight>50000</MatrixHeight>
|
||||
</TileMatrix>
|
||||
<TileMatrix>
|
||||
<ows:Identifier>2.5e6</ows:Identifier>
|
||||
<ScaleDenominator>2.5e6</ScaleDenominator>
|
||||
<TopLeftCorner>-180 84</TopLeftCorner>
|
||||
<TileWidth>256</TileWidth>
|
||||
<TileHeight>256</TileHeight>
|
||||
<MatrixWidth>9000</MatrixWidth>
|
||||
<MatrixHeight>7000</MatrixHeight>
|
||||
</TileMatrix>
|
||||
</TileMatrixSet>
|
||||
</Contents>
|
||||
<ServiceMetadataURL xlink:href="http://www.maps.bob/wmts/1.0.0/WMTSCapabilities.xml"/>
|
||||
</Capabilities>
|
||||
|
||||
@@ -44,9 +44,11 @@ describe('ol.format.WMTSCapabilities', function() {
|
||||
expect(layer.Style[0].LegendURL[0].format).to.be.eql('image/png');
|
||||
|
||||
expect(layer.TileMatrixSetLink).to.be.an('array');
|
||||
expect(layer.TileMatrixSetLink).to.have.length(1);
|
||||
expect(layer.TileMatrixSetLink).to.have.length(2);
|
||||
expect(layer.TileMatrixSetLink[0].TileMatrixSet).to.be
|
||||
.eql('BigWorldPixel');
|
||||
expect(layer.TileMatrixSetLink[1].TileMatrixSet).to.be
|
||||
.eql('google3857');
|
||||
|
||||
var wgs84Bbox = layer.WGS84BoundingBox;
|
||||
expect(wgs84Bbox).to.be.an('array');
|
||||
@@ -67,7 +69,7 @@ describe('ol.format.WMTSCapabilities', function() {
|
||||
it('Can read Capabilities.Content.TileMatrixSet', function() {
|
||||
expect(capabilities.Contents.TileMatrixSet).to.be.ok();
|
||||
|
||||
var bigWorld = capabilities.Contents.TileMatrixSet[1];
|
||||
var bigWorld = capabilities.Contents.TileMatrixSet[2];
|
||||
expect(bigWorld).to.be.ok();
|
||||
expect(bigWorld.Identifier).to.be.eql('BigWorld');
|
||||
expect(bigWorld.SupportedCRS).to.be.eql('urn:ogc:def:crs:OGC:1.3:CRS84');
|
||||
|
||||
@@ -504,7 +504,7 @@ describe('ol.interaction.Draw', function() {
|
||||
expect(interaction.sketchFeature_).to.be(null);
|
||||
});
|
||||
it('fires change:active', function() {
|
||||
listenerSpy = sinon.spy(function() {
|
||||
var listenerSpy = sinon.spy(function() {
|
||||
// test that the interaction's change:active listener is called first
|
||||
expect(interaction.overlay_.map_).to.be(null);
|
||||
});
|
||||
@@ -523,7 +523,7 @@ describe('ol.interaction.Draw', function() {
|
||||
expect(interaction.overlay_.map_).to.be(map);
|
||||
});
|
||||
it('fires change:active', function() {
|
||||
listenerSpy = sinon.spy(function() {
|
||||
var listenerSpy = sinon.spy(function() {
|
||||
// test that the interaction's change:active listener is called first
|
||||
expect(interaction.overlay_.map_).not.to.be(null);
|
||||
});
|
||||
@@ -592,6 +592,7 @@ goog.require('goog.dispose');
|
||||
goog.require('goog.events');
|
||||
goog.require('goog.events.BrowserEvent');
|
||||
goog.require('goog.style');
|
||||
goog.require('ol.DrawEventType');
|
||||
goog.require('ol.Map');
|
||||
goog.require('ol.MapBrowserPointerEvent');
|
||||
goog.require('ol.View');
|
||||
|
||||
212
test/spec/ol/interaction/selectinteraction.test.js
Normal file
212
test/spec/ol/interaction/selectinteraction.test.js
Normal file
@@ -0,0 +1,212 @@
|
||||
goog.provide('ol.test.interaction.Select');
|
||||
|
||||
describe('ol.interaction.Select', function() {
|
||||
var target, map, source;
|
||||
|
||||
var width = 360;
|
||||
var height = 180;
|
||||
|
||||
beforeEach(function(done) {
|
||||
target = document.createElement('div');
|
||||
var style = target.style;
|
||||
style.position = 'absolute';
|
||||
style.left = '-1000px';
|
||||
style.top = '-1000px';
|
||||
style.width = width + 'px';
|
||||
style.height = height + 'px';
|
||||
document.body.appendChild(target);
|
||||
var geometry = new ol.geom.Polygon([[[0, 0], [0, 40], [40, 40], [40, 0]]]);
|
||||
var geometry2 = new ol.geom.Polygon([[[0, 0], [0, 40], [40, 40], [40, 0]]]);
|
||||
var feature = new ol.Feature({
|
||||
geometry: geometry
|
||||
});
|
||||
var feature2 = new ol.Feature({
|
||||
geometry: geometry2
|
||||
});
|
||||
source = new ol.source.Vector({
|
||||
features: [feature, feature2]
|
||||
});
|
||||
var layer = new ol.layer.Vector({source: source});
|
||||
map = new ol.Map({
|
||||
target: target,
|
||||
layers: [layer],
|
||||
view: new ol.View({
|
||||
projection: 'EPSG:4326',
|
||||
center: [0, 0],
|
||||
resolution: 1
|
||||
})
|
||||
});
|
||||
map.on('postrender', function() {
|
||||
done();
|
||||
});
|
||||
});
|
||||
|
||||
afterEach(function() {
|
||||
goog.dispose(map);
|
||||
document.body.removeChild(target);
|
||||
});
|
||||
|
||||
/**
|
||||
* Simulates a browser event on the map viewport. The client x/y location
|
||||
* will be adjusted as if the map were centered at 0,0.
|
||||
* @param {string} type Event type.
|
||||
* @param {number} x Horizontal offset from map center.
|
||||
* @param {number} y Vertical offset from map center.
|
||||
* @param {boolean=} opt_shiftKey Shift key is pressed.
|
||||
*/
|
||||
function simulateEvent(type, x, y, opt_shiftKey) {
|
||||
var viewport = map.getViewport();
|
||||
// calculated in case body has top < 0 (test runner with small window)
|
||||
var position = goog.style.getClientPosition(viewport);
|
||||
var shiftKey = goog.isDef(opt_shiftKey) ? opt_shiftKey : false;
|
||||
var event = new ol.MapBrowserPointerEvent(type, map,
|
||||
new ol.pointer.PointerEvent(type,
|
||||
new goog.events.BrowserEvent({
|
||||
clientX: position.x + x + width / 2,
|
||||
clientY: position.y + y + height / 2,
|
||||
shiftKey: shiftKey
|
||||
})));
|
||||
console.debug(event);
|
||||
map.handleMapBrowserEvent(event);
|
||||
}
|
||||
|
||||
describe('constructor', function() {
|
||||
|
||||
it('creates a new interaction', function() {
|
||||
var select = new ol.interaction.Select();
|
||||
expect(select).to.be.a(ol.interaction.Select);
|
||||
expect(select).to.be.a(ol.interaction.Interaction);
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
describe('selecting a polygon', function() {
|
||||
var select;
|
||||
|
||||
beforeEach(function() {
|
||||
select = new ol.interaction.Select();
|
||||
map.addInteraction(select);
|
||||
});
|
||||
|
||||
it('select with single-click', function() {
|
||||
simulateEvent(ol.MapBrowserEvent.EventType.SINGLECLICK, 10, -20);
|
||||
|
||||
var features = select.getFeatures();
|
||||
expect(features.getLength()).to.equal(1);
|
||||
});
|
||||
});
|
||||
|
||||
describe('multiselecting polygons', function() {
|
||||
var select;
|
||||
|
||||
beforeEach(function() {
|
||||
select = new ol.interaction.Select({
|
||||
multi: true
|
||||
});
|
||||
map.addInteraction(select);
|
||||
});
|
||||
|
||||
it('select with single-click', function() {
|
||||
simulateEvent(ol.MapBrowserEvent.EventType.SINGLECLICK, 10, -20);
|
||||
|
||||
var features = select.getFeatures();
|
||||
expect(features.getLength()).to.equal(2);
|
||||
});
|
||||
});
|
||||
|
||||
describe('#setActive()', function() {
|
||||
var interaction;
|
||||
|
||||
beforeEach(function() {
|
||||
interaction = new ol.interaction.Select();
|
||||
|
||||
expect(interaction.getActive()).to.be(true);
|
||||
|
||||
map.addInteraction(interaction);
|
||||
|
||||
expect(interaction.featureOverlay_).not.to.be(null);
|
||||
|
||||
simulateEvent(ol.MapBrowserEvent.EventType.SINGLECLICK, 10, -20);
|
||||
});
|
||||
|
||||
afterEach(function() {
|
||||
map.removeInteraction(interaction);
|
||||
});
|
||||
|
||||
describe('#setActive(false)', function() {
|
||||
it('keeps the the selection', function() {
|
||||
interaction.setActive(false);
|
||||
expect(interaction.getFeatures().getLength()).to.equal(1);
|
||||
});
|
||||
});
|
||||
|
||||
describe('#setActive(true)', function() {
|
||||
beforeEach(function() {
|
||||
interaction.setActive(false);
|
||||
});
|
||||
it('sets the map into the feature overlay', function() {
|
||||
interaction.setActive(true);
|
||||
expect(interaction.featureOverlay_.map_).to.be(map);
|
||||
});
|
||||
it('fires change:active', function() {
|
||||
var listenerSpy = sinon.spy(function() {
|
||||
// test that the interaction's change:active listener is called first
|
||||
expect(interaction.featureOverlay_.map_).not.to.be(null);
|
||||
});
|
||||
interaction.on('change:active', listenerSpy);
|
||||
interaction.setActive(true);
|
||||
expect(listenerSpy.callCount).to.be(1);
|
||||
});
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
describe('#setMap()', function() {
|
||||
var interaction;
|
||||
|
||||
beforeEach(function() {
|
||||
interaction = new ol.interaction.Select();
|
||||
expect(interaction.getActive()).to.be(true);
|
||||
});
|
||||
|
||||
describe('#setMap(null)', function() {
|
||||
beforeEach(function() {
|
||||
map.addInteraction(interaction);
|
||||
});
|
||||
afterEach(function() {
|
||||
map.removeInteraction(interaction);
|
||||
});
|
||||
describe('#setMap(null) when interaction is active', function() {
|
||||
it('unsets the map from the feature overlay', function() {
|
||||
interaction.setMap(null);
|
||||
expect(interaction.featureOverlay_.map_).to.be(null);
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
describe('#setMap(map)', function() {
|
||||
describe('#setMap(map) when interaction is active', function() {
|
||||
it('sets the map into the feature overlay', function() {
|
||||
interaction.setMap(map);
|
||||
expect(interaction.featureOverlay_.map_).to.be(map);
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
goog.require('goog.dispose');
|
||||
goog.require('goog.events');
|
||||
goog.require('goog.events.BrowserEvent');
|
||||
goog.require('goog.style');
|
||||
goog.require('ol.Feature');
|
||||
goog.require('ol.Map');
|
||||
goog.require('ol.MapBrowserEvent.EventType');
|
||||
goog.require('ol.MapBrowserPointerEvent');
|
||||
goog.require('ol.View');
|
||||
goog.require('ol.geom.Polygon');
|
||||
goog.require('ol.interaction.Select');
|
||||
goog.require('ol.interaction.Interaction');
|
||||
goog.require('ol.layer.Vector');
|
||||
goog.require('ol.pointer.PointerEvent');
|
||||
goog.require('ol.source.Vector');
|
||||
@@ -366,10 +366,15 @@ describe('ol.proj', function() {
|
||||
'+proj=lcc +lat_1=29.3 +lat_2=30.7 +lat_0=28.66666666666667 ' +
|
||||
'+lon_0=-91.33333333333333 +x_0=609601.2192024384 +y_0=0 ' +
|
||||
'+ellps=clrk66 +datum=NAD27 +to_meter=0.3048006096012192 +no_defs');
|
||||
proj4.defs('EPSG:3739', '+proj=tmerc +lat_0=40.5 ' +
|
||||
'+lon_0=-110.0833333333333 +k=0.9999375 +x_0=800000.0000101599 ' +
|
||||
'+y_0=99999.99998983997 +ellps=GRS80 +towgs84=0,0,0,0,0,0,0 ' +
|
||||
'+units=us-ft +no_defs');
|
||||
});
|
||||
|
||||
afterEach(function() {
|
||||
delete proj4.defs['EPSG:26782'];
|
||||
delete proj4.defs['EPSG:3739'];
|
||||
});
|
||||
|
||||
it('returns value in meters', function() {
|
||||
@@ -382,6 +387,11 @@ describe('ol.proj', function() {
|
||||
expect(epsg26782.getMetersPerUnit()).to.eql(0.3048006096012192);
|
||||
});
|
||||
|
||||
it('works for proj4js projections with units other than m', function() {
|
||||
var epsg3739 = ol.proj.get('EPSG:3739');
|
||||
expect(epsg3739.getMetersPerUnit()).to.eql(1200 / 3937);
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
@@ -82,7 +82,7 @@ describe('ol.render.canvas.LineStringReplay', function() {
|
||||
|
||||
describe('#getBufferedMaxExtent()', function() {
|
||||
|
||||
it('buffers the max extent to accomodate stroke width', function() {
|
||||
it('buffers the max extent to accommodate stroke width', function() {
|
||||
var tolerance = 1;
|
||||
var extent = [-180, -90, 180, 90];
|
||||
var resolution = 10;
|
||||
@@ -104,7 +104,7 @@ describe('ol.render.canvas.PolygonReplay', function() {
|
||||
|
||||
describe('#getBufferedMaxExtent()', function() {
|
||||
|
||||
it('buffers the max extent to accomodate stroke width', function() {
|
||||
it('buffers the max extent to accommodate stroke width', function() {
|
||||
var tolerance = 1;
|
||||
var extent = [-180, -90, 180, 90];
|
||||
var resolution = 10;
|
||||
|
||||
@@ -5,10 +5,8 @@ describe('ol.renderer.Layer', function() {
|
||||
var eventType = goog.events.EventType.CHANGE;
|
||||
|
||||
beforeEach(function() {
|
||||
var map = new ol.Map({});
|
||||
var mapRenderer = map.getRenderer();
|
||||
var layer = new ol.layer.Layer({});
|
||||
renderer = new ol.renderer.Layer(mapRenderer, layer);
|
||||
renderer = new ol.renderer.Layer(layer);
|
||||
});
|
||||
|
||||
describe('#loadImage', function() {
|
||||
@@ -84,6 +82,5 @@ describe('ol.renderer.Layer', function() {
|
||||
goog.require('goog.events.EventType');
|
||||
goog.require('ol.Image');
|
||||
goog.require('ol.ImageState');
|
||||
goog.require('ol.Map');
|
||||
goog.require('ol.layer.Layer');
|
||||
goog.require('ol.renderer.Layer');
|
||||
|
||||
242
test/spec/ol/source/tilearcgisrestsource.test.js
Normal file
242
test/spec/ol/source/tilearcgisrestsource.test.js
Normal file
@@ -0,0 +1,242 @@
|
||||
goog.provide('ol.test.source.TileArcGISRest');
|
||||
|
||||
|
||||
describe('ol.source.TileArcGISRest', function() {
|
||||
|
||||
var options;
|
||||
beforeEach(function() {
|
||||
options = {
|
||||
params: {},
|
||||
url: 'http://example.com/MapServer'
|
||||
};
|
||||
});
|
||||
|
||||
describe('#getTile', function() {
|
||||
|
||||
it('returns a tile with the expected URL', function() {
|
||||
var source = new ol.source.TileArcGISRest(options);
|
||||
var tile = source.getTile(3, 2, 1, 1, ol.proj.get('EPSG:3857'));
|
||||
expect(tile).to.be.an(ol.ImageTile);
|
||||
var uri = new goog.Uri(tile.src_);
|
||||
expect(uri.getScheme()).to.be('http');
|
||||
expect(uri.getDomain()).to.be('example.com');
|
||||
expect(uri.getPath()).to.be('/MapServer/export');
|
||||
var queryData = uri.getQueryData();
|
||||
expect(queryData.get('BBOX')).to.be(
|
||||
'-10018754.171394622,-15028131.257091932,' +
|
||||
'-5009377.085697311,-10018754.17139462');
|
||||
expect(queryData.get('FORMAT')).to.be('PNG32');
|
||||
expect(queryData.get('SIZE')).to.be('256,256');
|
||||
expect(queryData.get('IMAGESR')).to.be('3857');
|
||||
expect(queryData.get('BBOXSR')).to.be('3857');
|
||||
expect(queryData.get('TRANSPARENT')).to.be('true');
|
||||
|
||||
});
|
||||
|
||||
it('returns a tile with the expected URL with url list', function() {
|
||||
|
||||
options.urls = ['http://test1.com/MapServer',
|
||||
'http://test2.com/MapServer'];
|
||||
var source = new ol.source.TileArcGISRest(options);
|
||||
|
||||
var tile = source.getTile(3, 2, 1, 1, ol.proj.get('EPSG:3857'));
|
||||
expect(tile).to.be.an(ol.ImageTile);
|
||||
var uri = new goog.Uri(tile.src_);
|
||||
expect(uri.getScheme()).to.be('http');
|
||||
expect(uri.getDomain()).to.match(/test[12]\.com/);
|
||||
expect(uri.getPath()).to.be('/MapServer/export');
|
||||
var queryData = uri.getQueryData();
|
||||
expect(queryData.get('BBOX')).to.be(
|
||||
'-10018754.171394622,-15028131.257091932,' +
|
||||
'-5009377.085697311,-10018754.17139462');
|
||||
expect(queryData.get('FORMAT')).to.be('PNG32');
|
||||
expect(queryData.get('SIZE')).to.be('256,256');
|
||||
expect(queryData.get('IMAGESR')).to.be('3857');
|
||||
expect(queryData.get('BBOXSR')).to.be('3857');
|
||||
expect(queryData.get('TRANSPARENT')).to.be('true');
|
||||
|
||||
});
|
||||
|
||||
it('returns a tile with the expected URL for ImageServer', function() {
|
||||
options.url = 'http://example.com/ImageServer';
|
||||
var source = new ol.source.TileArcGISRest(options);
|
||||
var tile = source.getTile(3, 2, 1, 1, ol.proj.get('EPSG:3857'));
|
||||
expect(tile).to.be.an(ol.ImageTile);
|
||||
var uri = new goog.Uri(tile.src_);
|
||||
expect(uri.getScheme()).to.be('http');
|
||||
expect(uri.getDomain()).to.be('example.com');
|
||||
expect(uri.getPath()).to.be('/ImageServer/exportImage');
|
||||
var queryData = uri.getQueryData();
|
||||
expect(queryData.get('BBOX')).to.be(
|
||||
'-10018754.171394622,-15028131.257091932,' +
|
||||
'-5009377.085697311,-10018754.17139462');
|
||||
expect(queryData.get('FORMAT')).to.be('PNG32');
|
||||
expect(queryData.get('SIZE')).to.be('256,256');
|
||||
expect(queryData.get('IMAGESR')).to.be('3857');
|
||||
expect(queryData.get('BBOXSR')).to.be('3857');
|
||||
expect(queryData.get('TRANSPARENT')).to.be('true');
|
||||
});
|
||||
|
||||
it('allows various parameters to be overridden', function() {
|
||||
options.params.FORMAT = 'png';
|
||||
options.params.TRANSPARENT = false;
|
||||
var source = new ol.source.TileArcGISRest(options);
|
||||
var tile = source.getTile(3, 2, 1, 1, ol.proj.get('EPSG:4326'));
|
||||
var uri = new goog.Uri(tile.src_);
|
||||
var queryData = uri.getQueryData();
|
||||
expect(queryData.get('FORMAT')).to.be('png');
|
||||
expect(queryData.get('TRANSPARENT')).to.be('false');
|
||||
});
|
||||
|
||||
it('allows adding rest option', function() {
|
||||
options.params.LAYERS = 'show:1,3,4';
|
||||
var source = new ol.source.TileArcGISRest(options);
|
||||
var tile = source.getTile(3, 2, 1, 1, ol.proj.get('EPSG:4326'));
|
||||
var uri = new goog.Uri(tile.src_);
|
||||
var queryData = uri.getQueryData();
|
||||
expect(queryData.get('LAYERS')).to.be('show:1,3,4');
|
||||
});
|
||||
});
|
||||
|
||||
describe('#updateParams', function() {
|
||||
|
||||
it('add a new param', function() {
|
||||
var source = new ol.source.TileArcGISRest(options);
|
||||
source.updateParams({ 'TEST': 'value' });
|
||||
|
||||
var tile = source.getTile(3, 2, 1, 1, ol.proj.get('EPSG:3857'));
|
||||
var uri = new goog.Uri(tile.src_);
|
||||
var queryData = uri.getQueryData();
|
||||
|
||||
expect(queryData.get('TEST')).to.be('value');
|
||||
});
|
||||
|
||||
it('updates an existing param', function() {
|
||||
options.params.TEST = 'value';
|
||||
|
||||
var source = new ol.source.TileArcGISRest(options);
|
||||
source.updateParams({ 'TEST': 'newValue' });
|
||||
|
||||
var tile = source.getTile(3, 2, 1, 1, ol.proj.get('EPSG:3857'));
|
||||
var uri = new goog.Uri(tile.src_);
|
||||
var queryData = uri.getQueryData();
|
||||
|
||||
expect(queryData.get('TEST')).to.be('newValue');
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
describe('#getParams', function() {
|
||||
|
||||
it('verify getting a param', function() {
|
||||
options.params.TEST = 'value';
|
||||
var source = new ol.source.TileArcGISRest(options);
|
||||
|
||||
var setParams = source.getParams();
|
||||
|
||||
expect(setParams).to.eql({ TEST: 'value' });
|
||||
});
|
||||
|
||||
it('verify on adding a param', function() {
|
||||
options.params.TEST = 'value';
|
||||
|
||||
var source = new ol.source.TileArcGISRest(options);
|
||||
source.updateParams({ 'TEST2': 'newValue' });
|
||||
|
||||
var setParams = source.getParams();
|
||||
|
||||
expect(setParams).to.eql({ TEST: 'value', TEST2: 'newValue' });
|
||||
});
|
||||
|
||||
it('verify on update a param', function() {
|
||||
options.params.TEST = 'value';
|
||||
|
||||
var source = new ol.source.TileArcGISRest(options);
|
||||
source.updateParams({ 'TEST': 'newValue' });
|
||||
|
||||
var setParams = source.getParams();
|
||||
|
||||
expect(setParams).to.eql({ TEST: 'newValue' });
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
describe('#getUrls', function() {
|
||||
|
||||
it('verify getting array of urls', function() {
|
||||
options.urls = ['http://test.com/MapServer',
|
||||
'http://test2.com/MapServer'];
|
||||
|
||||
var source = new ol.source.TileArcGISRest(options);
|
||||
|
||||
var urls = source.getUrls();
|
||||
|
||||
expect(urls).to.eql(['http://test.com/MapServer',
|
||||
'http://test2.com/MapServer']);
|
||||
});
|
||||
|
||||
|
||||
});
|
||||
|
||||
describe('#setUrls', function() {
|
||||
|
||||
it('verify setting urls when not set yet', function() {
|
||||
|
||||
var source = new ol.source.TileArcGISRest(options);
|
||||
source.setUrls(['http://test.com/MapServer',
|
||||
'http://test2.com/MapServer']);
|
||||
|
||||
var urls = source.getUrls();
|
||||
|
||||
expect(urls).to.eql(['http://test.com/MapServer',
|
||||
'http://test2.com/MapServer']);
|
||||
});
|
||||
|
||||
it('verify setting urls with existing list', function() {
|
||||
options.urls = ['http://test.com/MapServer',
|
||||
'http://test2.com/MapServer'];
|
||||
|
||||
var source = new ol.source.TileArcGISRest(options);
|
||||
source.setUrls(['http://test3.com/MapServer',
|
||||
'http://test4.com/MapServer']);
|
||||
|
||||
var urls = source.getUrls();
|
||||
|
||||
expect(urls).to.eql(['http://test3.com/MapServer',
|
||||
'http://test4.com/MapServer']);
|
||||
});
|
||||
});
|
||||
|
||||
describe('#setUrl', function() {
|
||||
|
||||
it('verify setting url with no urls', function() {
|
||||
|
||||
var source = new ol.source.TileArcGISRest(options);
|
||||
source.setUrl('http://test.com/MapServer');
|
||||
|
||||
var urls = source.getUrls();
|
||||
|
||||
expect(urls).to.eql(['http://test.com/MapServer']);
|
||||
});
|
||||
|
||||
it('verify setting url with list of urls', function() {
|
||||
options.urls = ['http://test.com/MapServer',
|
||||
'http://test2.com/MapServer'];
|
||||
|
||||
var source = new ol.source.TileArcGISRest(options);
|
||||
source.setUrl('http://test3.com/MapServer');
|
||||
|
||||
var urls = source.getUrls();
|
||||
|
||||
expect(urls).to.eql(['http://test3.com/MapServer']);
|
||||
});
|
||||
|
||||
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
goog.require('goog.Uri');
|
||||
goog.require('ol.ImageTile');
|
||||
goog.require('ol.source.TileArcGISRest');
|
||||
goog.require('ol.proj');
|
||||
@@ -12,176 +12,105 @@ describe('ol.source.Tile', function() {
|
||||
});
|
||||
});
|
||||
|
||||
describe('#findLoadedTiles()', function() {
|
||||
describe('#forEachLoadedTile()', function() {
|
||||
|
||||
it('adds no tiles if none are already loaded', function() {
|
||||
// a source with no loaded tiles
|
||||
var callback;
|
||||
beforeEach(function() {
|
||||
callback = sinon.spy();
|
||||
});
|
||||
|
||||
it('does not call the callback if no tiles are loaded', function() {
|
||||
var source = new ol.test.source.TileMock({});
|
||||
|
||||
var loadedTilesByZ = {};
|
||||
var grid = source.getTileGrid();
|
||||
var extent = [-180, -180, 180, 180];
|
||||
var range = grid.getTileRangeForExtentAndZ(extent, 3);
|
||||
var zoom = 3;
|
||||
var range = grid.getTileRangeForExtentAndZ(extent, zoom);
|
||||
|
||||
function getTileIfLoaded(z, x, y) {
|
||||
var tile = source.getTile(z, x, y);
|
||||
return (!goog.isNull(tile) && tile.getState() === ol.TileState.LOADED) ?
|
||||
tile : null;
|
||||
}
|
||||
source.findLoadedTiles(loadedTilesByZ, getTileIfLoaded, 3, range);
|
||||
|
||||
var keys = goog.object.getKeys(loadedTilesByZ);
|
||||
expect(keys.length).to.be(0);
|
||||
source.forEachLoadedTile(zoom, range, callback);
|
||||
expect(callback.callCount).to.be(0);
|
||||
});
|
||||
|
||||
it('adds loaded tiles to the lookup (z: 0)', function() {
|
||||
// a source with no loaded tiles
|
||||
var source = new ol.test.source.TileMock({
|
||||
'0/0/0': true,
|
||||
'1/0/0': true
|
||||
});
|
||||
|
||||
var loadedTilesByZ = {};
|
||||
var grid = source.getTileGrid();
|
||||
var extent = [-180, -180, 180, 180];
|
||||
var range = grid.getTileRangeForExtentAndZ(extent, 0);
|
||||
|
||||
function getTileIfLoaded(z, x, y) {
|
||||
var tile = source.getTile(z, x, y);
|
||||
return (!goog.isNull(tile) && tile.getState() === ol.TileState.LOADED) ?
|
||||
tile : null;
|
||||
}
|
||||
source.findLoadedTiles(loadedTilesByZ, getTileIfLoaded, 0, range);
|
||||
var keys = goog.object.getKeys(loadedTilesByZ);
|
||||
expect(keys.length).to.be(1);
|
||||
var tile = loadedTilesByZ['0']['0/0/0'];
|
||||
expect(tile).to.be.a(ol.Tile);
|
||||
expect(tile.state).to.be(ol.TileState.LOADED);
|
||||
});
|
||||
|
||||
it('adds loaded tiles to the lookup (z: 1)', function() {
|
||||
// a source with no loaded tiles
|
||||
var source = new ol.test.source.TileMock({
|
||||
'0/0/0': true,
|
||||
'1/0/0': true
|
||||
});
|
||||
|
||||
var loadedTilesByZ = {};
|
||||
var grid = source.getTileGrid();
|
||||
var extent = [-180, -180, 180, 180];
|
||||
var range = grid.getTileRangeForExtentAndZ(extent, 1);
|
||||
|
||||
function getTileIfLoaded(z, x, y) {
|
||||
var tile = source.getTile(z, x, y);
|
||||
return (!goog.isNull(tile) && tile.getState() === ol.TileState.LOADED) ?
|
||||
tile : null;
|
||||
}
|
||||
source.findLoadedTiles(loadedTilesByZ, getTileIfLoaded, 1, range);
|
||||
var keys = goog.object.getKeys(loadedTilesByZ);
|
||||
expect(keys.length).to.be(1);
|
||||
var tile = loadedTilesByZ['1']['1/0/0'];
|
||||
expect(tile).to.be.a(ol.Tile);
|
||||
expect(tile.state).to.be(ol.TileState.LOADED);
|
||||
});
|
||||
|
||||
it('returns true when all tiles are already loaded', function() {
|
||||
// a source with no loaded tiles
|
||||
var source = new ol.test.source.TileMock({
|
||||
'1/0/0': true,
|
||||
'1/0/1': true,
|
||||
'1/1/0': true,
|
||||
'1/1/1': true
|
||||
});
|
||||
|
||||
var loadedTilesByZ = {};
|
||||
var grid = source.getTileGrid();
|
||||
var extent = [-180, -180, 180, 180];
|
||||
var range = grid.getTileRangeForExtentAndZ(extent, 1);
|
||||
function getTileIfLoaded(z, x, y) {
|
||||
var tile = source.getTile(z, x, y);
|
||||
return (!goog.isNull(tile) && tile.getState() === ol.TileState.LOADED) ?
|
||||
tile : null;
|
||||
}
|
||||
var loaded = source.findLoadedTiles(
|
||||
loadedTilesByZ, getTileIfLoaded, 1, range);
|
||||
expect(loaded).to.be(true);
|
||||
});
|
||||
|
||||
it('returns true when all tiles are already loaded (part 2)', function() {
|
||||
// a source with no loaded tiles
|
||||
it('does not call getTile() if no tiles are loaded', function() {
|
||||
var source = new ol.test.source.TileMock({});
|
||||
|
||||
var loadedTilesByZ = {
|
||||
'1': {
|
||||
'1/0/0': true,
|
||||
'1/0/1': true,
|
||||
'1/1/0': true,
|
||||
'1/1/1': true,
|
||||
'1/1/2': true
|
||||
}
|
||||
};
|
||||
sinon.spy(source, 'getTile');
|
||||
var grid = source.getTileGrid();
|
||||
var extent = [-180, -180, 180, 180];
|
||||
var range = grid.getTileRangeForExtentAndZ(extent, 1);
|
||||
var zoom = 3;
|
||||
var range = grid.getTileRangeForExtentAndZ(extent, zoom);
|
||||
|
||||
function getTileIfLoaded(z, x, y) {
|
||||
var tile = source.getTile(z, x, y);
|
||||
return (!goog.isNull(tile) && tile.getState() === ol.TileState.LOADED) ?
|
||||
tile : null;
|
||||
}
|
||||
var loaded = source.findLoadedTiles(
|
||||
loadedTilesByZ, getTileIfLoaded, 1, range);
|
||||
expect(loaded).to.be(true);
|
||||
source.forEachLoadedTile(zoom, range, callback);
|
||||
expect(source.getTile.callCount).to.be(0);
|
||||
source.getTile.restore();
|
||||
});
|
||||
|
||||
it('returns false when all tiles are already loaded', function() {
|
||||
// a source with no loaded tiles
|
||||
|
||||
it('calls callback for each loaded tile', function() {
|
||||
var source = new ol.test.source.TileMock({
|
||||
'1/0/0': true,
|
||||
'1/0/1': true,
|
||||
'1/1/0': true,
|
||||
'1/1/1': false
|
||||
'1/0/0': ol.TileState.LOADED,
|
||||
'1/0/1': ol.TileState.LOADED,
|
||||
'1/1/0': ol.TileState.LOADING,
|
||||
'1/1/1': ol.TileState.LOADED
|
||||
});
|
||||
|
||||
var loadedTilesByZ = {};
|
||||
var grid = source.getTileGrid();
|
||||
var extent = [-180, -180, 180, 180];
|
||||
var range = grid.getTileRangeForExtentAndZ(extent, 1);
|
||||
var zoom = 1;
|
||||
var range = new ol.TileRange(0, 1, 0, 1);
|
||||
|
||||
function getTileIfLoaded(z, x, y) {
|
||||
var tile = source.getTile(z, x, y);
|
||||
return (!goog.isNull(tile) && tile.getState() === ol.TileState.LOADED) ?
|
||||
tile : null;
|
||||
}
|
||||
var loaded = source.findLoadedTiles(
|
||||
loadedTilesByZ, getTileIfLoaded, 1, range);
|
||||
expect(loaded).to.be(false);
|
||||
source.forEachLoadedTile(zoom, range, callback);
|
||||
expect(callback.callCount).to.be(3);
|
||||
});
|
||||
|
||||
it('returns false when all tiles are already loaded (part 2)', function() {
|
||||
it('returns true if range is fully loaded', function() {
|
||||
// a source with no loaded tiles
|
||||
var source = new ol.test.source.TileMock({});
|
||||
var source = new ol.test.source.TileMock({
|
||||
'1/0/0': ol.TileState.LOADED,
|
||||
'1/0/1': ol.TileState.LOADED,
|
||||
'1/1/0': ol.TileState.LOADED,
|
||||
'1/1/1': ol.TileState.LOADED
|
||||
});
|
||||
|
||||
var loadedTilesByZ = {
|
||||
'1': {
|
||||
'1/0/0': true,
|
||||
'1/0/1': true,
|
||||
'1/1/0': true,
|
||||
'1/1/1': false
|
||||
}
|
||||
};
|
||||
var grid = source.getTileGrid();
|
||||
var extent = [-180, -180, 180, 180];
|
||||
var range = grid.getTileRangeForExtentAndZ(extent, 1);
|
||||
var zoom = 1;
|
||||
var range = new ol.TileRange(0, 1, 0, 1);
|
||||
|
||||
function getTileIfLoaded(z, x, y) {
|
||||
var tile = source.getTile(z, x, y);
|
||||
return (!goog.isNull(tile) && tile.getState() === ol.TileState.LOADED) ?
|
||||
tile : null;
|
||||
}
|
||||
var loaded = source.findLoadedTiles(
|
||||
loadedTilesByZ, getTileIfLoaded, 1, range);
|
||||
expect(loaded).to.be(false);
|
||||
var covered = source.forEachLoadedTile(zoom, range, function() {
|
||||
return true;
|
||||
});
|
||||
expect(covered).to.be(true);
|
||||
});
|
||||
|
||||
it('returns false if range is not fully loaded', function() {
|
||||
// a source with no loaded tiles
|
||||
var source = new ol.test.source.TileMock({
|
||||
'1/0/0': ol.TileState.LOADED,
|
||||
'1/0/1': ol.TileState.LOADED,
|
||||
'1/1/0': ol.TileState.LOADING,
|
||||
'1/1/1': ol.TileState.LOADED
|
||||
});
|
||||
|
||||
var zoom = 1;
|
||||
var range = new ol.TileRange(0, 1, 0, 1);
|
||||
|
||||
var covered = source.forEachLoadedTile(zoom, range, function() {
|
||||
return true;
|
||||
});
|
||||
expect(covered).to.be(false);
|
||||
});
|
||||
|
||||
it('allows callback to override loaded check', function() {
|
||||
// a source with no loaded tiles
|
||||
var source = new ol.test.source.TileMock({
|
||||
'1/0/0': ol.TileState.LOADED,
|
||||
'1/0/1': ol.TileState.LOADED,
|
||||
'1/1/0': ol.TileState.LOADED,
|
||||
'1/1/1': ol.TileState.LOADED
|
||||
});
|
||||
|
||||
var zoom = 1;
|
||||
var range = new ol.TileRange(0, 1, 0, 1);
|
||||
|
||||
var covered = source.forEachLoadedTile(zoom, range, function() {
|
||||
return false;
|
||||
});
|
||||
expect(covered).to.be(false);
|
||||
});
|
||||
|
||||
});
|
||||
@@ -196,9 +125,10 @@ describe('ol.source.Tile', function() {
|
||||
*
|
||||
* @constructor
|
||||
* @extends {ol.source.Tile}
|
||||
* @param {Object.<string, boolean>} loaded Lookup of already loaded tiles.
|
||||
* @param {Object.<string, ol.TileState>} tileStates Lookup of tile key to
|
||||
* tile state.
|
||||
*/
|
||||
ol.test.source.TileMock = function(loaded) {
|
||||
ol.test.source.TileMock = function(tileStates) {
|
||||
var tileGrid = new ol.tilegrid.TileGrid({
|
||||
resolutions: [360 / 256, 180 / 256, 90 / 256, 45 / 256],
|
||||
origin: [-180, -180],
|
||||
@@ -210,11 +140,9 @@ ol.test.source.TileMock = function(loaded) {
|
||||
tileGrid: tileGrid
|
||||
});
|
||||
|
||||
/**
|
||||
* @type {Object.<string, boolean>}
|
||||
* @private
|
||||
*/
|
||||
this.loaded_ = loaded;
|
||||
for (var key in tileStates) {
|
||||
this.tileCache.set(key, new ol.Tile(key.split('/'), tileStates[key]));
|
||||
}
|
||||
|
||||
};
|
||||
goog.inherits(ol.test.source.TileMock, ol.source.Tile);
|
||||
@@ -224,9 +152,14 @@ goog.inherits(ol.test.source.TileMock, ol.source.Tile);
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.test.source.TileMock.prototype.getTile = function(z, x, y) {
|
||||
var key = ol.tilecoord.getKeyZXY(z, x, y);
|
||||
var tileState = this.loaded_[key] ? ol.TileState.LOADED : ol.TileState.IDLE;
|
||||
return new ol.Tile([z, x, y], tileState);
|
||||
var key = this.getKeyZXY(z, x, y);
|
||||
if (this.tileCache.containsKey(key)) {
|
||||
return /** @type {!ol.Tile} */ (this.tileCache.get(key));
|
||||
} else {
|
||||
var tile = new ol.Tile(key, ol.TileState.IDLE);
|
||||
this.tileCache.set(key, tile);
|
||||
return tile;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -243,8 +176,8 @@ describe('ol.test.source.TileMock', function() {
|
||||
describe('#getTile()', function() {
|
||||
it('returns a tile with state based on constructor arg', function() {
|
||||
var source = new ol.test.source.TileMock({
|
||||
'0/0/0': true,
|
||||
'1/0/0': true
|
||||
'0/0/0': ol.TileState.LOADED,
|
||||
'1/0/0': ol.TileState.LOADED
|
||||
});
|
||||
var tile;
|
||||
|
||||
@@ -270,9 +203,9 @@ describe('ol.test.source.TileMock', function() {
|
||||
|
||||
goog.require('goog.object');
|
||||
goog.require('ol.Tile');
|
||||
goog.require('ol.TileRange');
|
||||
goog.require('ol.TileState');
|
||||
goog.require('ol.proj');
|
||||
goog.require('ol.source.Source');
|
||||
goog.require('ol.source.Tile');
|
||||
goog.require('ol.tilecoord');
|
||||
goog.require('ol.tilegrid.TileGrid');
|
||||
|
||||
143
test/spec/ol/source/wmtssource.test.js
Normal file
143
test/spec/ol/source/wmtssource.test.js
Normal file
@@ -0,0 +1,143 @@
|
||||
goog.provide('ol.test.source.WMTS');
|
||||
|
||||
describe('ol.source.WMTS', function() {
|
||||
|
||||
describe('when creating options from capabilities', function() {
|
||||
var parser = new ol.format.WMTSCapabilities();
|
||||
var capabilities;
|
||||
before(function(done) {
|
||||
afterLoadText('spec/ol/format/wmts/ogcsample.xml', function(xml) {
|
||||
try {
|
||||
capabilities = parser.read(xml);
|
||||
} catch (e) {
|
||||
done(e);
|
||||
}
|
||||
done();
|
||||
});
|
||||
});
|
||||
|
||||
it('can create KVP options from spec/ol/format/wmts/ogcsample.xml',
|
||||
function() {
|
||||
var options;
|
||||
options = ol.source.WMTS.optionsFromCapabilities(
|
||||
capabilities,
|
||||
{ layer: 'BlueMarbleNextGeneration', matrixSet: 'google3857' });
|
||||
|
||||
expect(options.urls).to.be.an('array');
|
||||
expect(options.urls).to.have.length(1);
|
||||
expect(options.urls[0]).to.be.eql(
|
||||
'http://www.maps.bob/cgi-bin/MiraMon5_0.cgi?');
|
||||
|
||||
expect(options.layer).to.be.eql('BlueMarbleNextGeneration');
|
||||
|
||||
expect(options.matrixSet).to.be.eql('google3857');
|
||||
|
||||
expect(options.format).to.be.eql('image/jpeg');
|
||||
|
||||
expect(options.projection).to.be.a(ol.proj.Projection);
|
||||
expect(options.projection).to.be.eql(ol.proj.get('EPSG:3857'));
|
||||
|
||||
expect(options.requestEncoding).to.be.eql('KVP');
|
||||
|
||||
expect(options.tileGrid).to.be.a(ol.tilegrid.WMTS);
|
||||
|
||||
expect(options.style).to.be.eql('DarkBlue');
|
||||
|
||||
expect(options.dimensions).to.eql({});
|
||||
|
||||
});
|
||||
|
||||
it('can create REST options from spec/ol/format/wmts/ogcsample.xml',
|
||||
function() {
|
||||
var options;
|
||||
options = ol.source.WMTS.optionsFromCapabilities(
|
||||
capabilities,
|
||||
{ layer: 'BlueMarbleNextGeneration', matrixSet: 'google3857',
|
||||
requestEncoding: 'REST' });
|
||||
|
||||
expect(options.urls).to.be.an('array');
|
||||
expect(options.urls).to.have.length(1);
|
||||
expect(options.urls[0]).to.be.eql(
|
||||
'http://www.example.com/wmts/coastlines/{TileMatrix}/{TileRow}/{TileCol}.png');
|
||||
|
||||
expect(options.layer).to.be.eql('BlueMarbleNextGeneration');
|
||||
|
||||
expect(options.matrixSet).to.be.eql('google3857');
|
||||
|
||||
expect(options.format).to.be.eql('image/png');
|
||||
|
||||
expect(options.projection).to.be.a(ol.proj.Projection);
|
||||
expect(options.projection).to.be.eql(ol.proj.get('EPSG:3857'));
|
||||
|
||||
expect(options.requestEncoding).to.be.eql('REST');
|
||||
|
||||
expect(options.tileGrid).to.be.a(ol.tilegrid.WMTS);
|
||||
|
||||
expect(options.style).to.be.eql('DarkBlue');
|
||||
|
||||
expect(options.dimensions).to.eql({});
|
||||
|
||||
});
|
||||
});
|
||||
|
||||
describe('when creating tileUrlFunction', function() {
|
||||
|
||||
it('can replace lowercase REST parameters',
|
||||
function() {
|
||||
var source = new ol.source.WMTS({
|
||||
layer: 'layer',
|
||||
style: 'default',
|
||||
urls: ['http://www.example.com/wmts/coastlines/{layer}/{style}/' +
|
||||
'{tilematrixset}/{TileMatrix}/{TileCol}/{TileRow}.jpg'],
|
||||
matrixSet: 'EPSG:3857',
|
||||
requestEncoding: 'REST',
|
||||
tileGrid: new ol.tilegrid.WMTS({
|
||||
origin: [-20037508.342789244, 20037508.342789244],
|
||||
resolutions: [559082264.029 * 0.28E-3,
|
||||
279541132.015 * 0.28E-3,
|
||||
139770566.007 * 0.28E-3],
|
||||
matrixIds: [0, 1, 2]
|
||||
})
|
||||
});
|
||||
|
||||
var projection = ol.proj.get('EPSG:3857');
|
||||
var url = source.tileUrlFunction.call(source,
|
||||
[1, 1, -2], 1, projection);
|
||||
expect(url).to.be.eql('http://www.example.com/wmts/coastlines/' +
|
||||
'layer/default/EPSG:3857/1/1/1.jpg');
|
||||
|
||||
});
|
||||
|
||||
it('can replace camelcase REST parameters',
|
||||
function() {
|
||||
var source = new ol.source.WMTS({
|
||||
layer: 'layer',
|
||||
style: 'default',
|
||||
urls: ['http://www.example.com/wmts/coastlines/{Layer}/{Style}/' +
|
||||
'{tilematrixset}/{TileMatrix}/{TileCol}/{TileRow}.jpg'],
|
||||
matrixSet: 'EPSG:3857',
|
||||
requestEncoding: 'REST',
|
||||
tileGrid: new ol.tilegrid.WMTS({
|
||||
origin: [-20037508.342789244, 20037508.342789244],
|
||||
resolutions: [559082264.029 * 0.28E-3,
|
||||
279541132.015 * 0.28E-3,
|
||||
139770566.007 * 0.28E-3],
|
||||
matrixIds: [0, 1, 2]
|
||||
})
|
||||
});
|
||||
|
||||
var projection = ol.proj.get('EPSG:3857');
|
||||
var url = source.tileUrlFunction.call(source,
|
||||
[1, 1, -2], 1, projection);
|
||||
expect(url).to.be.eql('http://www.example.com/wmts/coastlines/' +
|
||||
'layer/default/EPSG:3857/1/1/1.jpg');
|
||||
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
goog.require('ol.format.WMTSCapabilities');
|
||||
goog.require('ol.proj');
|
||||
goog.require('ol.proj.Projection');
|
||||
goog.require('ol.tilegrid.WMTS');
|
||||
goog.require('ol.source.WMTS');
|
||||
@@ -264,8 +264,30 @@ describe('ol.Sphere', function() {
|
||||
|
||||
});
|
||||
|
||||
describe('Vincenty area', function() {
|
||||
var geometry;
|
||||
before(function(done) {
|
||||
afterLoadText('spec/ol/format/wkt/illinois.wkt', function(wkt) {
|
||||
try {
|
||||
var format = new ol.format.WKT();
|
||||
geometry = format.readGeometry(wkt);
|
||||
} catch (e) {
|
||||
done(e);
|
||||
}
|
||||
done();
|
||||
});
|
||||
});
|
||||
|
||||
it('results match the expected area of Ilinois', function() {
|
||||
var coords = geometry.getPolygon(0).getLinearRing(0).getCoordinates();
|
||||
expect(ol.sphere.WGS84.geodesicArea(coords)).to.equal(145978332359.37125);
|
||||
});
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
|
||||
goog.require('goog.math');
|
||||
goog.require('ol.Sphere');
|
||||
goog.require('ol.sphere.WGS84');
|
||||
goog.require('ol.format.WKT');
|
||||
|
||||
68
test/spec/ol/tilegrid/wmtstilegrid.test.js
Normal file
68
test/spec/ol/tilegrid/wmtstilegrid.test.js
Normal file
@@ -0,0 +1,68 @@
|
||||
goog.provide('ol.test.tilegrid.WMTS');
|
||||
|
||||
describe('ol.tilegrid.WMTS', function() {
|
||||
|
||||
describe('when creating tileGrid from capabilities', function() {
|
||||
var parser = new ol.format.WMTSCapabilities();
|
||||
var capabilities;
|
||||
before(function(done) {
|
||||
afterLoadText('spec/ol/format/wmts/ogcsample.xml', function(xml) {
|
||||
try {
|
||||
capabilities = parser.read(xml);
|
||||
} catch (e) {
|
||||
done(e);
|
||||
}
|
||||
done();
|
||||
});
|
||||
});
|
||||
|
||||
it('can create tileGrid for EPSG:3857',
|
||||
function() {
|
||||
var matrixSetObj = capabilities.Contents.TileMatrixSet[0];
|
||||
var tileGrid;
|
||||
tileGrid = ol.tilegrid.WMTS.createFromCapabilitiesMatrixSet(
|
||||
matrixSetObj);
|
||||
expect(tileGrid.matrixIds_).to.be.an('array');
|
||||
expect(tileGrid.matrixIds_).to.have.length(20);
|
||||
expect(tileGrid.matrixIds_).to.eql(
|
||||
['0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '10', '11',
|
||||
'12', '13', '14', '15', '16', '17', '18', '19']);
|
||||
|
||||
expect(tileGrid.resolutions_).to.be.an('array');
|
||||
expect(tileGrid.resolutions_).to.have.length(20);
|
||||
expect(tileGrid.resolutions_).to.eql(
|
||||
[156543.03392811998, 78271.51696419998, 39135.758481959994,
|
||||
19567.879241008, 9783.939620504, 4891.969810252, 2445.984905126,
|
||||
1222.9924525644, 611.4962262807999, 305.74811314039994,
|
||||
152.87405657047998, 76.43702828523999, 38.21851414248,
|
||||
19.109257071295996, 9.554628535647998, 4.777314267823999,
|
||||
2.3886571339119995, 1.1943285669559998, 0.5971642834779999,
|
||||
0.29858214174039993]);
|
||||
|
||||
expect(tileGrid.origins_).to.be.an('array');
|
||||
expect(tileGrid.origins_).to.have.length(20);
|
||||
expect(tileGrid.origins_).to.eql(
|
||||
[[-20037508.3428, 20037508.3428], [-20037508.3428, 20037508.3428],
|
||||
[-20037508.3428, 20037508.3428], [-20037508.3428, 20037508.3428],
|
||||
[-20037508.3428, 20037508.3428], [-20037508.3428, 20037508.3428],
|
||||
[-20037508.3428, 20037508.3428], [-20037508.3428, 20037508.3428],
|
||||
[-20037508.3428, 20037508.3428], [-20037508.3428, 20037508.3428],
|
||||
[-20037508.3428, 20037508.3428], [-20037508.3428, 20037508.3428],
|
||||
[-20037508.3428, 20037508.3428], [-20037508.3428, 20037508.3428],
|
||||
[-20037508.3428, 20037508.3428], [-20037508.3428, 20037508.3428],
|
||||
[-20037508.3428, 20037508.3428], [-20037508.3428, 20037508.3428],
|
||||
[-20037508.3428, 20037508.3428], [-20037508.3428, 20037508.3428]
|
||||
]);
|
||||
|
||||
expect(tileGrid.tileSizes_).to.be.an('array');
|
||||
expect(tileGrid.tileSizes_).to.have.length(20);
|
||||
expect(tileGrid.tileSizes_).to.eql(
|
||||
[256, 256, 256, 256, 256, 256, 256, 256, 256, 256,
|
||||
256, 256, 256, 256, 256, 256, 256, 256, 256, 256]);
|
||||
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
goog.require('ol.format.WMTSCapabilities');
|
||||
goog.require('ol.tilegrid.WMTS');
|
||||
Reference in New Issue
Block a user