Merge branch 'master' of github.com:openlayers/ol3 into vector
This commit is contained in:
2
.gitignore
vendored
2
.gitignore
vendored
@@ -1,5 +1,5 @@
|
||||
*.pyc
|
||||
/bin/plovr*.jar
|
||||
/bin/*.pyc
|
||||
/build/gh-pages
|
||||
/build/jsdoc-*-timestamp
|
||||
/build/lint-spec-timestamp
|
||||
|
||||
103
build.py
103
build.py
@@ -9,27 +9,28 @@ import re
|
||||
import shutil
|
||||
import sys
|
||||
|
||||
import pake
|
||||
from pake import Target, ifind, main, output, rule, target, variables, virtual
|
||||
|
||||
|
||||
if sys.platform == 'win32':
|
||||
pake.variables.GIT = 'C:/Program Files/Git/bin/git.exe'
|
||||
pake.variables.GJSLINT = 'gjslint' # FIXME
|
||||
pake.variables.JAVA = 'C:/Program Files/Java/jre7/bin/java.exe'
|
||||
pake.variables.JSDOC = 'jsdoc' # FIXME
|
||||
pake.variables.PHANTOMJS = 'phantomjs' # FIXME
|
||||
pake.variables.PYTHON = 'C:/Python27/python.exe'
|
||||
variables.GIT = 'C:/Program Files/Git/bin/git.exe'
|
||||
variables.GJSLINT = 'gjslint' # FIXME
|
||||
variables.JAVA = 'C:/Program Files/Java/jre7/bin/java.exe'
|
||||
variables.JSDOC = 'jsdoc' # FIXME
|
||||
variables.PHANTOMJS = 'phantomjs' # FIXME
|
||||
variables.PYTHON = 'C:/Python27/python.exe'
|
||||
else:
|
||||
pake.variables.GIT = 'git'
|
||||
pake.variables.GJSLINT = 'gjslint'
|
||||
pake.variables.JAVA = 'java'
|
||||
pake.variables.JSDOC = 'jsdoc'
|
||||
pake.variables.PHANTOMJS = 'phantomjs'
|
||||
pake.variables.PYTHON = 'python'
|
||||
variables.GIT = 'git'
|
||||
variables.GJSLINT = 'gjslint'
|
||||
variables.JAVA = 'java'
|
||||
variables.JSDOC = 'jsdoc'
|
||||
variables.PHANTOMJS = 'phantomjs'
|
||||
variables.PYTHON = 'python'
|
||||
|
||||
pake.variables.BRANCH = pake.output('%(GIT)s', 'rev-parse', '--abbrev-ref', 'HEAD').strip()
|
||||
variables.BRANCH = output('%(GIT)s', 'rev-parse', '--abbrev-ref', 'HEAD').strip()
|
||||
|
||||
EXPORTS = [path
|
||||
for path in pake.ifind('src')
|
||||
for path in ifind('src')
|
||||
if path.endswith('.exports')
|
||||
if path != 'src/objectliterals.exports']
|
||||
|
||||
@@ -43,7 +44,7 @@ EXAMPLES = [path
|
||||
if path != 'examples/example-list.html']
|
||||
|
||||
EXAMPLES_SRC = [path
|
||||
for path in pake.ifind('examples')
|
||||
for path in ifind('examples')
|
||||
if path.endswith('.js')
|
||||
if not path.endswith('.combined.js')
|
||||
if path != 'examples/Jugl.js'
|
||||
@@ -54,11 +55,11 @@ INTERNAL_SRC = [
|
||||
'build/src/internal/src/types.js']
|
||||
|
||||
SPEC = [path
|
||||
for path in pake.ifind('test/spec')
|
||||
for path in ifind('test/spec')
|
||||
if path.endswith('.js')]
|
||||
|
||||
SRC = [path
|
||||
for path in pake.ifind('src/ol')
|
||||
for path in ifind('src/ol')
|
||||
if path.endswith('.js')]
|
||||
|
||||
PLOVR_JAR = 'bin/plovr-eba786b34df9.jar'
|
||||
@@ -75,50 +76,50 @@ def report_sizes(t):
|
||||
t.info(' compressed: %d bytes', len(stringio.getvalue()))
|
||||
|
||||
|
||||
pake.virtual('all', 'build-all', 'build', 'examples')
|
||||
virtual('all', 'build-all', 'build', 'examples')
|
||||
|
||||
|
||||
pake.virtual('precommit', 'lint', 'build-all', 'test', 'doc', 'build', 'build-examples')
|
||||
virtual('precommit', 'lint', 'build-all', 'test', 'build', 'build-examples', 'doc')
|
||||
|
||||
|
||||
pake.virtual('build', 'build/ol.css', 'build/ol.js')
|
||||
virtual('build', 'build/ol.css', 'build/ol.js')
|
||||
|
||||
|
||||
@pake.target('build/ol.css', 'build/ol.js')
|
||||
@target('build/ol.css', 'build/ol.js')
|
||||
def build_ol_css(t):
|
||||
t.touch()
|
||||
|
||||
|
||||
@pake.target('build/ol.js', PLOVR_JAR, SRC, EXTERNAL_SRC, 'base.json', 'build/ol.json')
|
||||
@target('build/ol.js', PLOVR_JAR, SRC, EXTERNAL_SRC, 'base.json', 'build/ol.json')
|
||||
def build_ol_js(t):
|
||||
t.output('%(JAVA)s', '-jar', PLOVR_JAR, 'build', 'build/ol.json')
|
||||
report_sizes(t)
|
||||
|
||||
|
||||
pake.virtual('build-all', 'build/ol-all.js')
|
||||
virtual('build-all', 'build/ol-all.js')
|
||||
|
||||
|
||||
@pake.target('build/ol-all.js', PLOVR_JAR, SRC, INTERNAL_SRC, 'base.json', 'build/ol-all.json')
|
||||
@target('build/ol-all.js', PLOVR_JAR, SRC, INTERNAL_SRC, 'base.json', 'build/ol-all.json')
|
||||
def build_ol_all_js(t):
|
||||
t.output('%(JAVA)s', '-jar', PLOVR_JAR, 'build', 'build/ol-all.json')
|
||||
|
||||
|
||||
@pake.target('build/src/external/externs/types.js', 'bin/generate-exports.py', 'src/objectliterals.exports')
|
||||
@target('build/src/external/externs/types.js', 'bin/generate-exports.py', 'src/objectliterals.exports')
|
||||
def build_src_external_externs_types_js(t):
|
||||
t.output('%(PYTHON)s', 'bin/generate-exports.py', '--externs', 'src/objectliterals.exports')
|
||||
|
||||
|
||||
@pake.target('build/src/external/src/exports.js', 'bin/generate-exports.py', 'src/objectliterals.exports', EXPORTS)
|
||||
@target('build/src/external/src/exports.js', 'bin/generate-exports.py', 'src/objectliterals.exports', EXPORTS)
|
||||
def build_src_external_src_exports_js(t):
|
||||
t.output('%(PYTHON)s', 'bin/generate-exports.py', '--exports', 'src/objectliterals.exports', EXPORTS)
|
||||
|
||||
|
||||
@pake.target('build/src/external/src/types.js', 'bin/generate-exports', 'src/objectliterals.exports')
|
||||
@target('build/src/external/src/types.js', 'bin/generate-exports', 'src/objectliterals.exports')
|
||||
def build_src_external_src_types_js(t):
|
||||
t.output('%(PYTHON)s', 'bin/generate-exports.py', '--typedef', 'src/objectliterals.exports')
|
||||
|
||||
|
||||
@pake.target('build/src/internal/src/requireall.js', SRC)
|
||||
@target('build/src/internal/src/requireall.js', SRC)
|
||||
def build_src_internal_src_requireall_js(t):
|
||||
requires = set(('goog.dom',))
|
||||
for dependency in t.dependencies:
|
||||
@@ -131,23 +132,23 @@ def build_src_internal_src_requireall_js(t):
|
||||
f.write('goog.require(\'%s\');\n' % (require,))
|
||||
|
||||
|
||||
@pake.target('build/src/internal/src/types.js', 'bin/generate-exports.py', 'src/objectliterals.exports')
|
||||
@target('build/src/internal/src/types.js', 'bin/generate-exports.py', 'src/objectliterals.exports')
|
||||
def build_src_internal_types_js(t):
|
||||
t.output('%(PYTHON)s', 'bin/generate-exports.py', '--typedef', 'src/objectliterals.exports')
|
||||
|
||||
|
||||
pake.virtual('build-examples', 'examples', (path.replace('.html', '.combined.js') for path in EXAMPLES))
|
||||
virtual('build-examples', 'examples', (path.replace('.html', '.combined.js') for path in EXAMPLES))
|
||||
|
||||
|
||||
pake.virtual('examples', 'examples/example-list.js', (path.replace('.html', '.json') for path in EXAMPLES))
|
||||
virtual('examples', 'examples/example-list.js', (path.replace('.html', '.json') for path in EXAMPLES))
|
||||
|
||||
|
||||
@pake.target('examples/example-list.js', 'bin/exampleparser.py', EXAMPLES)
|
||||
@target('examples/example-list.js', 'bin/exampleparser.py', EXAMPLES)
|
||||
def examples_examples_list_js(t):
|
||||
t.run('%(PYTHON)s', 'bin/exampleparser.py', 'examples', 'examples')
|
||||
|
||||
|
||||
@pake.rule(r'\Aexamples/(?P<id>.*).json\Z')
|
||||
@rule(r'\Aexamples/(?P<id>.*).json\Z')
|
||||
def examples_star_json(name, match):
|
||||
def action(t):
|
||||
content = json.dumps({
|
||||
@@ -161,55 +162,55 @@ def examples_star_json(name, match):
|
||||
with open(t.name, 'w') as f:
|
||||
f.write(content)
|
||||
dependencies = [__file__, 'base.json']
|
||||
return pake.Target(name, action=action, dependencies=dependencies)
|
||||
return Target(name, action=action, dependencies=dependencies)
|
||||
|
||||
|
||||
@pake.rule(r'\Aexamples/(?P<id>.*).combined.js\Z')
|
||||
@rule(r'\Aexamples/(?P<id>.*).combined.js\Z')
|
||||
def examples_star_combined_js(name, match):
|
||||
def action(t):
|
||||
t.output('%(JAVA)s', '-jar', PLOVR_JAR, 'build', 'examples/%(id)s.json' % match.groupdict())
|
||||
report_sizes(t)
|
||||
dependencies = [PLOVR_JAR, SRC, INTERNAL_SRC, 'base.json', 'examples/%(id)s.js' % match.groupdict(), 'examples/%(id)s.json' % match.groupdict()]
|
||||
return pake.Target(name, action=action, dependencies=dependencies)
|
||||
return Target(name, action=action, dependencies=dependencies)
|
||||
|
||||
|
||||
@pake.target('serve', PLOVR_JAR, INTERNAL_SRC, 'examples')
|
||||
@target('serve', PLOVR_JAR, INTERNAL_SRC, 'examples')
|
||||
def serve(t):
|
||||
t.run('%(JAVA)s', '-jar', PLOVR_JAR, 'serve', glob.glob('build/*.json'), glob.glob('examples/*.json'))
|
||||
|
||||
|
||||
@pake.target('serve-precommit', PLOVR_JAR, INTERNAL_SRC)
|
||||
@target('serve-precommit', PLOVR_JAR, INTERNAL_SRC)
|
||||
def serve_precommit(t):
|
||||
t.run('%(JAVA)s', '-jar', PLOVR_JAR, 'serve', 'build/ol-all.json')
|
||||
|
||||
|
||||
pake.virtual('lint', 'build/lint-src-timestamp', 'build/lint-spec-timestamp')
|
||||
virtual('lint', 'build/lint-src-timestamp', 'build/lint-spec-timestamp')
|
||||
|
||||
|
||||
@pake.target('build/lint-src-timestamp', SRC, INTERNAL_SRC, EXTERNAL_SRC, EXAMPLES_SRC)
|
||||
@target('build/lint-src-timestamp', SRC, INTERNAL_SRC, EXTERNAL_SRC, EXAMPLES_SRC)
|
||||
def build_lint_src_timestamp(t):
|
||||
limited_doc_files = [path
|
||||
for path in pake.ifind('externs', 'build/src/external/externs')
|
||||
for path in ifind('externs', 'build/src/external/externs')
|
||||
if path.endswith('.js')]
|
||||
t.run('%(GJSLINT)s', '--strict', '--limited_doc_files=%s' % (','.join(limited_doc_files),), SRC, INTERNAL_SRC, EXTERNAL_SRC, EXAMPLES_SRC)
|
||||
t.touch()
|
||||
|
||||
|
||||
@pake.target('build/lint-spec-timestamp', SPEC)
|
||||
@target('build/lint-spec-timestamp', SPEC)
|
||||
def build_lint_spec_timestamp(t):
|
||||
t.run('%(GJSLINT)s', SPEC)
|
||||
t.touch()
|
||||
|
||||
|
||||
pake.virtual('plovr', PLOVR_JAR)
|
||||
virtual('plovr', PLOVR_JAR)
|
||||
|
||||
|
||||
@pake.target(PLOVR_JAR, clean=False)
|
||||
@target(PLOVR_JAR, clean=False)
|
||||
def plovr_jar(t):
|
||||
t.download('https://plovr.googlecode.com/files/' + os.path.basename(PLOVR_JAR), md5=PLOVR_JAR_MD5)
|
||||
|
||||
|
||||
@pake.target('gh-pages', 'hostexamples', 'doc', phony=True)
|
||||
@target('gh-pages', 'hostexamples', 'doc', phony=True)
|
||||
def gh_pages(t):
|
||||
with t.tempdir() as tempdir:
|
||||
t.run('%(GIT)s', 'clone', '--branch', 'gh-pages', 'git@github.com:openlayers/ol3.git', tempdir)
|
||||
@@ -222,16 +223,16 @@ def gh_pages(t):
|
||||
t.run('%(GIT)s', 'push', 'origin', 'gh-pages')
|
||||
|
||||
|
||||
pake.virtual('doc', 'build/jsdoc-%(BRANCH)s-timestamp' % vars(pake.variables))
|
||||
virtual('doc', 'build/jsdoc-%(BRANCH)s-timestamp' % vars(variables))
|
||||
|
||||
|
||||
@pake.target('build/jsdoc-%(BRANCH)s-timestamp' % vars(pake.variables), SRC, pake.ifind('doc/template'))
|
||||
@target('build/jsdoc-%(BRANCH)s-timestamp' % vars(variables), SRC, ifind('doc/template'))
|
||||
def jsdoc_BRANCH_timestamp(t):
|
||||
t.run('%(JSDOC)s', '-t', 'doc/template', '-r', 'src', '-d', 'build/gh-pages/%(BRANCH)s/apidoc')
|
||||
t.touch()
|
||||
|
||||
|
||||
@pake.target('hostexamples', 'build', 'examples', phony=True)
|
||||
@target('hostexamples', 'build', 'examples', phony=True)
|
||||
def hostexamples(t):
|
||||
t.makedirs('build/gh-pages/%(BRANCH)s/examples')
|
||||
t.makedirs('build/gh-pages/%(BRANCH)s/build')
|
||||
@@ -242,10 +243,10 @@ def hostexamples(t):
|
||||
t.cp('examples/example-list.js', 'examples/example-list.xml', 'examples/Jugl.js', 'build/gh-pages/%(BRANCH)s/examples/')
|
||||
|
||||
|
||||
@pake.target('test', INTERNAL_SRC, phony=True)
|
||||
@target('test', INTERNAL_SRC, phony=True)
|
||||
def test(t):
|
||||
t.run('%(PHANTOMJS)s', 'test/phantom-jasmine/run_jasmine_test.coffee', 'test/ol.html')
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
pake.main()
|
||||
main()
|
||||
|
||||
38
examples/canvas-tiles.html
Normal file
38
examples/canvas-tiles.html
Normal file
@@ -0,0 +1,38 @@
|
||||
<!doctype html>
|
||||
<html>
|
||||
<head>
|
||||
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
|
||||
<meta http-equiv="X-UA-Compatible" content="chrome=1">
|
||||
<link rel="stylesheet" href="style.css" type="text/css">
|
||||
<style type="text/css">
|
||||
.map {
|
||||
width: 400px;
|
||||
height: 400px;
|
||||
border: thin solid #cccccc;
|
||||
margin: 1em;
|
||||
}
|
||||
</style>
|
||||
<title>ol3 canvas tiles demo</title>
|
||||
</head>
|
||||
<body>
|
||||
<h1 id="title">Canvas tiles example</h1>
|
||||
<div id="shortdesc">The black grid tiles are generated on the client with an HTML5 canvas. Note that the tile coordinates are ol3 normalized tile coordinates (origin bottom left), not OSM tile coordinates (origin top left).</div>
|
||||
<table>
|
||||
<tr>
|
||||
<th>DOM</th>
|
||||
<th>WebGL</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<td><div id="domMap" class="map"></div></td>
|
||||
<td><div id="webglMap" class="map"></div></td>
|
||||
</tr>
|
||||
</table>
|
||||
<div id="docs">
|
||||
<p>See the
|
||||
<a href="canvas-tiles.js" target="_blank">canvas-tiles.js source</a>
|
||||
to see how this is done.</p>
|
||||
</div>
|
||||
<div id="tags">layers, stamen, canvas</div>
|
||||
<script src="loader.js?id=canvas-tiles" type="text/javascript"></script>
|
||||
</body>
|
||||
</html>
|
||||
43
examples/canvas-tiles.js
Normal file
43
examples/canvas-tiles.js
Normal file
@@ -0,0 +1,43 @@
|
||||
goog.require('ol.Collection');
|
||||
goog.require('ol.Coordinate');
|
||||
goog.require('ol.Map');
|
||||
goog.require('ol.Projection');
|
||||
goog.require('ol.RendererHint');
|
||||
goog.require('ol.layer.TileLayer');
|
||||
goog.require('ol.source.DebugTileSource');
|
||||
goog.require('ol.source.Stamen');
|
||||
|
||||
|
||||
var layers = new ol.Collection([
|
||||
new ol.layer.TileLayer({
|
||||
source: new ol.source.Stamen({
|
||||
provider: ol.source.StamenProvider.WATERCOLOR
|
||||
})
|
||||
}),
|
||||
new ol.layer.TileLayer({
|
||||
source: new ol.source.DebugTileSource({
|
||||
projection: ol.Projection.getFromCode('EPSG:3857'),
|
||||
tileGrid: new ol.tilegrid.XYZ({
|
||||
maxZoom: 22
|
||||
})
|
||||
})
|
||||
})
|
||||
]);
|
||||
|
||||
var webglMap = new ol.Map({
|
||||
view: new ol.View2D({
|
||||
center: ol.Projection.transformWithCodes(
|
||||
new ol.Coordinate(-0.1275, 51.507222), 'EPSG:4326', 'EPSG:3857'),
|
||||
zoom: 10
|
||||
}),
|
||||
layers: layers,
|
||||
renderer: ol.RendererHint.WEBGL,
|
||||
target: 'webglMap'
|
||||
});
|
||||
|
||||
var domMap = new ol.Map({
|
||||
renderer: ol.RendererHint.DOM,
|
||||
target: 'domMap'
|
||||
});
|
||||
domMap.bindTo('layers', webglMap);
|
||||
domMap.bindTo('view', webglMap);
|
||||
@@ -4,6 +4,8 @@ goog.require('goog.debug.Logger.Level');
|
||||
goog.require('ol.Collection');
|
||||
goog.require('ol.Coordinate');
|
||||
goog.require('ol.Map');
|
||||
goog.require('ol.RendererHints');
|
||||
goog.require('ol.View2D');
|
||||
goog.require('ol.source.MapQuestOpenAerial');
|
||||
|
||||
|
||||
@@ -17,8 +19,11 @@ var layer = new ol.layer.TileLayer({
|
||||
source: new ol.source.MapQuestOpenAerial()
|
||||
});
|
||||
var map = new ol.Map({
|
||||
center: new ol.Coordinate(0, 0),
|
||||
layers: new ol.Collection([layer]),
|
||||
renderers: ol.RendererHints.createFromQueryData(),
|
||||
target: 'map',
|
||||
zoom: 2
|
||||
view: new ol.View2D({
|
||||
center: new ol.Coordinate(0, 0),
|
||||
zoom: 0
|
||||
})
|
||||
});
|
||||
|
||||
@@ -4,6 +4,8 @@ goog.require('goog.debug.Logger.Level');
|
||||
goog.require('ol.Collection');
|
||||
goog.require('ol.Coordinate');
|
||||
goog.require('ol.Map');
|
||||
goog.require('ol.RendererHints');
|
||||
goog.require('ol.View2D');
|
||||
goog.require('ol.overlay.Overlay');
|
||||
goog.require('ol.source.MapQuestOpenAerial');
|
||||
|
||||
@@ -17,11 +19,15 @@ if (goog.DEBUG) {
|
||||
var layer = new ol.layer.TileLayer({
|
||||
source: new ol.source.MapQuestOpenAerial()
|
||||
});
|
||||
|
||||
var map = new ol.Map({
|
||||
center: new ol.Coordinate(0, 0),
|
||||
layers: new ol.Collection([layer]),
|
||||
renderers: ol.RendererHints.createFromQueryData(),
|
||||
target: 'map',
|
||||
zoom: 2
|
||||
view: new ol.View2D({
|
||||
center: new ol.Coordinate(0, 0),
|
||||
zoom: 2
|
||||
})
|
||||
});
|
||||
|
||||
// Vienna label
|
||||
|
||||
@@ -60,6 +60,10 @@
|
||||
<td>Visibility:</td>
|
||||
<td><code>v</code>/<code>V</code> keys</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Animations:</td>
|
||||
<td><code>j</code>/<code>l</code>/<code>m</code>/<code>x</code>/<code>L</code>/<code>M</code>/<code>X</code> keys</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>Reset</td>
|
||||
<td><code>0</code> key</td>
|
||||
|
||||
@@ -4,6 +4,8 @@ goog.require('goog.debug.Logger.Level');
|
||||
goog.require('ol.Coordinate');
|
||||
goog.require('ol.Map');
|
||||
goog.require('ol.RendererHint');
|
||||
goog.require('ol.View2D');
|
||||
goog.require('ol.animation');
|
||||
goog.require('ol.control.MousePosition');
|
||||
goog.require('ol.interaction.Keyboard');
|
||||
goog.require('ol.layer.TileLayer');
|
||||
@@ -16,23 +18,32 @@ if (goog.DEBUG) {
|
||||
}
|
||||
|
||||
|
||||
var LONDON = ol.Projection.transformWithCodes(
|
||||
new ol.Coordinate(-0.12755, 51.507222), 'EPSG:4326', 'EPSG:3857');
|
||||
var MOSCOW = ol.Projection.transformWithCodes(
|
||||
new ol.Coordinate(37.6178, 55.7517), 'EPSG:4326', 'EPSG:3857');
|
||||
|
||||
var layer = new ol.layer.TileLayer({
|
||||
source: new ol.source.MapQuestOpenAerial()
|
||||
});
|
||||
|
||||
var domMap = new ol.Map({
|
||||
var view = new ol.View2D({
|
||||
center: new ol.Coordinate(0, 0),
|
||||
zoom: 1
|
||||
});
|
||||
|
||||
var domMap = new ol.Map({
|
||||
layers: new ol.Collection([layer]),
|
||||
renderer: ol.RendererHint.DOM,
|
||||
target: 'domMap',
|
||||
zoom: 1
|
||||
view: view
|
||||
});
|
||||
|
||||
domMap.getControls().push(new ol.control.MousePosition({
|
||||
coordinateFormat: ol.Coordinate.toStringHDMS,
|
||||
projection: ol.Projection.getFromCode('EPSG:4326'),
|
||||
target: document.getElementById('domMousePosition'),
|
||||
undefinedHtml: ' '
|
||||
undefinedHTML: ' '
|
||||
}));
|
||||
|
||||
var webglMap = new ol.Map({
|
||||
@@ -40,17 +51,15 @@ var webglMap = new ol.Map({
|
||||
target: 'webglMap'
|
||||
});
|
||||
if (webglMap !== null) {
|
||||
webglMap.bindTo('center', domMap);
|
||||
webglMap.bindTo('layers', domMap);
|
||||
webglMap.bindTo('resolution', domMap);
|
||||
webglMap.bindTo('rotation', domMap);
|
||||
webglMap.bindTo('view', domMap);
|
||||
}
|
||||
|
||||
webglMap.getControls().push(new ol.control.MousePosition({
|
||||
coordinateFormat: ol.Coordinate.toStringHDMS,
|
||||
projection: ol.Projection.getFromCode('EPSG:4326'),
|
||||
target: document.getElementById('webglMousePosition'),
|
||||
undefinedHtml: ' '
|
||||
undefinedHTML: ' '
|
||||
}));
|
||||
|
||||
var keyboardInteraction = new ol.interaction.Keyboard();
|
||||
@@ -81,6 +90,47 @@ keyboardInteraction.addCallback('h', function() {
|
||||
keyboardInteraction.addCallback('H', function() {
|
||||
layer.setHue(layer.getHue() + (Math.PI / 5));
|
||||
});
|
||||
keyboardInteraction.addCallback('j', function() {
|
||||
var bounce = ol.animation.createBounce(2 * view.getResolution());
|
||||
domMap.addPreRenderFunction(bounce);
|
||||
webglMap.addPreRenderFunction(bounce);
|
||||
});
|
||||
keyboardInteraction.addCallback('l', function() {
|
||||
var panFrom = ol.animation.createPanFrom(view.getCenter());
|
||||
domMap.addPreRenderFunction(panFrom);
|
||||
webglMap.addPreRenderFunction(panFrom);
|
||||
view.setCenter(LONDON);
|
||||
});
|
||||
keyboardInteraction.addCallback('L', function() {
|
||||
var start = Date.now();
|
||||
var duration = 5000;
|
||||
var bounce = ol.animation.createBounce(
|
||||
2 * view.getResolution(), duration, start);
|
||||
var panFrom = ol.animation.createPanFrom(view.getCenter(), duration, start);
|
||||
var spin = ol.animation.createSpin(duration, 2, start);
|
||||
var preRenderFunctions = [bounce, panFrom, spin];
|
||||
domMap.addPreRenderFunctions(preRenderFunctions);
|
||||
webglMap.addPreRenderFunctions(preRenderFunctions);
|
||||
view.setCenter(LONDON);
|
||||
});
|
||||
keyboardInteraction.addCallback('m', function() {
|
||||
var panFrom = ol.animation.createPanFrom(view.getCenter(), 1000);
|
||||
domMap.addPreRenderFunction(panFrom);
|
||||
webglMap.addPreRenderFunction(panFrom);
|
||||
view.setCenter(MOSCOW);
|
||||
});
|
||||
keyboardInteraction.addCallback('M', function() {
|
||||
var start = Date.now();
|
||||
var duration = 5000;
|
||||
var bounce = ol.animation.createBounce(
|
||||
2 * view.getResolution(), duration, start);
|
||||
var panFrom = ol.animation.createPanFrom(view.getCenter(), duration, start);
|
||||
var spin = ol.animation.createSpin(duration, -2, start);
|
||||
var preRenderFunctions = [bounce, panFrom, spin];
|
||||
domMap.addPreRenderFunctions(preRenderFunctions);
|
||||
webglMap.addPreRenderFunctions(preRenderFunctions);
|
||||
view.setCenter(MOSCOW);
|
||||
});
|
||||
keyboardInteraction.addCallback('o', function() {
|
||||
layer.setOpacity(layer.getOpacity() - 0.1);
|
||||
});
|
||||
@@ -88,7 +138,7 @@ keyboardInteraction.addCallback('O', function() {
|
||||
layer.setOpacity(layer.getOpacity() + 0.1);
|
||||
});
|
||||
keyboardInteraction.addCallback('r', function() {
|
||||
webglMap.setRotation(0);
|
||||
view.setRotation(0);
|
||||
});
|
||||
keyboardInteraction.addCallback('s', function() {
|
||||
layer.setSaturation(layer.getSaturation() - 0.1);
|
||||
@@ -100,4 +150,14 @@ keyboardInteraction.addCallback('S', function() {
|
||||
keyboardInteraction.addCallback('vV', function() {
|
||||
layer.setVisible(!layer.getVisible());
|
||||
});
|
||||
keyboardInteraction.addCallback('x', function() {
|
||||
var spin = ol.animation.createSpin(2000, 2);
|
||||
domMap.addPreRenderFunction(spin);
|
||||
webglMap.addPreRenderFunction(spin);
|
||||
});
|
||||
keyboardInteraction.addCallback('X', function() {
|
||||
var spin = ol.animation.createSpin(2000, -2);
|
||||
domMap.addPreRenderFunction(spin);
|
||||
webglMap.addPreRenderFunction(spin);
|
||||
});
|
||||
domMap.getInteractions().push(keyboardInteraction);
|
||||
|
||||
@@ -3,6 +3,7 @@ goog.require('ol.Coordinate');
|
||||
goog.require('ol.Map');
|
||||
goog.require('ol.Projection');
|
||||
goog.require('ol.RendererHint');
|
||||
goog.require('ol.View2D');
|
||||
goog.require('ol.layer.TileLayer');
|
||||
goog.require('ol.source.BingMaps');
|
||||
goog.require('ol.source.TileJSON');
|
||||
@@ -11,7 +12,7 @@ goog.require('ol.source.TileJSON');
|
||||
var layers = new ol.Collection([
|
||||
new ol.layer.TileLayer({
|
||||
source: new ol.source.BingMaps({
|
||||
key: 'Ak0kFwyFsvMr0dVwuaURTqKAXytSSN47KOdj4uVpaWBhK-DT6Zo-FeHCiJUL0tYL',
|
||||
key: 'AgtFlPYDnymLEe9zJ5PCkghbNiFZE9aAtTy3mPaEnEBXqLHtFuTcKoZ-miMC3w7R',
|
||||
style: ol.BingMapsStyle.AERIAL
|
||||
})
|
||||
}),
|
||||
@@ -23,19 +24,19 @@ var layers = new ol.Collection([
|
||||
]);
|
||||
|
||||
var webglMap = new ol.Map({
|
||||
center: ol.Projection.transformWithCodes(
|
||||
new ol.Coordinate(-77.93255, 37.9555), 'EPSG:4326', 'EPSG:3857'),
|
||||
layers: layers,
|
||||
renderer: ol.RendererHint.WEBGL,
|
||||
target: 'webglMap',
|
||||
zoom: 5
|
||||
view: new ol.View2D({
|
||||
center: ol.Projection.transformWithCodes(
|
||||
new ol.Coordinate(-77.93255, 37.9555), 'EPSG:4326', 'EPSG:3857'),
|
||||
zoom: 5
|
||||
})
|
||||
});
|
||||
|
||||
var domMap = new ol.Map({
|
||||
renderer: ol.RendererHint.DOM,
|
||||
target: 'domMap'
|
||||
});
|
||||
domMap.bindTo('center', webglMap);
|
||||
domMap.bindTo('layers', webglMap);
|
||||
domMap.bindTo('resolution', webglMap);
|
||||
domMap.bindTo('rotation', webglMap);
|
||||
domMap.bindTo('view', webglMap);
|
||||
|
||||
@@ -5,6 +5,8 @@ goog.require('ol.Collection');
|
||||
goog.require('ol.Coordinate');
|
||||
goog.require('ol.Map');
|
||||
goog.require('ol.Projection');
|
||||
goog.require('ol.RendererHints');
|
||||
goog.require('ol.View2D');
|
||||
goog.require('ol.source.TiledWMS');
|
||||
|
||||
|
||||
@@ -50,12 +52,15 @@ var layers = new ol.Collection([
|
||||
]);
|
||||
|
||||
var map = new ol.Map({
|
||||
center: new ol.Coordinate(660000, 190000),
|
||||
projection: epsg21781,
|
||||
// By setting userProjection to the same as projection, we do not need
|
||||
// proj4js because we do not need any transforms.
|
||||
userProjection: epsg21781,
|
||||
layers: layers,
|
||||
renderers: ol.RendererHints.createFromQueryData(),
|
||||
target: 'map',
|
||||
zoom: 9
|
||||
view: new ol.View2D({
|
||||
projection: epsg21781,
|
||||
center: new ol.Coordinate(660000, 190000),
|
||||
zoom: 2
|
||||
})
|
||||
});
|
||||
|
||||
@@ -4,6 +4,7 @@ goog.require('goog.debug.Logger.Level');
|
||||
goog.require('ol.Collection');
|
||||
goog.require('ol.Coordinate');
|
||||
goog.require('ol.Map');
|
||||
goog.require('ol.View2D');
|
||||
goog.require('ol.source.MapQuestOpenAerial');
|
||||
goog.require('ol.source.TiledWMS');
|
||||
|
||||
@@ -31,6 +32,8 @@ var map = new ol.Map({
|
||||
renderer: ol.RendererHint.DOM,
|
||||
layers: layers,
|
||||
target: 'map',
|
||||
center: new ol.Coordinate(-10997148, 4569099),
|
||||
zoom: 4
|
||||
view: new ol.View2D({
|
||||
center: new ol.Coordinate(-10997148, 4569099),
|
||||
zoom: 4
|
||||
})
|
||||
});
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
Copyright 2005-2012 OpenLayers Contributors. All rights reserved. See
|
||||
Copyright 2005-2013 OpenLayers Contributors. All rights reserved. See
|
||||
authors.txt for full list.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification,
|
||||
|
||||
@@ -51,6 +51,6 @@ The `.html` file needs to include a script tag with
|
||||
the examples are `myexample.js` and `myexample.html` then `id` should be set to
|
||||
`myexample` in the `loader.js` URL.
|
||||
|
||||
`make serve` should be stopped and restarted for the
|
||||
`loader.js?id=<example_name>` script tag to refer to a valid URL. `make serve`
|
||||
`build.py serve` should be stopped and restarted for the
|
||||
`loader.js?id=<example_name>` script tag to refer to a valid URL. `build.py serve`
|
||||
triggers the `examples` target which creates Plovr JSON file for each example.
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
@exportObjectLiteralProperty ol.control.MousePositionOptions.map ol.Map|undefined
|
||||
@exportObjectLiteralProperty ol.control.MousePositionOptions.projection ol.Projection|undefined
|
||||
@exportObjectLiteralProperty ol.control.MousePositionOptions.target Element|undefined
|
||||
@exportObjectLiteralProperty ol.control.MousePositionOptions.undefinedHtml string|undefined
|
||||
@exportObjectLiteralProperty ol.control.MousePositionOptions.undefinedHTML string|undefined
|
||||
|
||||
@exportObjectLiteral ol.control.ZoomOptions
|
||||
@exportObjectLiteralProperty ol.control.ZoomOptions.delta number|undefined
|
||||
@@ -24,7 +24,6 @@
|
||||
@exportObjectLiteralProperty ol.layer.LayerOptions.visible boolean|undefined
|
||||
|
||||
@exportObjectLiteral ol.MapOptions
|
||||
@exportObjectLiteralProperty ol.MapOptions.center ol.Coordinate|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.controls ol.Collection|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.doubleClickZoom boolean|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.dragPan boolean|undefined
|
||||
@@ -32,22 +31,14 @@
|
||||
@exportObjectLiteralProperty ol.MapOptions.keyboard boolean|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.keyboardPanOffset number|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.layers ol.Collection|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.maxResolution number|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.mouseWheelZoom boolean|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.mouseWheelZoomDelta number|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.numZoomLevels number|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.projection ol.Projection|string|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.renderer ol.RendererHint|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.renderers Array.<ol.RendererHint>|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.resolution number|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.resolutions Array.<number>|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.rotate boolean|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.shiftDragZoom boolean|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.target Element|string
|
||||
@exportObjectLiteralProperty ol.MapOptions.userProjection ol.Projection|string|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.zoom number|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.view ol.IView|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.zoomDelta number|undefined
|
||||
@exportObjectLiteralProperty ol.MapOptions.zoomFactor number|undefined
|
||||
|
||||
@exportObjectLiteral ol.overlay.OverlayOptions
|
||||
@exportObjectLiteralProperty ol.overlay.OverlayOptions.coordinate ol.Coordinate|undefined
|
||||
@@ -71,3 +62,14 @@
|
||||
@exportObjectLiteralProperty ol.source.TiledWMSOptions.projection ol.Projection|undefined
|
||||
@exportObjectLiteralProperty ol.source.TiledWMSOptions.url string|undefined
|
||||
@exportObjectLiteralProperty ol.source.TiledWMSOptions.urls Array.<string>|undefined
|
||||
|
||||
@exportObjectLiteral ol.View2DOptions
|
||||
@exportObjectLiteralProperty ol.View2DOptions.center ol.Coordinate|undefined
|
||||
@exportObjectLiteralProperty ol.View2DOptions.maxResolution number|undefined
|
||||
@exportObjectLiteralProperty ol.View2DOptions.numZoomLevels number|undefined
|
||||
@exportObjectLiteralProperty ol.View2DOptions.projection ol.Projection|string|undefined
|
||||
@exportObjectLiteralProperty ol.View2DOptions.resolution number|undefined
|
||||
@exportObjectLiteralProperty ol.View2DOptions.resolutions Array.<number>|undefined
|
||||
@exportObjectLiteralProperty ol.View2DOptions.rotation number|undefined
|
||||
@exportObjectLiteralProperty ol.View2DOptions.zoom number|undefined
|
||||
@exportObjectLiteralProperty ol.View2DOptions.zoomFactor number|undefined
|
||||
|
||||
109
src/ol/animation.js
Normal file
109
src/ol/animation.js
Normal file
@@ -0,0 +1,109 @@
|
||||
// FIXME works for View2D only
|
||||
|
||||
goog.provide('ol.animation');
|
||||
|
||||
goog.require('goog.fx.easing');
|
||||
goog.require('ol.PreRenderFunction');
|
||||
goog.require('ol.View2D');
|
||||
goog.require('ol.easing');
|
||||
|
||||
|
||||
/**
|
||||
* @param {number} resolution Resolution.
|
||||
* @param {number=} opt_duration Duration.
|
||||
* @param {number=} opt_start Start.
|
||||
* @param {function(number): number=} opt_easingFunction Easing function.
|
||||
* @return {ol.PreRenderFunction} Pre-render function.
|
||||
*/
|
||||
ol.animation.createBounce =
|
||||
function(resolution, opt_duration, opt_start, opt_easingFunction) {
|
||||
var start = goog.isDef(opt_start) ? opt_start : Date.now();
|
||||
var duration = goog.isDef(opt_duration) ? opt_duration : 1000;
|
||||
var easingFunction = goog.isDef(opt_easingFunction) ?
|
||||
opt_easingFunction : ol.easing.upAndDown;
|
||||
return function(map, frameState) {
|
||||
if (frameState.time < start) {
|
||||
frameState.animate = true;
|
||||
frameState.viewHints[ol.ViewHint.ANIMATING] += 1;
|
||||
return true;
|
||||
} else if (frameState.time < start + duration) {
|
||||
var delta = easingFunction((frameState.time - start) / duration);
|
||||
var deltaResolution = resolution - frameState.view2DState.resolution;
|
||||
frameState.animate = true;
|
||||
frameState.view2DState.resolution += delta * deltaResolution;
|
||||
frameState.viewHints[ol.ViewHint.ANIMATING] += 1;
|
||||
return true;
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Coordinate} source Source.
|
||||
* @param {number=} opt_duration Duration.
|
||||
* @param {number=} opt_start Start.
|
||||
* @param {function(number): number=} opt_easingFunction Easing function.
|
||||
* @return {ol.PreRenderFunction} Pre-render function.
|
||||
*/
|
||||
ol.animation.createPanFrom =
|
||||
function(source, opt_duration, opt_start, opt_easingFunction) {
|
||||
var start = goog.isDef(opt_start) ? opt_start : Date.now();
|
||||
var sourceX = source.x;
|
||||
var sourceY = source.y;
|
||||
var duration = goog.isDef(opt_duration) ? opt_duration : 1000;
|
||||
var easingFunction = goog.isDef(opt_easingFunction) ?
|
||||
opt_easingFunction : goog.fx.easing.inAndOut;
|
||||
return function(map, frameState) {
|
||||
if (frameState.time < start) {
|
||||
frameState.animate = true;
|
||||
frameState.viewHints[ol.ViewHint.ANIMATING] += 1;
|
||||
return true;
|
||||
} else if (frameState.time < start + duration) {
|
||||
var delta = 1 - easingFunction((frameState.time - start) / duration);
|
||||
var deltaX = sourceX - frameState.view2DState.center.x;
|
||||
var deltaY = sourceY - frameState.view2DState.center.y;
|
||||
frameState.animate = true;
|
||||
frameState.view2DState.center.x += delta * deltaX;
|
||||
frameState.view2DState.center.y += delta * deltaY;
|
||||
frameState.viewHints[ol.ViewHint.ANIMATING] += 1;
|
||||
return true;
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {number=} opt_duration Duration.
|
||||
* @param {number=} opt_turns Turns.
|
||||
* @param {number=} opt_start Start.
|
||||
* @param {function(number): number=} opt_easingFunction Easing function.
|
||||
* @return {ol.PreRenderFunction} Pre-render function.
|
||||
*/
|
||||
ol.animation.createSpin =
|
||||
function(opt_duration, opt_turns, opt_start, opt_easingFunction) {
|
||||
var start = goog.isDef(opt_start) ? opt_start : Date.now();
|
||||
var duration = goog.isDef(opt_duration) ? opt_duration : 1000;
|
||||
var turns = goog.isDef(opt_turns) ? opt_turns : 1;
|
||||
var deltaTheta = 2 * turns * Math.PI;
|
||||
var easingFunction = goog.isDef(opt_easingFunction) ?
|
||||
opt_easingFunction : goog.fx.easing.inAndOut;
|
||||
return function(map, frameState) {
|
||||
if (frameState.time < start) {
|
||||
frameState.animate = true;
|
||||
frameState.viewHints[ol.ViewHint.ANIMATING] += 1;
|
||||
return true;
|
||||
} else if (frameState.time < start + duration) {
|
||||
var delta = easingFunction((frameState.time - start) / duration);
|
||||
frameState.animate = true;
|
||||
frameState.view2DState.rotation += delta * deltaTheta;
|
||||
frameState.viewHints[ol.ViewHint.ANIMATING] += 1;
|
||||
return true;
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
};
|
||||
};
|
||||
@@ -130,7 +130,7 @@ ol.Collection.prototype.getAt = function(index) {
|
||||
* @return {number} Length.
|
||||
*/
|
||||
ol.Collection.prototype.getLength = function() {
|
||||
return /** @type {number} */ this.get(ol.CollectionProperty.LENGTH);
|
||||
return /** @type {number} */ (this.get(ol.CollectionProperty.LENGTH));
|
||||
};
|
||||
|
||||
|
||||
|
||||
@@ -46,3 +46,16 @@ ol.Color.createFromString = function(str, opt_a) {
|
||||
var a = opt_a || 255;
|
||||
return new ol.Color(rgb[0], rgb[1], rgb[2], a);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Color} color1 Color 1.
|
||||
* @param {ol.Color} color2 Color 2.
|
||||
* @return {boolean} Equals.
|
||||
*/
|
||||
ol.Color.equals = function(color1, color2) {
|
||||
return (color1.r == color2.r &&
|
||||
color1.g == color2.g &&
|
||||
color1.b == color2.b &&
|
||||
color1.a == color2.a);
|
||||
};
|
||||
|
||||
@@ -2,6 +2,7 @@
|
||||
// FIXME handle date line wrap
|
||||
// FIXME handle layer order
|
||||
// FIXME check clean-up code
|
||||
// FIXME works for View2D only
|
||||
|
||||
goog.provide('ol.control.Attribution');
|
||||
|
||||
@@ -14,6 +15,8 @@ goog.require('goog.style');
|
||||
goog.require('ol.Collection');
|
||||
goog.require('ol.CoverageArea');
|
||||
goog.require('ol.TileCoverageArea');
|
||||
goog.require('ol.View2D');
|
||||
goog.require('ol.View2DProperty');
|
||||
goog.require('ol.control.Control');
|
||||
goog.require('ol.layer.Layer');
|
||||
|
||||
@@ -33,12 +36,6 @@ ol.control.Attribution = function(attributionOptions) {
|
||||
'class': 'ol-attribution'
|
||||
}, this.ulElement_);
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Array.<number>}
|
||||
*/
|
||||
this.layersListenerKeys_ = null;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Object.<number, ?number>}
|
||||
@@ -63,6 +60,18 @@ ol.control.Attribution = function(attributionOptions) {
|
||||
*/
|
||||
this.mapListenerKeys_ = null;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Array.<number>}
|
||||
*/
|
||||
this.layersListenerKeys_ = null;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Array.<number>}
|
||||
*/
|
||||
this.viewListenerKeys_ = null;
|
||||
|
||||
goog.base(this, {
|
||||
element: element,
|
||||
map: attributionOptions.map,
|
||||
@@ -110,14 +119,17 @@ ol.control.Attribution.prototype.createAttributionElementsForLayer_ =
|
||||
|
||||
var map = this.getMap();
|
||||
var mapIsDef = map.isDef();
|
||||
var mapExtent = /** @type {ol.Extent} */ map.getExtent();
|
||||
var mapProjection = /** @type {ol.Projection} */ map.getProjection();
|
||||
var mapResolution = /** @type {number} */ map.getResolution();
|
||||
|
||||
var layerVisible = layer.getVisible();
|
||||
|
||||
var attributionVisibilities;
|
||||
if (mapIsDef && layerVisible) {
|
||||
var mapSize = /** @type {ol.Size} */ (map.getSize());
|
||||
// FIXME works for View2D only
|
||||
var view = map.getView();
|
||||
goog.asserts.assert(view instanceof ol.View2D);
|
||||
var mapExtent = view.getExtent(mapSize);
|
||||
var mapProjection = /** @type {ol.Projection} */ (view.getProjection());
|
||||
var mapResolution = /** @type {number} */ (view.getResolution());
|
||||
attributionVisibilities = this.getLayerAttributionVisiblities_(
|
||||
layer, mapExtent, mapResolution, mapProjection);
|
||||
} else {
|
||||
@@ -131,7 +143,7 @@ ol.control.Attribution.prototype.createAttributionElementsForLayer_ =
|
||||
var attributionElement = goog.dom.createElement(goog.dom.TagName.LI);
|
||||
attributionElement.innerHTML = attribution.getHtml();
|
||||
|
||||
if (!map.isDef ||
|
||||
if (!mapIsDef ||
|
||||
!layerVisible ||
|
||||
goog.isNull(attributionVisibilities) ||
|
||||
!attributionVisibilities[attributionKey]) {
|
||||
@@ -151,8 +163,8 @@ ol.control.Attribution.prototype.createAttributionElementsForLayer_ =
|
||||
|
||||
/**
|
||||
* @param {ol.layer.Layer} layer Layer.
|
||||
* @param {ol.Extent} mapExtent Map extent.
|
||||
* @param {number} mapResolution Map resolution.
|
||||
* @param {ol.Extent} mapExtent View extent.
|
||||
* @param {number} mapResolution View resolution.
|
||||
* @param {ol.Projection} mapProjection Map projection.
|
||||
* @return {Object.<number, boolean>} Attribution visibilities.
|
||||
* @private
|
||||
@@ -169,7 +181,7 @@ ol.control.Attribution.prototype.getLayerAttributionVisiblities_ =
|
||||
|
||||
var mapZ;
|
||||
if (source instanceof ol.source.TileSource) {
|
||||
var tileSource = /** @type {ol.source.TileSource} */ source;
|
||||
var tileSource = /** @type {ol.source.TileSource} */ (source);
|
||||
var tileGrid = tileSource.getTileGrid();
|
||||
mapZ = tileGrid.getZForResolution(mapResolution);
|
||||
}
|
||||
@@ -230,7 +242,7 @@ ol.control.Attribution.prototype.getLayerAttributionVisiblities_ =
|
||||
* @param {goog.events.Event} event Event.
|
||||
*/
|
||||
ol.control.Attribution.prototype.handleLayerLoad = function(event) {
|
||||
var layer = /** @type {ol.layer.Layer} */ event.target;
|
||||
var layer = /** @type {ol.layer.Layer} */ (event.target);
|
||||
this.createAttributionElementsForLayer_(layer);
|
||||
};
|
||||
|
||||
@@ -240,17 +252,8 @@ ol.control.Attribution.prototype.handleLayerLoad = function(event) {
|
||||
* @protected
|
||||
*/
|
||||
ol.control.Attribution.prototype.handleLayerVisibleChanged = function(event) {
|
||||
|
||||
var map = this.getMap();
|
||||
var mapIsDef = map.isDef();
|
||||
var mapExtent = /** @type {ol.Extent} */ map.getExtent();
|
||||
var mapProjection = /** @type {ol.Projection} */ map.getProjection();
|
||||
var mapResolution = /** @type {number} */ map.getResolution();
|
||||
|
||||
var layer = /** @type {ol.layer.Layer} */ event.target;
|
||||
|
||||
this.updateLayerAttributionsVisibility_(
|
||||
layer, mapIsDef, mapExtent, mapResolution, mapProjection);
|
||||
var layer = /** @type {ol.layer.Layer} */ (event.target);
|
||||
this.updateLayerAttributionsVisibility_(layer);
|
||||
|
||||
};
|
||||
|
||||
@@ -260,7 +263,7 @@ ol.control.Attribution.prototype.handleLayerVisibleChanged = function(event) {
|
||||
* @protected
|
||||
*/
|
||||
ol.control.Attribution.prototype.handleLayersAdd = function(collectionEvent) {
|
||||
var layer = /** @type {ol.layer.Layer} */ collectionEvent.elem;
|
||||
var layer = /** @type {ol.layer.Layer} */ (collectionEvent.elem);
|
||||
this.addLayer(layer);
|
||||
};
|
||||
|
||||
@@ -271,7 +274,7 @@ ol.control.Attribution.prototype.handleLayersAdd = function(collectionEvent) {
|
||||
*/
|
||||
ol.control.Attribution.prototype.handleLayersRemove =
|
||||
function(collectionEvent) {
|
||||
var layer = /** @type {ol.layer.Layer} */ collectionEvent.elem;
|
||||
var layer = /** @type {ol.layer.Layer} */ (collectionEvent.elem);
|
||||
this.removeLayer(layer);
|
||||
};
|
||||
|
||||
@@ -279,20 +282,26 @@ ol.control.Attribution.prototype.handleLayersRemove =
|
||||
/**
|
||||
* @protected
|
||||
*/
|
||||
ol.control.Attribution.prototype.handleMapChanged = function() {
|
||||
|
||||
ol.control.Attribution.prototype.handleMapViewChanged = function() {
|
||||
if (!goog.isNull(this.viewListenerKeys_)) {
|
||||
goog.array.forEach(this.viewListenerKeys_, goog.events.unlistenByKey);
|
||||
this.viewListenerKeys_ = null;
|
||||
}
|
||||
var map = this.getMap();
|
||||
var mapIsDef = map.isDef();
|
||||
var mapExtent = /** @type {ol.Extent} */ map.getExtent();
|
||||
var mapProjection = /** @type {ol.Projection} */ map.getProjection();
|
||||
var mapResolution = map.getResolution();
|
||||
|
||||
var layers = map.getLayers();
|
||||
layers.forEach(function(layer) {
|
||||
this.updateLayerAttributionsVisibility_(
|
||||
layer, mapIsDef, mapExtent, mapResolution, mapProjection);
|
||||
}, this);
|
||||
|
||||
goog.asserts.assert(!goog.isNull(map));
|
||||
var view = map.getView();
|
||||
if (!goog.isNull(view)) {
|
||||
// FIXME works for View2D only
|
||||
goog.asserts.assert(view instanceof ol.View2D);
|
||||
this.viewListenerKeys_ = [
|
||||
goog.events.listen(
|
||||
view, ol.Object.getChangedEventType(ol.View2DProperty.CENTER),
|
||||
this.updateAttributions, false, this),
|
||||
goog.events.listen(
|
||||
view, ol.Object.getChangedEventType(ol.View2DProperty.RESOLUTION),
|
||||
this.updateAttributions, false, this)
|
||||
];
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -359,35 +368,51 @@ ol.control.Attribution.prototype.setMap = function(map) {
|
||||
goog.base(this, 'setMap', map);
|
||||
if (!goog.isNull(map)) {
|
||||
this.mapListenerKeys_ = [
|
||||
goog.events.listen(
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.CENTER),
|
||||
this.handleMapChanged, false, this),
|
||||
goog.events.listen(
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.LAYERS),
|
||||
this.handleMapLayersChanged, false, this),
|
||||
goog.events.listen(
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.RESOLUTION),
|
||||
this.handleMapChanged, false, this),
|
||||
goog.events.listen(
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.SIZE),
|
||||
this.handleMapChanged, false, this)
|
||||
this.updateAttributions, false, this),
|
||||
goog.events.listen(
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.VIEW),
|
||||
this.updateAttributions, false, this)
|
||||
];
|
||||
this.handleMapViewChanged();
|
||||
this.handleMapLayersChanged();
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @protected
|
||||
*/
|
||||
ol.control.Attribution.prototype.updateAttributions = function() {
|
||||
|
||||
var map = this.getMap();
|
||||
var layers = map.getLayers();
|
||||
layers.forEach(function(layer) {
|
||||
this.updateLayerAttributionsVisibility_(layer);
|
||||
}, this);
|
||||
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.layer.Layer} layer Layer.
|
||||
* @param {boolean} mapIsDef Map is defined.
|
||||
* @param {ol.Extent} mapExtent Map extent.
|
||||
* @param {number} mapResolution Map resolution.
|
||||
* @param {ol.Projection} mapProjection Map projection.
|
||||
* @private
|
||||
*/
|
||||
ol.control.Attribution.prototype.updateLayerAttributionsVisibility_ =
|
||||
function(layer, mapIsDef, mapExtent, mapResolution, mapProjection) {
|
||||
if (mapIsDef && layer.getVisible()) {
|
||||
function(layer) {
|
||||
var map = this.getMap();
|
||||
if (map.isDef() && layer.getVisible()) {
|
||||
var mapSize = /** @type {ol.Size} */ (map.getSize());
|
||||
var view = map.getView();
|
||||
// FIXME works for View2D only
|
||||
goog.asserts.assert(view instanceof ol.View2D);
|
||||
var mapExtent = view.getExtent(mapSize);
|
||||
var mapProjection = /** @type {ol.Projection} */ (view.getProjection());
|
||||
var mapResolution = /** @type {number} */ (view.getResolution());
|
||||
var attributionVisibilities = this.getLayerAttributionVisiblities_(
|
||||
layer, mapExtent, mapResolution, mapProjection);
|
||||
goog.object.forEach(
|
||||
|
||||
@@ -1,7 +1,9 @@
|
||||
// FIXME should listen on appropriate pane, once it is defined
|
||||
// FIXME works for View2D only
|
||||
|
||||
goog.provide('ol.control.MousePosition');
|
||||
|
||||
goog.require('goog.dom');
|
||||
goog.require('goog.events');
|
||||
goog.require('goog.events.EventType');
|
||||
goog.require('goog.style');
|
||||
@@ -47,8 +49,20 @@ ol.control.MousePosition = function(mousePositionOptions) {
|
||||
* @private
|
||||
* @type {string}
|
||||
*/
|
||||
this.undefinedHtml_ = goog.isDef(mousePositionOptions.undefinedHtml) ?
|
||||
mousePositionOptions.undefinedHtml : '';
|
||||
this.undefinedHTML_ = goog.isDef(mousePositionOptions.undefinedHTML) ?
|
||||
mousePositionOptions.undefinedHTML : '';
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {string}
|
||||
*/
|
||||
this.renderedHTML_ = element.innerHTML;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.Projection}
|
||||
*/
|
||||
this.mapProjection_ = null;
|
||||
|
||||
/**
|
||||
* @private
|
||||
@@ -58,23 +72,38 @@ ol.control.MousePosition = function(mousePositionOptions) {
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Array.<number>}
|
||||
* @type {ol.Projection}
|
||||
*/
|
||||
this.listenerKeys_ = [];
|
||||
this.renderedProjection_ = null;
|
||||
|
||||
this.handleMapProjectionChanged();
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.Pixel}
|
||||
*/
|
||||
this.lastMouseMovePixel_ = null;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Array.<?number>}
|
||||
*/
|
||||
this.listenerKeys_ = null;
|
||||
|
||||
};
|
||||
goog.inherits(ol.control.MousePosition, ol.control.Control);
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.MapEvent} mapEvent Map event.
|
||||
* @protected
|
||||
*/
|
||||
ol.control.MousePosition.prototype.handleMapProjectionChanged = function() {
|
||||
this.updateTransform_();
|
||||
// FIXME should we instead re-calculate using the last known mouse position?
|
||||
this.element.innerHTML = this.undefinedHtml_;
|
||||
ol.control.MousePosition.prototype.handleMapPostrender = function(mapEvent) {
|
||||
var frameState = mapEvent.frameState;
|
||||
if (goog.isNull(frameState)) {
|
||||
this.mapProjection_ = null;
|
||||
} else {
|
||||
this.mapProjection_ = frameState.view2DState.projection;
|
||||
}
|
||||
this.updateHTML_(this.lastMouseMovePixel_);
|
||||
};
|
||||
|
||||
|
||||
@@ -87,19 +116,8 @@ ol.control.MousePosition.prototype.handleMouseMove = function(browserEvent) {
|
||||
var eventPosition = goog.style.getRelativePosition(
|
||||
browserEvent, map.getViewport());
|
||||
var pixel = new ol.Pixel(eventPosition.x, eventPosition.y);
|
||||
var coordinate = map.getCoordinateFromPixel(pixel);
|
||||
var html;
|
||||
if (!goog.isNull(coordinate)) {
|
||||
coordinate = this.transform_(coordinate);
|
||||
if (goog.isDef(this.coordinateFormat_)) {
|
||||
html = this.coordinateFormat_(coordinate);
|
||||
} else {
|
||||
html = coordinate.toString();
|
||||
}
|
||||
} else {
|
||||
html = this.undefinedHtml_;
|
||||
}
|
||||
this.element.innerHTML = html;
|
||||
this.updateHTML_(pixel);
|
||||
this.lastMouseMovePixel_ = pixel;
|
||||
};
|
||||
|
||||
|
||||
@@ -108,7 +126,8 @@ ol.control.MousePosition.prototype.handleMouseMove = function(browserEvent) {
|
||||
* @protected
|
||||
*/
|
||||
ol.control.MousePosition.prototype.handleMouseOut = function(browserEvent) {
|
||||
this.element.innerHTML = this.undefinedHtml_;
|
||||
this.updateHTML_(null);
|
||||
this.lastMouseMovePixel_ = null;
|
||||
};
|
||||
|
||||
|
||||
@@ -123,34 +142,47 @@ ol.control.MousePosition.prototype.setMap = function(map) {
|
||||
goog.base(this, 'setMap', map);
|
||||
if (!goog.isNull(map)) {
|
||||
var viewport = map.getViewport();
|
||||
this.listenerKeys = [
|
||||
goog.events.listen(map,
|
||||
ol.Object.getChangedEventType(ol.MapProperty.PROJECTION),
|
||||
this.handleMapProjectionChanged, false, this),
|
||||
this.listenerKeys_ = [
|
||||
goog.events.listen(viewport, goog.events.EventType.MOUSEMOVE,
|
||||
this.handleMouseMove, false, this),
|
||||
goog.events.listen(viewport, goog.events.EventType.MOUSEOUT,
|
||||
this.handleMouseOut, false, this)
|
||||
this.handleMouseOut, false, this),
|
||||
goog.events.listen(map, ol.MapEventType.POSTRENDER,
|
||||
this.handleMapPostrender, false, this)
|
||||
];
|
||||
this.updateTransform_();
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {?ol.Pixel} pixel Pixel.
|
||||
* @private
|
||||
*/
|
||||
ol.control.MousePosition.prototype.updateTransform_ = function() {
|
||||
var map = this.getMap();
|
||||
if (goog.isNull(map)) {
|
||||
this.transform_ = ol.Projection.identityTransform;
|
||||
} else {
|
||||
var mapProjection = map.getProjection();
|
||||
if (!goog.isDef(mapProjection) || !goog.isDef(this.projection_)) {
|
||||
this.transform_ = ol.Projection.identityTransform;
|
||||
} else {
|
||||
this.transform_ =
|
||||
ol.Projection.getTransform(mapProjection, this.projection_);
|
||||
ol.control.MousePosition.prototype.updateHTML_ = function(pixel) {
|
||||
var html = this.undefinedHTML_;
|
||||
if (!goog.isNull(pixel)) {
|
||||
if (this.renderedProjection_ != this.mapProjection_) {
|
||||
if (goog.isDef(this.projection_)) {
|
||||
this.transform_ = ol.Projection.getTransform(
|
||||
this.mapProjection_, this.projection_);
|
||||
} else {
|
||||
this.transform_ = ol.Projection.identityTransform;
|
||||
}
|
||||
this.renderedProjection_ = this.mapProjection_;
|
||||
}
|
||||
var map = this.getMap();
|
||||
var coordinate = map.getCoordinateFromPixel(pixel);
|
||||
if (!goog.isNull(coordinate)) {
|
||||
coordinate = this.transform_(coordinate);
|
||||
if (goog.isDef(this.coordinateFormat_)) {
|
||||
html = this.coordinateFormat_(coordinate);
|
||||
} else {
|
||||
html = coordinate.toString();
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!goog.isDef(this.renderedHTML_) || html != this.renderedHTML_) {
|
||||
this.element.innerHTML = html;
|
||||
this.renderedHTML_ = html;
|
||||
}
|
||||
};
|
||||
|
||||
@@ -1,3 +1,5 @@
|
||||
// FIXME works for View2D only
|
||||
|
||||
goog.provide('ol.control.Zoom');
|
||||
|
||||
goog.require('goog.dom');
|
||||
@@ -58,7 +60,9 @@ goog.inherits(ol.control.Zoom, ol.control.Control);
|
||||
ol.control.Zoom.prototype.handleIn_ = function(browserEvent) {
|
||||
// prevent #zoomIn anchor from getting appended to the url
|
||||
browserEvent.preventDefault();
|
||||
this.getMap().zoom(this.delta_);
|
||||
var map = this.getMap();
|
||||
// FIXME works for View2D only
|
||||
map.getView().zoom(map, this.delta_);
|
||||
};
|
||||
|
||||
|
||||
@@ -69,5 +73,7 @@ ol.control.Zoom.prototype.handleIn_ = function(browserEvent) {
|
||||
ol.control.Zoom.prototype.handleOut_ = function(browserEvent) {
|
||||
// prevent #zoomOut anchor from getting appended to the url
|
||||
browserEvent.preventDefault();
|
||||
this.getMap().zoom(-this.delta_);
|
||||
var map = this.getMap();
|
||||
// FIXME works for View2D only
|
||||
map.getView().zoom(map, -this.delta_);
|
||||
};
|
||||
|
||||
86
src/ol/dom/dom.js
Normal file
86
src/ol/dom/dom.js
Normal file
@@ -0,0 +1,86 @@
|
||||
// FIXME add tests for browser features (Modernizr?)
|
||||
// FIXME implement Matrix Filter for IE < 9
|
||||
|
||||
goog.provide('ol.dom');
|
||||
goog.provide('ol.dom.BrowserFeature');
|
||||
|
||||
goog.require('goog.vec.Mat4');
|
||||
|
||||
|
||||
/**
|
||||
* @enum {boolean}
|
||||
*/
|
||||
ol.dom.BrowserFeature = {
|
||||
CAN_USE_CSS_TRANSFORM: false,
|
||||
CAN_USE_CSS_TRANSFORM3D: true,
|
||||
CAN_USE_MATRIX_FILTER: false
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {Element} element Element.
|
||||
* @param {string} value Value.
|
||||
*/
|
||||
ol.dom.setTransform = function(element, value) {
|
||||
var style = element.style;
|
||||
style.WebkitTransform = value;
|
||||
style.MozTransform = value;
|
||||
style.OTransform = value;
|
||||
style.transform = value;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {Element} element Element.
|
||||
* @param {goog.vec.Mat4.AnyType} transform Matrix.
|
||||
* @param {number=} opt_precision Precision.
|
||||
*/
|
||||
ol.dom.transformElement2D = function(element, transform, opt_precision) {
|
||||
// using matrix() causes gaps in Chrome and Firefox on Mac OS X, so prefer
|
||||
// matrix3d()
|
||||
var i;
|
||||
if (ol.dom.BrowserFeature.CAN_USE_CSS_TRANSFORM3D) {
|
||||
var value3D;
|
||||
if (goog.isDef(opt_precision)) {
|
||||
/** @type {Array.<string>} */
|
||||
var strings3D = new Array(16);
|
||||
for (i = 0; i < 16; ++i) {
|
||||
strings3D[i] = transform[i].toFixed(opt_precision);
|
||||
}
|
||||
value3D = strings3D.join(',');
|
||||
} else {
|
||||
value3D = transform.join(',');
|
||||
}
|
||||
ol.dom.setTransform(element, 'matrix3d(' + value3D + ')');
|
||||
} else if (ol.dom.BrowserFeature.CAN_USE_CSS_TRANSFORM) {
|
||||
/** @type {Array.<number>} */
|
||||
var transform2D = [
|
||||
goog.vec.Mat4.getElement(transform, 0, 0),
|
||||
goog.vec.Mat4.getElement(transform, 1, 0),
|
||||
goog.vec.Mat4.getElement(transform, 0, 1),
|
||||
goog.vec.Mat4.getElement(transform, 1, 1),
|
||||
goog.vec.Mat4.getElement(transform, 0, 3),
|
||||
goog.vec.Mat4.getElement(transform, 1, 3)
|
||||
];
|
||||
var value2D;
|
||||
if (goog.isDef(opt_precision)) {
|
||||
/** @type {Array.<string>} */
|
||||
var strings2D = new Array(6);
|
||||
for (i = 0; i < 6; ++i) {
|
||||
strings2D[i] = transform2D[i].toFixed(opt_precision);
|
||||
}
|
||||
value2D = strings2D.join(',');
|
||||
} else {
|
||||
value2D = transform2D.join(',');
|
||||
}
|
||||
ol.dom.setTransform(element, 'matrix(' + value2D + ')');
|
||||
} else if (ol.dom.BrowserFeature.CAN_USE_MATRIX_FILTER) {
|
||||
// http://msdn.microsoft.com/en-us/library/ms533014%28VS.85,loband%29.aspx
|
||||
goog.asserts.assert(false); // FIXME
|
||||
} else {
|
||||
// FIXME check this code!
|
||||
var style = element.style;
|
||||
style.left = Math.round(goog.vec.Mat4.getElement(transform, 0, 3)) + 'px';
|
||||
style.top = Math.round(goog.vec.Mat4.getElement(transform, 1, 3)) + 'px';
|
||||
}
|
||||
};
|
||||
14
src/ol/easing.js
Normal file
14
src/ol/easing.js
Normal file
@@ -0,0 +1,14 @@
|
||||
goog.provide('ol.easing');
|
||||
|
||||
|
||||
/**
|
||||
* @param {number} t Input between 0 and 1.
|
||||
* @return {number} Output between 0 and 1.
|
||||
*/
|
||||
ol.easing.upAndDown = function(t) {
|
||||
if (t < 0.5) {
|
||||
return goog.fx.easing.inAndOut(2 * t);
|
||||
} else {
|
||||
return 1 - goog.fx.easing.inAndOut(2 * (t - 0.5));
|
||||
}
|
||||
};
|
||||
44
src/ol/framestate.js
Normal file
44
src/ol/framestate.js
Normal file
@@ -0,0 +1,44 @@
|
||||
// FIXME add view3DState
|
||||
|
||||
goog.provide('ol.FrameState');
|
||||
goog.provide('ol.PostRenderFunction');
|
||||
goog.provide('ol.PreRenderFunction');
|
||||
|
||||
goog.require('goog.vec.Mat4');
|
||||
goog.require('ol.Color');
|
||||
goog.require('ol.Coordinate');
|
||||
goog.require('ol.Extent');
|
||||
goog.require('ol.Size');
|
||||
goog.require('ol.TileQueue');
|
||||
goog.require('ol.View2DState');
|
||||
goog.require('ol.layer.LayerState');
|
||||
|
||||
|
||||
/**
|
||||
* @typedef {{animate: boolean,
|
||||
* backgroundColor: ol.Color,
|
||||
* coordinateToPixelMatrix: goog.vec.Mat4.Number,
|
||||
* extent: (null|ol.Extent),
|
||||
* layersArray: Array.<ol.layer.Layer>,
|
||||
* layerStates: Object.<number, ol.layer.LayerState>,
|
||||
* pixelToCoordinateMatrix: goog.vec.Mat4.Number,
|
||||
* postRenderFunctions: Array.<ol.PostRenderFunction>,
|
||||
* size: ol.Size,
|
||||
* tileQueue: ol.TileQueue,
|
||||
* time: number,
|
||||
* view2DState: ol.View2DState,
|
||||
* viewHints: Array.<number>}}
|
||||
*/
|
||||
ol.FrameState;
|
||||
|
||||
|
||||
/**
|
||||
* @typedef {function(ol.Map, ?ol.FrameState): boolean}
|
||||
*/
|
||||
ol.PostRenderFunction;
|
||||
|
||||
|
||||
/**
|
||||
* @typedef {function(ol.Map, ?ol.FrameState): boolean}
|
||||
*/
|
||||
ol.PreRenderFunction;
|
||||
138
src/ol/imagetile.js
Normal file
138
src/ol/imagetile.js
Normal file
@@ -0,0 +1,138 @@
|
||||
goog.provide('ol.ImageTile');
|
||||
|
||||
goog.require('goog.array');
|
||||
goog.require('goog.events');
|
||||
goog.require('goog.events.EventTarget');
|
||||
goog.require('goog.events.EventType');
|
||||
goog.require('ol.Tile');
|
||||
goog.require('ol.TileCoord');
|
||||
goog.require('ol.TileState');
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.Tile}
|
||||
* @param {ol.TileCoord} tileCoord Tile coordinate.
|
||||
* @param {string} src Image source URI.
|
||||
* @param {?string} crossOrigin Cross origin.
|
||||
*/
|
||||
ol.ImageTile = function(tileCoord, src, crossOrigin) {
|
||||
|
||||
goog.base(this, tileCoord);
|
||||
|
||||
/**
|
||||
* Image URI
|
||||
*
|
||||
* @private
|
||||
* @type {string}
|
||||
*/
|
||||
this.src_ = src;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Image}
|
||||
*/
|
||||
this.image_ = new Image();
|
||||
if (!goog.isNull(crossOrigin)) {
|
||||
this.image_.crossOrigin = crossOrigin;
|
||||
}
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Object.<number, Image>}
|
||||
*/
|
||||
this.imageByContext_ = {};
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Array.<number>}
|
||||
*/
|
||||
this.imageListenerKeys_ = null;
|
||||
|
||||
};
|
||||
goog.inherits(ol.ImageTile, ol.Tile);
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.ImageTile.prototype.getImage = function(opt_context) {
|
||||
if (goog.isDef(opt_context)) {
|
||||
var image;
|
||||
var key = goog.getUid(opt_context);
|
||||
if (key in this.imageByContext_) {
|
||||
return this.imageByContext_[key];
|
||||
} else if (goog.object.isEmpty(this.imageByContext_)) {
|
||||
image = this.image_;
|
||||
} else {
|
||||
image = /** @type {Image} */ (this.image_.cloneNode(false));
|
||||
}
|
||||
this.imageByContext_[key] = image;
|
||||
return image;
|
||||
} else {
|
||||
return this.image_;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.ImageTile.prototype.getKey = function() {
|
||||
return this.src_;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Tracks loading or read errors.
|
||||
*
|
||||
* @private
|
||||
*/
|
||||
ol.ImageTile.prototype.handleImageError_ = function() {
|
||||
this.state = ol.TileState.ERROR;
|
||||
this.unlistenImage_();
|
||||
this.dispatchChangeEvent();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Tracks successful image load.
|
||||
*
|
||||
* @private
|
||||
*/
|
||||
ol.ImageTile.prototype.handleImageLoad_ = function() {
|
||||
this.state = ol.TileState.LOADED;
|
||||
this.unlistenImage_();
|
||||
this.dispatchChangeEvent();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Load not yet loaded URI.
|
||||
*/
|
||||
ol.ImageTile.prototype.load = function() {
|
||||
if (this.state == ol.TileState.IDLE) {
|
||||
this.state = ol.TileState.LOADING;
|
||||
goog.asserts.assert(goog.isNull(this.imageListenerKeys_));
|
||||
this.imageListenerKeys_ = [
|
||||
goog.events.listenOnce(this.image_, goog.events.EventType.ERROR,
|
||||
this.handleImageError_, false, this),
|
||||
goog.events.listenOnce(this.image_, goog.events.EventType.LOAD,
|
||||
this.handleImageLoad_, false, this)
|
||||
];
|
||||
this.image_.src = this.src_;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Discards event handlers which listen for load completion or errors.
|
||||
*
|
||||
* @private
|
||||
*/
|
||||
ol.ImageTile.prototype.unlistenImage_ = function() {
|
||||
goog.asserts.assert(!goog.isNull(this.imageListenerKeys_));
|
||||
goog.array.forEach(this.imageListenerKeys_, goog.events.unlistenByKey);
|
||||
this.imageListenerKeys_ = null;
|
||||
};
|
||||
@@ -1,7 +1,10 @@
|
||||
// FIXME works for View2D only
|
||||
|
||||
goog.provide('ol.interaction.DblClickZoom');
|
||||
|
||||
goog.require('ol.MapBrowserEvent');
|
||||
goog.require('ol.MapBrowserEvent.EventType');
|
||||
goog.require('ol.View2D');
|
||||
goog.require('ol.interaction.Interaction');
|
||||
|
||||
|
||||
@@ -35,7 +38,10 @@ ol.interaction.DblClickZoom.prototype.handleMapBrowserEvent =
|
||||
var anchor = mapBrowserEvent.getCoordinate();
|
||||
var delta = mapBrowserEvent.browserEvent.shiftKey ?
|
||||
-this.delta_ : this.delta_;
|
||||
map.zoom(delta, anchor);
|
||||
// FIXME works for View2D only
|
||||
var view = map.getView();
|
||||
goog.asserts.assert(view instanceof ol.View2D);
|
||||
view.zoom(map, delta, anchor);
|
||||
mapBrowserEvent.preventDefault();
|
||||
browserEvent.preventDefault();
|
||||
}
|
||||
|
||||
@@ -89,6 +89,7 @@ ol.interaction.Drag.prototype.handleMapBrowserEvent =
|
||||
if (!map.isDef()) {
|
||||
return;
|
||||
}
|
||||
var view = map.getView();
|
||||
var browserEvent = mapBrowserEvent.browserEvent;
|
||||
if (this.dragging_) {
|
||||
if (mapBrowserEvent.type == ol.MapBrowserEvent.EventType.DRAG) {
|
||||
@@ -109,9 +110,9 @@ ol.interaction.Drag.prototype.handleMapBrowserEvent =
|
||||
this.startY = browserEvent.clientY;
|
||||
this.deltaX = 0;
|
||||
this.deltaY = 0;
|
||||
this.startCenter = /** @type {!ol.Coordinate} */ map.getCenter();
|
||||
this.startCenter = /** @type {!ol.Coordinate} */ (view.getCenter());
|
||||
this.startCoordinate = /** @type {ol.Coordinate} */
|
||||
mapBrowserEvent.getCoordinate();
|
||||
(mapBrowserEvent.getCoordinate());
|
||||
var handled = this.handleDragStart(mapBrowserEvent);
|
||||
if (handled) {
|
||||
this.dragging_ = true;
|
||||
|
||||
@@ -1,7 +1,12 @@
|
||||
// FIXME works for View2D only
|
||||
|
||||
goog.provide('ol.interaction.DragPan');
|
||||
|
||||
goog.require('goog.asserts');
|
||||
goog.require('ol.Coordinate');
|
||||
goog.require('ol.MapBrowserEvent');
|
||||
goog.require('ol.View2D');
|
||||
goog.require('ol.ViewHint');
|
||||
goog.require('ol.interaction.ConditionType');
|
||||
goog.require('ol.interaction.Drag');
|
||||
|
||||
@@ -31,17 +36,28 @@ goog.inherits(ol.interaction.DragPan, ol.interaction.Drag);
|
||||
*/
|
||||
ol.interaction.DragPan.prototype.handleDrag = function(mapBrowserEvent) {
|
||||
var map = mapBrowserEvent.map;
|
||||
var resolution = map.getResolution();
|
||||
var rotation = map.getRotation();
|
||||
// FIXME works for View2D only
|
||||
var view = map.getView();
|
||||
goog.asserts.assert(view instanceof ol.View2D);
|
||||
var resolution = view.getResolution();
|
||||
var rotation = view.getRotation();
|
||||
var delta =
|
||||
new ol.Coordinate(-resolution * this.deltaX, resolution * this.deltaY);
|
||||
if (map.canRotate() && goog.isDef(rotation)) {
|
||||
delta.rotate(rotation);
|
||||
}
|
||||
delta.rotate(rotation);
|
||||
var newCenter = new ol.Coordinate(
|
||||
this.startCenter.x + delta.x, this.startCenter.y + delta.y);
|
||||
map.requestRenderFrame();
|
||||
map.setCenter(newCenter);
|
||||
view.setCenter(newCenter);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.interaction.DragPan.prototype.handleDragEnd = function(mapBrowserEvent) {
|
||||
var map = mapBrowserEvent.map;
|
||||
map.requestRenderFrame();
|
||||
map.getView().setHint(ol.ViewHint.PANNING, -1);
|
||||
};
|
||||
|
||||
|
||||
@@ -51,7 +67,9 @@ ol.interaction.DragPan.prototype.handleDrag = function(mapBrowserEvent) {
|
||||
ol.interaction.DragPan.prototype.handleDragStart = function(mapBrowserEvent) {
|
||||
var browserEvent = mapBrowserEvent.browserEvent;
|
||||
if (this.condition_(browserEvent)) {
|
||||
mapBrowserEvent.map.requestRenderFrame();
|
||||
var map = mapBrowserEvent.map;
|
||||
map.requestRenderFrame();
|
||||
map.getView().setHint(ol.ViewHint.PANNING, 1);
|
||||
return true;
|
||||
} else {
|
||||
return false;
|
||||
|
||||
@@ -1,7 +1,10 @@
|
||||
// FIXME works for View2D only
|
||||
|
||||
goog.provide('ol.interaction.DragRotateAndZoom');
|
||||
|
||||
goog.require('goog.math.Vec2');
|
||||
goog.require('ol.MapBrowserEvent');
|
||||
goog.require('ol.View2D');
|
||||
goog.require('ol.interaction.ConditionType');
|
||||
goog.require('ol.interaction.Drag');
|
||||
|
||||
@@ -50,12 +53,15 @@ ol.interaction.DragRotateAndZoom.prototype.handleDrag =
|
||||
browserEvent.offsetX - size.width / 2,
|
||||
size.height / 2 - browserEvent.offsetY);
|
||||
var theta = Math.atan2(delta.y, delta.x);
|
||||
var resolution = this.startRatio_ * delta.magnitude();
|
||||
// FIXME works for View2D only
|
||||
var view = map.getView();
|
||||
goog.asserts.assert(view instanceof ol.View2D);
|
||||
map.requestRenderFrame();
|
||||
// FIXME the calls to map.rotate and map.zoomToResolution should use
|
||||
// map.withFrozenRendering but an assertion fails :-(
|
||||
map.rotate(this.startRotation_, -theta);
|
||||
var resolution = this.startRatio_ * delta.magnitude();
|
||||
map.zoomToResolution(resolution);
|
||||
view.rotate(map, this.startRotation_, -theta);
|
||||
view.zoomToResolution(map, resolution);
|
||||
};
|
||||
|
||||
|
||||
@@ -66,14 +72,15 @@ ol.interaction.DragRotateAndZoom.prototype.handleDragStart =
|
||||
function(mapBrowserEvent) {
|
||||
var browserEvent = mapBrowserEvent.browserEvent;
|
||||
var map = mapBrowserEvent.map;
|
||||
if (map.canRotate() && this.condition_(browserEvent)) {
|
||||
var resolution = map.getResolution();
|
||||
var view = map.getView().getView2D();
|
||||
if (this.condition_(browserEvent)) {
|
||||
var resolution = view.getResolution();
|
||||
var size = map.getSize();
|
||||
var delta = new goog.math.Vec2(
|
||||
browserEvent.offsetX - size.width / 2,
|
||||
size.height / 2 - browserEvent.offsetY);
|
||||
var theta = Math.atan2(delta.y, delta.x);
|
||||
this.startRotation_ = (map.getRotation() || 0) + theta;
|
||||
this.startRotation_ = (view.getRotation() || 0) + theta;
|
||||
this.startRatio_ = resolution / delta.magnitude();
|
||||
map.requestRenderFrame();
|
||||
return true;
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
goog.provide('ol.interaction.DragRotate');
|
||||
|
||||
goog.require('ol.MapBrowserEvent');
|
||||
goog.require('ol.View2D');
|
||||
goog.require('ol.interaction.ConditionType');
|
||||
goog.require('ol.interaction.Drag');
|
||||
|
||||
@@ -42,8 +43,11 @@ ol.interaction.DragRotate.prototype.handleDrag = function(mapBrowserEvent) {
|
||||
var theta = Math.atan2(
|
||||
size.height / 2 - offset.y,
|
||||
offset.x - size.width / 2);
|
||||
// FIXME supports View2D only
|
||||
var view = map.getView();
|
||||
goog.asserts.assert(view instanceof ol.View2D);
|
||||
map.requestRenderFrame();
|
||||
map.rotate(this.startRotation_, -theta);
|
||||
view.rotate(map, this.startRotation_, -theta);
|
||||
};
|
||||
|
||||
|
||||
@@ -54,15 +58,17 @@ ol.interaction.DragRotate.prototype.handleDragStart =
|
||||
function(mapBrowserEvent) {
|
||||
var browserEvent = mapBrowserEvent.browserEvent;
|
||||
var map = mapBrowserEvent.map;
|
||||
if (browserEvent.isMouseActionButton() && this.condition_(browserEvent) &&
|
||||
map.canRotate()) {
|
||||
// FIXME supports View2D only
|
||||
var view = map.getView();
|
||||
goog.asserts.assert(view instanceof ol.View2D);
|
||||
if (browserEvent.isMouseActionButton() && this.condition_(browserEvent)) {
|
||||
map.requestRenderFrame();
|
||||
var size = map.getSize();
|
||||
var offset = mapBrowserEvent.getPixel();
|
||||
var theta = Math.atan2(
|
||||
size.height / 2 - offset.y,
|
||||
offset.x - size.width / 2);
|
||||
this.startRotation_ = (map.getRotation() || 0) + theta;
|
||||
this.startRotation_ = (view.getRotation() || 0) + theta;
|
||||
return true;
|
||||
} else {
|
||||
return false;
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
// FIXME draw drag box
|
||||
// FIXME works for View2D only
|
||||
|
||||
goog.provide('ol.interaction.DragZoom');
|
||||
|
||||
@@ -63,7 +64,15 @@ ol.interaction.DragZoom.prototype.handleDragEnd =
|
||||
var extent = ol.Extent.boundingExtent(
|
||||
this.startCoordinate,
|
||||
mapBrowserEvent.getCoordinate());
|
||||
map.fitExtent(extent);
|
||||
map.withFrozenRendering(function() {
|
||||
// FIXME works for View2D only
|
||||
var view = map.getView();
|
||||
goog.asserts.assert(view instanceof ol.View2D);
|
||||
var mapSize = /** @type {ol.Size} */ (map.getSize());
|
||||
view.fitExtent(extent, mapSize);
|
||||
// FIXME we should preserve rotation
|
||||
view.setRotation(0);
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -43,7 +43,7 @@ ol.interaction.Keyboard.prototype.handleMapBrowserEvent =
|
||||
function(mapBrowserEvent) {
|
||||
if (mapBrowserEvent.type == goog.events.KeyHandler.EventType.KEY) {
|
||||
var keyEvent = /** @type {goog.events.KeyEvent} */
|
||||
mapBrowserEvent.browserEvent;
|
||||
(mapBrowserEvent.browserEvent);
|
||||
var callback = this.charCodeCallbacks_[keyEvent.charCode];
|
||||
if (callback) {
|
||||
callback();
|
||||
|
||||
@@ -1,7 +1,10 @@
|
||||
// FIXME works for View2D only
|
||||
|
||||
goog.provide('ol.interaction.KeyboardPan');
|
||||
|
||||
goog.require('goog.events.KeyCodes');
|
||||
goog.require('goog.events.KeyHandler.EventType');
|
||||
goog.require('ol.View2D');
|
||||
goog.require('ol.interaction.Interaction');
|
||||
|
||||
|
||||
@@ -32,14 +35,17 @@ ol.interaction.KeyboardPan.prototype.handleMapBrowserEvent =
|
||||
function(mapBrowserEvent) {
|
||||
if (mapBrowserEvent.type == goog.events.KeyHandler.EventType.KEY) {
|
||||
var keyEvent = /** @type {goog.events.KeyEvent} */
|
||||
mapBrowserEvent.browserEvent;
|
||||
(mapBrowserEvent.browserEvent);
|
||||
var keyCode = keyEvent.keyCode;
|
||||
if (keyCode == goog.events.KeyCodes.DOWN ||
|
||||
keyCode == goog.events.KeyCodes.LEFT ||
|
||||
keyCode == goog.events.KeyCodes.RIGHT ||
|
||||
keyCode == goog.events.KeyCodes.UP) {
|
||||
var map = mapBrowserEvent.map;
|
||||
var resolution = map.getResolution();
|
||||
// FIXME works for View2D only
|
||||
var view = map.getView();
|
||||
goog.asserts.assert(view instanceof ol.View2D);
|
||||
var resolution = view.getResolution();
|
||||
var delta;
|
||||
var mapUnitsDelta = resolution * this.pixelDelta_;
|
||||
if (keyCode == goog.events.KeyCodes.DOWN) {
|
||||
@@ -52,10 +58,10 @@ ol.interaction.KeyboardPan.prototype.handleMapBrowserEvent =
|
||||
goog.asserts.assert(keyCode == goog.events.KeyCodes.UP);
|
||||
delta = new ol.Coordinate(0, mapUnitsDelta);
|
||||
}
|
||||
var oldCenter = map.getCenter();
|
||||
var oldCenter = view.getCenter();
|
||||
var newCenter = new ol.Coordinate(
|
||||
oldCenter.x + delta.x, oldCenter.y + delta.y);
|
||||
map.setCenter(newCenter);
|
||||
view.setCenter(newCenter);
|
||||
keyEvent.preventDefault();
|
||||
mapBrowserEvent.preventDefault();
|
||||
}
|
||||
|
||||
@@ -1,7 +1,10 @@
|
||||
// FIXME works for View2D only
|
||||
|
||||
goog.provide('ol.interaction.KeyboardZoom');
|
||||
|
||||
goog.require('goog.events.KeyCodes');
|
||||
goog.require('goog.events.KeyHandler.EventType');
|
||||
goog.require('ol.View2D');
|
||||
goog.require('ol.interaction.Interaction');
|
||||
|
||||
|
||||
@@ -23,12 +26,15 @@ ol.interaction.KeyboardZoom.prototype.handleMapBrowserEvent =
|
||||
function(mapBrowserEvent) {
|
||||
if (mapBrowserEvent.type == goog.events.KeyHandler.EventType.KEY) {
|
||||
var keyEvent = /** @type {goog.events.KeyEvent} */
|
||||
mapBrowserEvent.browserEvent;
|
||||
(mapBrowserEvent.browserEvent);
|
||||
var charCode = keyEvent.charCode;
|
||||
if (charCode == '+'.charCodeAt(0) || charCode == '-'.charCodeAt(0)) {
|
||||
var map = mapBrowserEvent.map;
|
||||
var delta = (charCode == '+'.charCodeAt(0)) ? 4 : -4;
|
||||
map.zoom(delta);
|
||||
// FIXME works for View2D only
|
||||
var view = map.getView();
|
||||
goog.asserts.assert(view instanceof ol.View2D);
|
||||
view.zoom(map, delta);
|
||||
keyEvent.preventDefault();
|
||||
mapBrowserEvent.preventDefault();
|
||||
}
|
||||
|
||||
@@ -1,8 +1,11 @@
|
||||
// FIXME works for View2D only
|
||||
|
||||
goog.provide('ol.interaction.MouseWheelZoom');
|
||||
|
||||
goog.require('goog.events.MouseWheelEvent');
|
||||
goog.require('goog.events.MouseWheelHandler.EventType');
|
||||
goog.require('ol.MapBrowserEvent');
|
||||
goog.require('ol.View2D');
|
||||
|
||||
|
||||
|
||||
@@ -32,12 +35,15 @@ ol.interaction.MouseWheelZoom.prototype.handleMapBrowserEvent =
|
||||
goog.events.MouseWheelHandler.EventType.MOUSEWHEEL) {
|
||||
var map = mapBrowserEvent.map;
|
||||
var mouseWheelEvent = /** @type {goog.events.MouseWheelEvent} */
|
||||
mapBrowserEvent.browserEvent;
|
||||
(mapBrowserEvent.browserEvent);
|
||||
goog.asserts.assert(mouseWheelEvent instanceof goog.events.MouseWheelEvent);
|
||||
var anchor = mapBrowserEvent.getCoordinate();
|
||||
var delta = mouseWheelEvent.deltaY < 0 ? this.delta_ : -this.delta_;
|
||||
// FIXME works for View2D only
|
||||
var view = map.getView();
|
||||
goog.asserts.assert(view instanceof ol.View2D);
|
||||
map.requestRenderFrame();
|
||||
map.zoom(delta, anchor);
|
||||
view.zoom(map, delta, anchor);
|
||||
mapBrowserEvent.preventDefault();
|
||||
mouseWheelEvent.preventDefault();
|
||||
}
|
||||
|
||||
27
src/ol/iview.js
Normal file
27
src/ol/iview.js
Normal file
@@ -0,0 +1,27 @@
|
||||
goog.provide('ol.IView');
|
||||
|
||||
goog.require('ol.IView2D');
|
||||
goog.require('ol.IView3D');
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Interface for views.
|
||||
* @interface
|
||||
*/
|
||||
ol.IView = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.IView2D} View2D.
|
||||
*/
|
||||
ol.IView.prototype.getView2D = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.IView3D} View3D.
|
||||
*/
|
||||
ol.IView.prototype.getView3D = function() {
|
||||
};
|
||||
59
src/ol/iview2d.js
Normal file
59
src/ol/iview2d.js
Normal file
@@ -0,0 +1,59 @@
|
||||
goog.provide('ol.IView2D');
|
||||
goog.provide('ol.View2DState');
|
||||
|
||||
goog.require('ol.Coordinate');
|
||||
goog.require('ol.Extent');
|
||||
goog.require('ol.Projection');
|
||||
|
||||
|
||||
/**
|
||||
* @typedef {{center: ol.Coordinate,
|
||||
* projection: ol.Projection,
|
||||
* resolution: number,
|
||||
* rotation: number}}
|
||||
*/
|
||||
ol.View2DState;
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Interface for views.
|
||||
* @interface
|
||||
*/
|
||||
ol.IView2D = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.Coordinate|undefined} Map center.
|
||||
*/
|
||||
ol.IView2D.prototype.getCenter = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.Projection|undefined} Map projection.
|
||||
*/
|
||||
ol.IView2D.prototype.getProjection = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {number|undefined} Map resolution.
|
||||
*/
|
||||
ol.IView2D.prototype.getResolution = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {number|undefined} Map rotation.
|
||||
*/
|
||||
ol.IView2D.prototype.getRotation = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.View2DState} View2D state.
|
||||
*/
|
||||
ol.IView2D.prototype.getView2DState = function() {
|
||||
};
|
||||
12
src/ol/iview3d.js
Normal file
12
src/ol/iview3d.js
Normal file
@@ -0,0 +1,12 @@
|
||||
goog.provide('ol.IView3D');
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Interface for views.
|
||||
* @interface
|
||||
*/
|
||||
ol.IView3D = function() {
|
||||
};
|
||||
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
goog.provide('ol.layer.Layer');
|
||||
goog.provide('ol.layer.LayerProperty');
|
||||
goog.provide('ol.layer.LayerState');
|
||||
|
||||
goog.require('goog.events');
|
||||
goog.require('goog.events.EventType');
|
||||
@@ -21,6 +22,18 @@ ol.layer.LayerProperty = {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @typedef {{brightness: number,
|
||||
* contrast: number,
|
||||
* hue: number,
|
||||
* opacity: number,
|
||||
* ready: boolean,
|
||||
* saturation: number,
|
||||
* visible: boolean}}
|
||||
*/
|
||||
ol.layer.LayerState;
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @constructor
|
||||
@@ -71,7 +84,7 @@ ol.layer.Layer.prototype.dispatchLoadEvent_ = function() {
|
||||
* @return {number} Brightness.
|
||||
*/
|
||||
ol.layer.Layer.prototype.getBrightness = function() {
|
||||
return /** @type {number} */ this.get(ol.layer.LayerProperty.BRIGHTNESS);
|
||||
return /** @type {number} */ (this.get(ol.layer.LayerProperty.BRIGHTNESS));
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.layer.Layer.prototype,
|
||||
@@ -83,7 +96,7 @@ goog.exportProperty(
|
||||
* @return {number} Contrast.
|
||||
*/
|
||||
ol.layer.Layer.prototype.getContrast = function() {
|
||||
return /** @type {number} */ this.get(ol.layer.LayerProperty.CONTRAST);
|
||||
return /** @type {number} */ (this.get(ol.layer.LayerProperty.CONTRAST));
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.layer.Layer.prototype,
|
||||
@@ -95,7 +108,7 @@ goog.exportProperty(
|
||||
* @return {number} Hue.
|
||||
*/
|
||||
ol.layer.Layer.prototype.getHue = function() {
|
||||
return /** @type {number} */ this.get(ol.layer.LayerProperty.HUE);
|
||||
return /** @type {number} */ (this.get(ol.layer.LayerProperty.HUE));
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.layer.Layer.prototype,
|
||||
@@ -103,11 +116,34 @@ goog.exportProperty(
|
||||
ol.layer.Layer.prototype.getHue);
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.layer.LayerState} Layer state.
|
||||
*/
|
||||
ol.layer.Layer.prototype.getLayerState = function() {
|
||||
var brightness = this.getBrightness();
|
||||
var contrast = this.getContrast();
|
||||
var hue = this.getHue();
|
||||
var opacity = this.getOpacity();
|
||||
var ready = this.isReady();
|
||||
var saturation = this.getSaturation();
|
||||
var visible = this.getVisible();
|
||||
return {
|
||||
brightness: goog.isDef(brightness) ? brightness : 0,
|
||||
contrast: goog.isDef(contrast) ? contrast : 1,
|
||||
hue: goog.isDef(hue) ? hue : 0,
|
||||
opacity: goog.isDef(opacity) ? opacity : 1,
|
||||
ready: ready,
|
||||
saturation: goog.isDef(saturation) ? saturation : 1,
|
||||
visible: goog.isDef(visible) ? visible : true
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {number} Opacity.
|
||||
*/
|
||||
ol.layer.Layer.prototype.getOpacity = function() {
|
||||
return /** @type {number} */ this.get(ol.layer.LayerProperty.OPACITY);
|
||||
return /** @type {number} */ (this.get(ol.layer.LayerProperty.OPACITY));
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.layer.Layer.prototype,
|
||||
@@ -119,7 +155,7 @@ goog.exportProperty(
|
||||
* @return {number} Saturation.
|
||||
*/
|
||||
ol.layer.Layer.prototype.getSaturation = function() {
|
||||
return /** @type {number} */ this.get(ol.layer.LayerProperty.SATURATION);
|
||||
return /** @type {number} */ (this.get(ol.layer.LayerProperty.SATURATION));
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.layer.Layer.prototype,
|
||||
@@ -139,7 +175,7 @@ ol.layer.Layer.prototype.getSource = function() {
|
||||
* @return {boolean} Visible.
|
||||
*/
|
||||
ol.layer.Layer.prototype.getVisible = function() {
|
||||
return /** @type {boolean} */ this.get(ol.layer.LayerProperty.VISIBLE);
|
||||
return /** @type {boolean} */ (this.get(ol.layer.LayerProperty.VISIBLE));
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.layer.Layer.prototype,
|
||||
|
||||
@@ -20,5 +20,5 @@ goog.inherits(ol.layer.TileLayer, ol.layer.Layer);
|
||||
* @return {ol.source.TileSource} Source.
|
||||
*/
|
||||
ol.layer.TileLayer.prototype.getTileSource = function() {
|
||||
return /** @type {ol.source.TileSource} */ this.getSource();
|
||||
return /** @type {ol.source.TileSource} */ (this.getSource());
|
||||
};
|
||||
|
||||
642
src/ol/map.js
642
src/ol/map.js
@@ -3,10 +3,11 @@
|
||||
// FIXME add tilt and height?
|
||||
|
||||
goog.provide('ol.Map');
|
||||
goog.provide('ol.MapEventType');
|
||||
goog.provide('ol.MapProperty');
|
||||
goog.provide('ol.RendererHint');
|
||||
goog.provide('ol.RendererHints');
|
||||
|
||||
goog.require('goog.Uri.QueryData');
|
||||
goog.require('goog.array');
|
||||
goog.require('goog.async.AnimationDelay');
|
||||
goog.require('goog.debug.Logger');
|
||||
@@ -22,22 +23,24 @@ goog.require('goog.events.KeyHandler.EventType');
|
||||
goog.require('goog.events.MouseWheelEvent');
|
||||
goog.require('goog.events.MouseWheelHandler');
|
||||
goog.require('goog.events.MouseWheelHandler.EventType');
|
||||
goog.require('goog.functions');
|
||||
goog.require('goog.object');
|
||||
goog.require('ol.BrowserFeature');
|
||||
goog.require('ol.Collection');
|
||||
goog.require('ol.Color');
|
||||
goog.require('ol.Constraints');
|
||||
goog.require('ol.Coordinate');
|
||||
goog.require('ol.Extent');
|
||||
goog.require('ol.FrameState');
|
||||
goog.require('ol.MapBrowserEvent');
|
||||
goog.require('ol.Object');
|
||||
goog.require('ol.Pixel');
|
||||
goog.require('ol.Projection');
|
||||
goog.require('ol.ResolutionConstraint');
|
||||
goog.require('ol.RotationConstraint');
|
||||
goog.require('ol.Size');
|
||||
goog.require('ol.TileQueue');
|
||||
goog.require('ol.TransformFunction');
|
||||
goog.require('ol.View');
|
||||
goog.require('ol.View2D');
|
||||
goog.require('ol.View2DState');
|
||||
goog.require('ol.control.Attribution');
|
||||
goog.require('ol.control.Zoom');
|
||||
goog.require('ol.interaction.DblClickZoom');
|
||||
@@ -87,26 +90,14 @@ ol.DEFAULT_RENDERER_HINTS = [
|
||||
];
|
||||
|
||||
|
||||
/**
|
||||
* @enum {string}
|
||||
*/
|
||||
ol.MapEventType = {
|
||||
POSTRENDER: 'postrender'
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @enum {string}
|
||||
*/
|
||||
ol.MapProperty = {
|
||||
BACKGROUND_COLOR: 'backgroundColor',
|
||||
CENTER: 'center',
|
||||
LAYERS: 'layers',
|
||||
PROJECTION: 'projection',
|
||||
RESOLUTION: 'resolution',
|
||||
ROTATION: 'rotation',
|
||||
SIZE: 'size',
|
||||
USER_PROJECTION: 'userProjection'
|
||||
VIEW: 'view'
|
||||
};
|
||||
|
||||
|
||||
@@ -130,18 +121,6 @@ ol.Map = function(mapOptions) {
|
||||
|
||||
var mapOptionsInternal = ol.Map.createOptionsInternal(mapOptions);
|
||||
|
||||
/**
|
||||
* @type {ol.TransformFunction}
|
||||
* @private
|
||||
*/
|
||||
this.userToMapTransform_ = ol.Projection.identityTransform;
|
||||
|
||||
/**
|
||||
* @type {ol.TransformFunction}
|
||||
* @private
|
||||
*/
|
||||
this.mapToUserTransform_ = ol.Projection.cloneTransform;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {goog.async.AnimationDelay}
|
||||
@@ -150,6 +129,24 @@ ol.Map = function(mapOptions) {
|
||||
new goog.async.AnimationDelay(this.renderFrame_, undefined, this);
|
||||
this.registerDisposable(this.animationDelay_);
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {goog.vec.Mat4.Number}
|
||||
*/
|
||||
this.coordinateToPixelMatrix_ = goog.vec.Mat4.createNumber();
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {goog.vec.Mat4.Number}
|
||||
*/
|
||||
this.pixelToCoordinateMatrix_ = goog.vec.Mat4.createNumber();
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {?ol.FrameState}
|
||||
*/
|
||||
this.frameState_ = null;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {number}
|
||||
@@ -168,12 +165,6 @@ ol.Map = function(mapOptions) {
|
||||
*/
|
||||
this.target_ = mapOptionsInternal.target;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.Constraints}
|
||||
*/
|
||||
this.constraints_ = mapOptionsInternal.constraints;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Element}
|
||||
@@ -253,13 +244,29 @@ ol.Map = function(mapOptions) {
|
||||
goog.events.listen(this.viewportSizeMonitor_, goog.events.EventType.RESIZE,
|
||||
this.handleBrowserWindowResize, false, this);
|
||||
|
||||
goog.events.listen(
|
||||
this, ol.Object.getChangedEventType(ol.MapProperty.PROJECTION),
|
||||
this.handleProjectionChanged, false, this);
|
||||
/**
|
||||
* @private
|
||||
* @type {Array.<ol.PreRenderFunction>}
|
||||
*/
|
||||
this.preRenderFunctions_ = [];
|
||||
|
||||
goog.events.listen(
|
||||
this, ol.Object.getChangedEventType(ol.MapProperty.USER_PROJECTION),
|
||||
this.handleUserProjectionChanged, false, this);
|
||||
/**
|
||||
* @private
|
||||
* @type {Array.<ol.PostRenderFunction>}
|
||||
*/
|
||||
this.postRenderFunctions_ = [];
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {function(this: ol.Map)}
|
||||
*/
|
||||
this.handlePostRender_ = goog.bind(this.handlePostRender, this);
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.TileQueue}
|
||||
*/
|
||||
this.tileQueue_ = new ol.TileQueue(goog.bind(this.getTilePriority, this));
|
||||
|
||||
this.setValues(mapOptionsInternal.values);
|
||||
|
||||
@@ -278,10 +285,22 @@ goog.inherits(ol.Map, ol.Object);
|
||||
|
||||
|
||||
/**
|
||||
* @return {boolean} Can rotate.
|
||||
* @param {ol.PreRenderFunction} preRenderFunction Pre-render function.
|
||||
*/
|
||||
ol.Map.prototype.canRotate = function() {
|
||||
return this.renderer_.canRotate();
|
||||
ol.Map.prototype.addPreRenderFunction = function(preRenderFunction) {
|
||||
this.requestRenderFrame();
|
||||
this.preRenderFunctions_.push(preRenderFunction);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {Array.<ol.PreRenderFunction>} preRenderFunctions
|
||||
* Pre-render functions.
|
||||
*/
|
||||
ol.Map.prototype.addPreRenderFunctions = function(preRenderFunctions) {
|
||||
this.requestRenderFrame();
|
||||
Array.prototype.push.apply(
|
||||
this.preRenderFunctions_, preRenderFunctions);
|
||||
};
|
||||
|
||||
|
||||
@@ -295,30 +314,6 @@ ol.Map.prototype.disposeInternal = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Extent} extent Extent.
|
||||
*/
|
||||
ol.Map.prototype.fitExtent = function(extent) {
|
||||
this.withFrozenRendering(function() {
|
||||
this.setCenter(extent.getCenter());
|
||||
var resolution = this.getResolutionForExtent(extent);
|
||||
resolution = this.constraints_.resolution(resolution, 0);
|
||||
this.setResolution(resolution);
|
||||
if (this.canRotate()) {
|
||||
this.setRotation(0);
|
||||
}
|
||||
}, this);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Extent} userExtent Extent in user projection.
|
||||
*/
|
||||
ol.Map.prototype.fitUserExtent = function(userExtent) {
|
||||
this.fitExtent(userExtent.transform(this.userToMapTransform_));
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Freeze rendering.
|
||||
*/
|
||||
@@ -340,18 +335,6 @@ goog.exportProperty(
|
||||
ol.Map.prototype.getBackgroundColor);
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.Coordinate|undefined} Center.
|
||||
*/
|
||||
ol.Map.prototype.getCenter = function() {
|
||||
return /** @type {ol.Coordinate} */ this.get(ol.MapProperty.CENTER);
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.Map.prototype,
|
||||
'getCenter',
|
||||
ol.Map.prototype.getCenter);
|
||||
|
||||
|
||||
/**
|
||||
* @return {Element} Container.
|
||||
*/
|
||||
@@ -373,25 +356,13 @@ ol.Map.prototype.getControls = function() {
|
||||
* @return {ol.Coordinate} Coordinate.
|
||||
*/
|
||||
ol.Map.prototype.getCoordinateFromPixel = function(pixel) {
|
||||
return this.isDef() ? this.renderer_.getCoordinateFromPixel(pixel) : null;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.Extent|undefined} Extent.
|
||||
*/
|
||||
ol.Map.prototype.getExtent = function() {
|
||||
if (this.isDef()) {
|
||||
var center = this.getCenter();
|
||||
var resolution = this.getResolution();
|
||||
var size = this.getSize();
|
||||
var minX = center.x - resolution * size.width / 2;
|
||||
var minY = center.y - resolution * size.height / 2;
|
||||
var maxX = center.x + resolution * size.width / 2;
|
||||
var maxY = center.y + resolution * size.height / 2;
|
||||
return new ol.Extent(minX, minY, maxX, maxY);
|
||||
var frameState = this.frameState_;
|
||||
if (goog.isNull(frameState)) {
|
||||
return null;
|
||||
} else {
|
||||
return undefined;
|
||||
var vec3 = [pixel.x, pixel.y, 0];
|
||||
goog.vec.Mat4.multVec3(frameState.pixelToCoordinateMatrix, vec3, vec3);
|
||||
return new ol.Coordinate(vec3[0], vec3[1]);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -414,99 +385,25 @@ ol.Map.prototype.getLayers = function() {
|
||||
|
||||
/**
|
||||
* @param {ol.Coordinate} coordinate Coordinate.
|
||||
* @return {ol.Pixel|undefined} Pixel.
|
||||
* @return {ol.Pixel} Pixel.
|
||||
*/
|
||||
ol.Map.prototype.getPixelFromCoordinate = function(coordinate) {
|
||||
if (this.isDef()) {
|
||||
return this.renderer_.getPixelFromCoordinate(coordinate);
|
||||
var frameState = this.frameState_;
|
||||
if (goog.isNull(frameState)) {
|
||||
return null;
|
||||
} else {
|
||||
return undefined;
|
||||
var vec3 = [coordinate.x, coordinate.y, 0];
|
||||
goog.vec.Mat4.multVec3(frameState.coordinateToPixelMatrix, vec3, vec3);
|
||||
return new ol.Pixel(vec3[0], vec3[1]);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.Projection|undefined} Projection.
|
||||
*/
|
||||
ol.Map.prototype.getProjection = function() {
|
||||
return /** @type {ol.Projection} */ this.get(ol.MapProperty.PROJECTION);
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.Map.prototype,
|
||||
'getProjection',
|
||||
ol.Map.prototype.getProjection);
|
||||
|
||||
|
||||
/**
|
||||
* @return {number|undefined} Resolution.
|
||||
*/
|
||||
ol.Map.prototype.getResolution = function() {
|
||||
return /** @type {number} */ this.get(ol.MapProperty.RESOLUTION);
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.Map.prototype,
|
||||
'getResolution',
|
||||
ol.Map.prototype.getResolution);
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Extent} extent Extent.
|
||||
* @return {number|undefined} Resolution.
|
||||
*/
|
||||
ol.Map.prototype.getResolutionForExtent = function(extent) {
|
||||
var size = this.getSize();
|
||||
if (goog.isDef(size)) {
|
||||
var xResolution = (extent.maxX - extent.minX) / size.width;
|
||||
var yResolution = (extent.maxY - extent.minY) / size.height;
|
||||
return Math.max(xResolution, yResolution);
|
||||
} else {
|
||||
return undefined;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.Extent} Rotated extent.
|
||||
*/
|
||||
ol.Map.prototype.getRotatedExtent = function() {
|
||||
goog.asserts.assert(this.isDef());
|
||||
var center = /** @type {!ol.Coordinate} */ this.getCenter();
|
||||
var resolution = this.getResolution();
|
||||
var rotation = this.getRotation() || 0;
|
||||
var size = this.getSize();
|
||||
var xScale = resolution * size.width / 2;
|
||||
var yScale = resolution * size.height / 2;
|
||||
var corners = [
|
||||
new ol.Coordinate(-xScale, -yScale),
|
||||
new ol.Coordinate(-xScale, yScale),
|
||||
new ol.Coordinate(xScale, -yScale),
|
||||
new ol.Coordinate(xScale, yScale)
|
||||
];
|
||||
goog.array.forEach(corners, function(corner) {
|
||||
corner.rotate(rotation);
|
||||
corner.add(center);
|
||||
});
|
||||
return ol.Extent.boundingExtent.apply(null, corners);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {number} Rotation.
|
||||
*/
|
||||
ol.Map.prototype.getRotation = function() {
|
||||
return /** @type {number} */ this.get(ol.MapProperty.ROTATION) || 0;
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.Map.prototype,
|
||||
'getRotation',
|
||||
ol.Map.prototype.getRotation);
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.Size|undefined} Size.
|
||||
*/
|
||||
ol.Map.prototype.getSize = function() {
|
||||
return /** @type {ol.Size|undefined} */ this.get(ol.MapProperty.SIZE);
|
||||
return /** @type {ol.Size|undefined} */ (this.get(ol.MapProperty.SIZE));
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.Map.prototype,
|
||||
@@ -515,42 +412,15 @@ goog.exportProperty(
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.Coordinate|undefined} Center in user projection.
|
||||
* @return {ol.View} View.
|
||||
*/
|
||||
ol.Map.prototype.getUserCenter = function() {
|
||||
var center = this.getCenter();
|
||||
if (goog.isDef(center)) {
|
||||
return this.mapToUserTransform_(center);
|
||||
} else {
|
||||
return undefined;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.Extent|undefined} Extent in user projection.
|
||||
*/
|
||||
ol.Map.prototype.getUserExtent = function() {
|
||||
var extent = this.getExtent();
|
||||
if (goog.isDef(extent)) {
|
||||
return extent.transform(this.mapToUserTransform_);
|
||||
} else {
|
||||
return undefined;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.Projection|undefined} Projection.
|
||||
*/
|
||||
ol.Map.prototype.getUserProjection = function() {
|
||||
return /** @type {ol.Projection} */ this.get(
|
||||
ol.MapProperty.USER_PROJECTION);
|
||||
ol.Map.prototype.getView = function() {
|
||||
return /** @type {ol.View} */ (this.get(ol.MapProperty.VIEW));
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.Map.prototype,
|
||||
'getUserProjection',
|
||||
ol.Map.prototype.getUserProjection);
|
||||
'getView',
|
||||
ol.Map.prototype.getView);
|
||||
|
||||
|
||||
/**
|
||||
@@ -571,6 +441,24 @@ ol.Map.prototype.getOverlayContainer = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Tile} tile Tile.
|
||||
* @param {ol.Coordinate} tileCenter Tile center.
|
||||
* @param {number} tileResolution Tile resolution.
|
||||
* @return {number|undefined} Tile priority.
|
||||
*/
|
||||
ol.Map.prototype.getTilePriority = function(tile, tileCenter, tileResolution) {
|
||||
if (goog.isNull(this.frameState_)) {
|
||||
return undefined;
|
||||
} else {
|
||||
var center = this.frameState_.view2DState.center;
|
||||
var deltaX = tileCenter.x - center.x;
|
||||
var deltaY = tileCenter.y - center.y;
|
||||
return Math.sqrt(deltaX * deltaX + deltaY * deltaY) / tileResolution;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {goog.events.BrowserEvent} browserEvent Browser event.
|
||||
* @param {string=} opt_type Type.
|
||||
@@ -587,7 +475,7 @@ ol.Map.prototype.handleBrowserEvent = function(browserEvent, opt_type) {
|
||||
* @private
|
||||
*/
|
||||
ol.Map.prototype.handleControlsAdd_ = function(collectionEvent) {
|
||||
var control = /** @type {ol.control.Control} */ collectionEvent.elem;
|
||||
var control = /** @type {ol.control.Control} */ (collectionEvent.elem);
|
||||
control.setMap(this);
|
||||
};
|
||||
|
||||
@@ -597,7 +485,7 @@ ol.Map.prototype.handleControlsAdd_ = function(collectionEvent) {
|
||||
* @private
|
||||
*/
|
||||
ol.Map.prototype.handleControlsRemove_ = function(collectionEvent) {
|
||||
var control = /** @type {ol.control.Control} */ collectionEvent.elem;
|
||||
var control = /** @type {ol.control.Control} */ (collectionEvent.elem);
|
||||
control.setMap(null);
|
||||
};
|
||||
|
||||
@@ -608,7 +496,7 @@ ol.Map.prototype.handleControlsRemove_ = function(collectionEvent) {
|
||||
ol.Map.prototype.handleMapBrowserEvent = function(mapBrowserEvent) {
|
||||
var interactions = this.getInteractions();
|
||||
var interactionsArray = /** @type {Array.<ol.interaction.Interaction>} */
|
||||
interactions.getArray();
|
||||
(interactions.getArray());
|
||||
if (this.dispatchEvent(mapBrowserEvent) !== false) {
|
||||
for (var i = interactionsArray.length - 1; i >= 0; i--) {
|
||||
var interaction = interactionsArray[i];
|
||||
@@ -624,16 +512,16 @@ ol.Map.prototype.handleMapBrowserEvent = function(mapBrowserEvent) {
|
||||
/**
|
||||
* @protected
|
||||
*/
|
||||
ol.Map.prototype.handleProjectionChanged = function() {
|
||||
this.recalculateTransforms_();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @protected
|
||||
*/
|
||||
ol.Map.prototype.handleUserProjectionChanged = function() {
|
||||
this.recalculateTransforms_();
|
||||
ol.Map.prototype.handlePostRender = function() {
|
||||
this.tileQueue_.reprioritize(); // FIXME only call if needed
|
||||
this.tileQueue_.loadMoreTiles();
|
||||
goog.array.forEach(
|
||||
this.postRenderFunctions_,
|
||||
function(postRenderFunction) {
|
||||
postRenderFunction(this, this.frameState_);
|
||||
},
|
||||
this);
|
||||
this.postRenderFunctions_.length = 0;
|
||||
};
|
||||
|
||||
|
||||
@@ -650,31 +538,12 @@ ol.Map.prototype.handleBrowserWindowResize = function() {
|
||||
* @return {boolean} Is defined.
|
||||
*/
|
||||
ol.Map.prototype.isDef = function() {
|
||||
return goog.isDefAndNotNull(this.getCenter()) &&
|
||||
goog.isDef(this.getResolution()) &&
|
||||
var view = this.getView();
|
||||
return goog.isDef(view) && view.isDef() &&
|
||||
goog.isDefAndNotNull(this.getSize());
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @private
|
||||
*/
|
||||
ol.Map.prototype.recalculateTransforms_ = function() {
|
||||
var projection = this.getProjection();
|
||||
var userProjection = this.getUserProjection();
|
||||
if (goog.isDefAndNotNull(projection) &&
|
||||
goog.isDefAndNotNull(userProjection)) {
|
||||
this.mapToUserTransform_ = ol.Projection.getTransform(
|
||||
projection, userProjection);
|
||||
this.userToMapTransform_ = ol.Projection.getTransform(
|
||||
userProjection, projection);
|
||||
} else {
|
||||
this.mapToUserTransform_ = ol.Projection.cloneTransform;
|
||||
this.userToMapTransform_ = ol.Projection.identityTransform;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Render.
|
||||
*/
|
||||
@@ -708,28 +577,98 @@ ol.Map.prototype.requestRenderFrame = function() {
|
||||
* @private
|
||||
*/
|
||||
ol.Map.prototype.renderFrame_ = function(time) {
|
||||
|
||||
var i;
|
||||
|
||||
if (this.freezeRenderingCount_ != 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (goog.DEBUG) {
|
||||
this.logger.info('renderFrame_');
|
||||
}
|
||||
this.renderer_.renderFrame(time);
|
||||
this.dirty_ = false;
|
||||
if (goog.DEBUG) {
|
||||
this.logger.info('postrender');
|
||||
|
||||
var size = this.getSize();
|
||||
var layers = this.getLayers();
|
||||
var layersArray = goog.isDef(layers) ?
|
||||
/** @type {Array.<ol.layer.Layer>} */ (layers.getArray()) : undefined;
|
||||
var view = this.getView();
|
||||
var view2D = goog.isDef(view) ? this.getView().getView2D() : undefined;
|
||||
/** @type {?ol.FrameState} */
|
||||
var frameState = null;
|
||||
if (goog.isDef(layersArray) && goog.isDef(size) && goog.isDef(view2D) &&
|
||||
view2D.isDef()) {
|
||||
var backgroundColor = this.getBackgroundColor();
|
||||
var viewHints = view.getHints();
|
||||
var layerStates = {};
|
||||
goog.array.forEach(layersArray, function(layer) {
|
||||
layerStates[goog.getUid(layer)] = layer.getLayerState();
|
||||
});
|
||||
var view2DState = view2D.getView2DState();
|
||||
frameState = {
|
||||
animate: false,
|
||||
backgroundColor: goog.isDef(backgroundColor) ?
|
||||
backgroundColor : new ol.Color(1, 1, 1, 1),
|
||||
coordinateToPixelMatrix: this.coordinateToPixelMatrix_,
|
||||
extent: null,
|
||||
layersArray: layersArray,
|
||||
layerStates: layerStates,
|
||||
pixelToCoordinateMatrix: this.pixelToCoordinateMatrix_,
|
||||
postRenderFunctions: [],
|
||||
size: size,
|
||||
tileQueue: this.tileQueue_,
|
||||
view2DState: view2DState,
|
||||
viewHints: viewHints,
|
||||
time: time
|
||||
};
|
||||
}
|
||||
this.dispatchEvent(ol.MapEventType.POSTRENDER);
|
||||
};
|
||||
|
||||
this.preRenderFunctions_ = goog.array.filter(
|
||||
this.preRenderFunctions_,
|
||||
function(preRenderFunction) {
|
||||
return preRenderFunction(this, frameState);
|
||||
},
|
||||
this);
|
||||
|
||||
if (!goog.isNull(frameState)) {
|
||||
// FIXME works for View2D only
|
||||
var center = view2DState.center;
|
||||
var resolution = view2DState.resolution;
|
||||
var rotation = view2DState.rotation;
|
||||
var x = resolution * size.width / 2;
|
||||
var y = resolution * size.height / 2;
|
||||
var corners = [
|
||||
new ol.Coordinate(-x, -y),
|
||||
new ol.Coordinate(-x, y),
|
||||
new ol.Coordinate(x, -y),
|
||||
new ol.Coordinate(x, y)
|
||||
];
|
||||
var corner;
|
||||
for (i = 0; i < 4; ++i) {
|
||||
corner = corners[i];
|
||||
corner.rotate(rotation);
|
||||
corner.add(center);
|
||||
}
|
||||
frameState.extent = ol.Extent.boundingExtent.apply(null, corners);
|
||||
}
|
||||
|
||||
this.renderer_.renderFrame(frameState);
|
||||
|
||||
if (!goog.isNull(frameState)) {
|
||||
if (frameState.animate) {
|
||||
this.requestRenderFrame();
|
||||
}
|
||||
Array.prototype.push.apply(
|
||||
this.postRenderFunctions_, frameState.postRenderFunctions);
|
||||
}
|
||||
this.frameState_ = frameState;
|
||||
this.dirty_ = false;
|
||||
|
||||
this.dispatchEvent(
|
||||
new ol.MapEvent(ol.MapEventType.POSTRENDER, this, frameState));
|
||||
|
||||
goog.global.setTimeout(this.handlePostRender_, 0);
|
||||
|
||||
/**
|
||||
* @param {number|undefined} rotation Rotation.
|
||||
* @param {number} delta Delta.
|
||||
*/
|
||||
ol.Map.prototype.rotate = function(rotation, delta) {
|
||||
rotation = this.constraints_.rotation(rotation, delta);
|
||||
this.setRotation(rotation);
|
||||
};
|
||||
|
||||
|
||||
@@ -745,18 +684,6 @@ goog.exportProperty(
|
||||
ol.Map.prototype.setBackgroundColor);
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Coordinate|undefined} center Center.
|
||||
*/
|
||||
ol.Map.prototype.setCenter = function(center) {
|
||||
this.set(ol.MapProperty.CENTER, center);
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.Map.prototype,
|
||||
'setCenter',
|
||||
ol.Map.prototype.setCenter);
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Collection} layers Layers.
|
||||
*/
|
||||
@@ -769,42 +696,6 @@ goog.exportProperty(
|
||||
ol.Map.prototype.setLayers);
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Projection} projection Projection.
|
||||
*/
|
||||
ol.Map.prototype.setProjection = function(projection) {
|
||||
this.set(ol.MapProperty.PROJECTION, projection);
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.Map.prototype,
|
||||
'setProjection',
|
||||
ol.Map.prototype.setProjection);
|
||||
|
||||
|
||||
/**
|
||||
* @param {number|undefined} resolution Resolution.
|
||||
*/
|
||||
ol.Map.prototype.setResolution = function(resolution) {
|
||||
this.set(ol.MapProperty.RESOLUTION, resolution);
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.Map.prototype,
|
||||
'setResolution',
|
||||
ol.Map.prototype.setResolution);
|
||||
|
||||
|
||||
/**
|
||||
* @param {number|undefined} rotation Rotation.
|
||||
*/
|
||||
ol.Map.prototype.setRotation = function(rotation) {
|
||||
this.set(ol.MapProperty.ROTATION, rotation);
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.Map.prototype,
|
||||
'setRotation',
|
||||
ol.Map.prototype.setRotation);
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Size} size Size.
|
||||
*/
|
||||
@@ -818,23 +709,15 @@ goog.exportProperty(
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Coordinate} userCenter Center in user projection.
|
||||
* @param {ol.IView} view View.
|
||||
*/
|
||||
ol.Map.prototype.setUserCenter = function(userCenter) {
|
||||
this.setCenter(this.userToMapTransform_(userCenter));
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Projection} userProjection User projection.
|
||||
*/
|
||||
ol.Map.prototype.setUserProjection = function(userProjection) {
|
||||
this.set(ol.MapProperty.USER_PROJECTION, userProjection);
|
||||
ol.Map.prototype.setView = function(view) {
|
||||
this.set(ol.MapProperty.VIEW, view);
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.Map.prototype,
|
||||
'setUserProjection',
|
||||
ol.Map.prototype.setUserProjection);
|
||||
'setView',
|
||||
ol.Map.prototype.setView);
|
||||
|
||||
|
||||
/**
|
||||
@@ -863,53 +746,9 @@ ol.Map.prototype.withFrozenRendering = function(f, opt_obj) {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @param {number|undefined} resolution Resolution to go to.
|
||||
* @param {ol.Coordinate=} opt_anchor Anchor coordinate.
|
||||
*/
|
||||
ol.Map.prototype.zoom_ = function(resolution, opt_anchor) {
|
||||
if (goog.isDefAndNotNull(resolution) && goog.isDefAndNotNull(opt_anchor)) {
|
||||
var anchor = opt_anchor;
|
||||
var oldCenter = /** @type {!ol.Coordinate} */ this.getCenter();
|
||||
var oldResolution = this.getResolution();
|
||||
var x = anchor.x - resolution * (anchor.x - oldCenter.x) / oldResolution;
|
||||
var y = anchor.y - resolution * (anchor.y - oldCenter.y) / oldResolution;
|
||||
var center = new ol.Coordinate(x, y);
|
||||
this.withFrozenRendering(function() {
|
||||
this.setCenter(center);
|
||||
this.setResolution(resolution);
|
||||
}, this);
|
||||
} else {
|
||||
this.setResolution(resolution);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {number} delta Delta from previous zoom level.
|
||||
* @param {ol.Coordinate=} opt_anchor Anchor coordinate.
|
||||
*/
|
||||
ol.Map.prototype.zoom = function(delta, opt_anchor) {
|
||||
var resolution = this.constraints_.resolution(this.getResolution(), delta);
|
||||
this.zoom_(resolution, opt_anchor);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {number|undefined} resolution Resolution to go to.
|
||||
* @param {ol.Coordinate=} opt_anchor Anchor coordinate.
|
||||
*/
|
||||
ol.Map.prototype.zoomToResolution = function(resolution, opt_anchor) {
|
||||
resolution = this.constraints_.resolution(resolution, 0);
|
||||
this.zoom_(resolution, opt_anchor);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @typedef {{controls: ol.Collection,
|
||||
* interactions: ol.Collection,
|
||||
* constraints: ol.Constraints,
|
||||
* rendererConstructor:
|
||||
* function(new: ol.renderer.Map, Element, ol.Map),
|
||||
* target: Element,
|
||||
@@ -929,25 +768,11 @@ ol.Map.createOptionsInternal = function(mapOptions) {
|
||||
*/
|
||||
var values = {};
|
||||
|
||||
if (goog.isDef(mapOptions.center)) {
|
||||
values[ol.MapProperty.CENTER] = mapOptions.center;
|
||||
}
|
||||
|
||||
values[ol.MapProperty.LAYERS] = goog.isDef(mapOptions.layers) ?
|
||||
mapOptions.layers : new ol.Collection();
|
||||
|
||||
values[ol.MapProperty.PROJECTION] = ol.Projection.createProjection(
|
||||
mapOptions.projection, 'EPSG:3857');
|
||||
|
||||
if (goog.isDef(mapOptions.resolution)) {
|
||||
values[ol.MapProperty.RESOLUTION] = mapOptions.resolution;
|
||||
} else if (goog.isDef(mapOptions.zoom)) {
|
||||
values[ol.MapProperty.RESOLUTION] =
|
||||
ol.Projection.EPSG_3857_HALF_SIZE / (128 << mapOptions.zoom);
|
||||
}
|
||||
|
||||
values[ol.MapProperty.USER_PROJECTION] = ol.Projection.createProjection(
|
||||
mapOptions.userProjection, 'EPSG:4326');
|
||||
values[ol.MapProperty.VIEW] = goog.isDef(mapOptions.view) ?
|
||||
mapOptions.view : new ol.View2D();
|
||||
|
||||
/**
|
||||
* @type {function(new: ol.renderer.Map, Element, ol.Map)}
|
||||
@@ -982,11 +807,6 @@ ol.Map.createOptionsInternal = function(mapOptions) {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @type {ol.Constraints}
|
||||
*/
|
||||
var constraints = ol.Map.createConstraints_(mapOptions);
|
||||
|
||||
/**
|
||||
* @type {ol.Collection}
|
||||
*/
|
||||
@@ -1013,7 +833,6 @@ ol.Map.createOptionsInternal = function(mapOptions) {
|
||||
var target = goog.dom.getElement(mapOptions.target);
|
||||
|
||||
return {
|
||||
constraints: constraints,
|
||||
controls: controls,
|
||||
interactions: interactions,
|
||||
rendererConstructor: rendererConstructor,
|
||||
@@ -1024,40 +843,6 @@ ol.Map.createOptionsInternal = function(mapOptions) {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @param {ol.MapOptions} mapOptions Map options.
|
||||
* @return {ol.Constraints} Map constraints.
|
||||
*/
|
||||
ol.Map.createConstraints_ = function(mapOptions) {
|
||||
var resolutionConstraint;
|
||||
if (goog.isDef(mapOptions.resolutions)) {
|
||||
resolutionConstraint = ol.ResolutionConstraint.createSnapToResolutions(
|
||||
mapOptions.resolutions);
|
||||
} else {
|
||||
var maxResolution, numZoomLevels, zoomFactor;
|
||||
if (goog.isDef(mapOptions.maxResolution) &&
|
||||
goog.isDef(mapOptions.numZoomLevels) &&
|
||||
goog.isDef(mapOptions.zoomFactor)) {
|
||||
maxResolution = mapOptions.maxResolution;
|
||||
numZoomLevels = mapOptions.numZoomLevels;
|
||||
zoomFactor = mapOptions.zoomFactor;
|
||||
} else {
|
||||
maxResolution = ol.Projection.EPSG_3857_HALF_SIZE / 128;
|
||||
// number of steps we want between two data resolutions
|
||||
var numSteps = 4;
|
||||
numZoomLevels = 29 * numSteps;
|
||||
zoomFactor = Math.exp(Math.log(2) / numSteps);
|
||||
}
|
||||
resolutionConstraint = ol.ResolutionConstraint.createSnapToPower(
|
||||
zoomFactor, maxResolution, numZoomLevels - 1);
|
||||
}
|
||||
// FIXME rotation constraint is not configurable at the moment
|
||||
var rotationConstraint = ol.RotationConstraint.none;
|
||||
return new ol.Constraints(resolutionConstraint, rotationConstraint);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @param {ol.MapOptions} mapOptions Map options.
|
||||
@@ -1139,3 +924,20 @@ ol.Map.createInteractions_ = function(mapOptions) {
|
||||
return interactions;
|
||||
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {goog.Uri.QueryData=} opt_queryData Query data.
|
||||
* @return {Array.<ol.RendererHint>} Renderer hints.
|
||||
*/
|
||||
ol.RendererHints.createFromQueryData = function(opt_queryData) {
|
||||
var queryData = goog.isDef(opt_queryData) ?
|
||||
opt_queryData : new goog.Uri.QueryData(goog.global.location.search);
|
||||
if (queryData.containsKey('renderers')) {
|
||||
return queryData.get('renderers').split(',');
|
||||
} else if (queryData.containsKey('renderer')) {
|
||||
return [queryData.get('renderer')];
|
||||
} else {
|
||||
return ol.DEFAULT_RENDERER_HINTS;
|
||||
}
|
||||
};
|
||||
|
||||
@@ -270,7 +270,9 @@ ol.MapBrowserEventHandler.prototype.drag_ = function(browserEvent) {
|
||||
};
|
||||
|
||||
|
||||
/** @override */
|
||||
/**
|
||||
* FIXME empty description for jsdoc
|
||||
*/
|
||||
ol.MapBrowserEventHandler.prototype.disposeInternal = function() {
|
||||
var element = this.map_.getViewport();
|
||||
goog.events.unlisten(element,
|
||||
|
||||
@@ -1,6 +1,16 @@
|
||||
goog.provide('ol.MapEvent');
|
||||
goog.provide('ol.MapEventType');
|
||||
|
||||
goog.require('goog.events.Event');
|
||||
goog.require('ol.FrameState');
|
||||
|
||||
|
||||
/**
|
||||
* @enum {string}
|
||||
*/
|
||||
ol.MapEventType = {
|
||||
POSTRENDER: 'postrender'
|
||||
};
|
||||
|
||||
|
||||
|
||||
@@ -9,8 +19,9 @@ goog.require('goog.events.Event');
|
||||
* @extends {goog.events.Event}
|
||||
* @param {string} type Event type.
|
||||
* @param {ol.Map} map Map.
|
||||
* @param {?ol.FrameState=} opt_frameState Frame state.
|
||||
*/
|
||||
ol.MapEvent = function(type, map) {
|
||||
ol.MapEvent = function(type, map, opt_frameState) {
|
||||
|
||||
goog.base(this, type);
|
||||
|
||||
@@ -24,6 +35,11 @@ ol.MapEvent = function(type, map) {
|
||||
*/
|
||||
this.defaultPrevented = false;
|
||||
|
||||
/**
|
||||
* @type {?ol.FrameState}
|
||||
*/
|
||||
this.frameState = goog.isDef(opt_frameState) ? opt_frameState : null;
|
||||
|
||||
};
|
||||
goog.inherits(ol.MapEvent, goog.events.Event);
|
||||
|
||||
|
||||
@@ -6,6 +6,7 @@
|
||||
*/
|
||||
|
||||
goog.provide('ol.Object');
|
||||
goog.provide('ol.ObjectEventType');
|
||||
|
||||
goog.require('goog.array');
|
||||
goog.require('goog.events');
|
||||
@@ -13,6 +14,14 @@ goog.require('goog.events.EventTarget');
|
||||
goog.require('goog.object');
|
||||
|
||||
|
||||
/**
|
||||
* @enum {string}
|
||||
*/
|
||||
ol.ObjectEventType = {
|
||||
CHANGED: 'changed'
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @enum {string}
|
||||
*/
|
||||
@@ -192,6 +201,7 @@ ol.Object.prototype.notify = function(key) {
|
||||
ol.Object.prototype.notifyInternal_ = function(key) {
|
||||
var eventType = ol.Object.getChangedEventType(key);
|
||||
this.dispatchEvent(eventType);
|
||||
this.dispatchEvent(ol.ObjectEventType.CHANGED);
|
||||
};
|
||||
|
||||
|
||||
|
||||
@@ -43,7 +43,13 @@ ol.overlay.Overlay = function(overlayOptions) {
|
||||
* @private
|
||||
* @type {Array.<number>}
|
||||
*/
|
||||
this.mapListenerKeys_ = [];
|
||||
this.mapListenerKeys_ = null;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Array.<number>}
|
||||
*/
|
||||
this.viewListenerKeys_ = null;
|
||||
|
||||
if (goog.isDef(overlayOptions.coordinate)) {
|
||||
this.setCoordinate(overlayOptions.coordinate);
|
||||
@@ -60,6 +66,37 @@ ol.overlay.Overlay = function(overlayOptions) {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @private
|
||||
*/
|
||||
ol.overlay.Overlay.prototype.handleViewChanged_ = function() {
|
||||
goog.asserts.assert(!goog.isNull(this.map_));
|
||||
if (!goog.isNull(this.viewListenerKeys_)) {
|
||||
goog.array.forEach(this.viewListenerKeys_, goog.events.unlistenByKey);
|
||||
this.viewListenerKeys_ = null;
|
||||
}
|
||||
var view = this.map_.getView();
|
||||
if (goog.isDefAndNotNull(view)) {
|
||||
// FIXME works for View2D only
|
||||
goog.asserts.assert(view instanceof ol.View2D);
|
||||
this.viewListenerKeys_ = [
|
||||
goog.events.listen(
|
||||
view, ol.Object.getChangedEventType(ol.View2DProperty.CENTER),
|
||||
this.updatePixelPosition_, false, this),
|
||||
|
||||
goog.events.listen(
|
||||
view, ol.Object.getChangedEventType(ol.View2DProperty.RESOLUTION),
|
||||
this.updatePixelPosition_, false, this),
|
||||
|
||||
goog.events.listen(
|
||||
view, ol.Object.getChangedEventType(ol.View2DProperty.ROTATION),
|
||||
this.updatePixelPosition_, false, this)
|
||||
];
|
||||
this.updatePixelPosition_();
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Coordinate} coordinate Coordinate for the overlay's position on
|
||||
* the map.
|
||||
@@ -100,25 +137,24 @@ ol.overlay.Overlay.prototype.getElement = function() {
|
||||
*/
|
||||
ol.overlay.Overlay.prototype.setMap = function(map) {
|
||||
this.map_ = map;
|
||||
goog.array.forEach(this.mapListenerKeys_, goog.events.unlistenByKey);
|
||||
if (!goog.isNull(this.mapListenerKeys_)) {
|
||||
goog.array.forEach(this.mapListenerKeys_, goog.events.unlistenByKey);
|
||||
this.mapListenerKeys_ = null;
|
||||
}
|
||||
if (this.element_) {
|
||||
this.setElement(this.element_);
|
||||
}
|
||||
this.mapListenerKeys_ = map ? [
|
||||
goog.events.listen(
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.CENTER),
|
||||
this.updatePixelPosition_, false, this),
|
||||
goog.events.listen(
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.RESOLUTION),
|
||||
this.updatePixelPosition_, false, this),
|
||||
goog.events.listen(
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.ROTATION),
|
||||
this.updatePixelPosition_, false, this),
|
||||
goog.events.listen(
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.SIZE),
|
||||
this.updatePixelPosition_, false, this)
|
||||
] : [];
|
||||
this.updatePixelPosition_();
|
||||
if (goog.isDefAndNotNull(map)) {
|
||||
this.mapListenerKeys_ = [
|
||||
goog.events.listen(
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.SIZE),
|
||||
this.updatePixelPosition_, false, this),
|
||||
goog.events.listen(
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.VIEW),
|
||||
this.handleViewChanged_, false, this)
|
||||
];
|
||||
this.handleViewChanged_();
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
|
||||
@@ -87,7 +87,7 @@ ol.Projection.prototype.getUnits = function() {
|
||||
*/
|
||||
ol.Proj4jsProjection = function(code, proj4jsProj) {
|
||||
|
||||
var units = /** @type {ol.ProjectionUnits} */ proj4jsProj.units;
|
||||
var units = /** @type {ol.ProjectionUnits} */ (proj4jsProj.units);
|
||||
|
||||
goog.base(this, code, units, null);
|
||||
|
||||
|
||||
@@ -1,6 +1,9 @@
|
||||
goog.provide('ol.renderer.dom.Layer');
|
||||
|
||||
goog.require('ol.Coordinate');
|
||||
goog.require('ol.FrameState');
|
||||
goog.require('ol.layer.Layer');
|
||||
goog.require('ol.layer.LayerState');
|
||||
goog.require('ol.renderer.Layer');
|
||||
|
||||
|
||||
@@ -13,6 +16,7 @@ goog.require('ol.renderer.Layer');
|
||||
* @param {!Element} target Target.
|
||||
*/
|
||||
ol.renderer.dom.Layer = function(mapRenderer, layer, target) {
|
||||
|
||||
goog.base(this, mapRenderer, layer);
|
||||
|
||||
/**
|
||||
@@ -21,27 +25,15 @@ ol.renderer.dom.Layer = function(mapRenderer, layer, target) {
|
||||
*/
|
||||
this.target = target;
|
||||
|
||||
/**
|
||||
* Top left corner of the target in map coords.
|
||||
*
|
||||
* @type {ol.Coordinate}
|
||||
* @protected
|
||||
*/
|
||||
this.origin = null;
|
||||
|
||||
this.handleLayerOpacityChange();
|
||||
this.handleLayerVisibleChange();
|
||||
|
||||
};
|
||||
goog.inherits(ol.renderer.dom.Layer, ol.renderer.Layer);
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
* @return {ol.renderer.Map} Map renderer.
|
||||
* @return {!Element} Target.
|
||||
*/
|
||||
ol.renderer.dom.Layer.prototype.getMapRenderer = function() {
|
||||
return /** @type {ol.renderer.dom.Map} */ goog.base(this, 'getMapRenderer');
|
||||
ol.renderer.dom.Layer.prototype.getTarget = function() {
|
||||
return this.target;
|
||||
};
|
||||
|
||||
|
||||
@@ -57,7 +49,7 @@ ol.renderer.dom.Layer.prototype.handleLayerLoad = function() {
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.dom.Layer.prototype.handleLayerOpacityChange = function() {
|
||||
goog.style.setOpacity(this.target, this.getLayer().getOpacity());
|
||||
this.getMap().render();
|
||||
};
|
||||
|
||||
|
||||
@@ -65,22 +57,12 @@ ol.renderer.dom.Layer.prototype.handleLayerOpacityChange = function() {
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.dom.Layer.prototype.handleLayerVisibleChange = function() {
|
||||
goog.style.showElement(this.target, this.getLayer().getVisible());
|
||||
this.getMap().render();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Render.
|
||||
* @param {number} time Time.
|
||||
* @param {ol.FrameState} frameState Frame state.
|
||||
* @param {ol.layer.LayerState} layerState Layer state.
|
||||
*/
|
||||
ol.renderer.dom.Layer.prototype.renderFrame = goog.abstractMethod;
|
||||
|
||||
|
||||
/**
|
||||
* Set the location of the top left corner of the target.
|
||||
*
|
||||
* @param {ol.Coordinate} origin Origin.
|
||||
*/
|
||||
ol.renderer.dom.Layer.prototype.setOrigin = function(origin) {
|
||||
this.origin = origin;
|
||||
};
|
||||
|
||||
@@ -5,8 +5,9 @@ goog.require('goog.dom');
|
||||
goog.require('goog.dom.TagName');
|
||||
goog.require('goog.events');
|
||||
goog.require('goog.events.Event');
|
||||
goog.require('goog.functions');
|
||||
goog.require('goog.style');
|
||||
goog.require('ol.Coordinate');
|
||||
goog.require('ol.FrameState');
|
||||
goog.require('ol.layer.TileLayer');
|
||||
goog.require('ol.renderer.Map');
|
||||
goog.require('ol.renderer.dom.TileLayer');
|
||||
@@ -37,92 +38,32 @@ ol.renderer.dom.Map = function(container, map) {
|
||||
goog.dom.insertChildAt(container, this.layersPane_, 0);
|
||||
|
||||
/**
|
||||
* @type {Object}
|
||||
* @private
|
||||
* @type {boolean}
|
||||
*/
|
||||
this.layerPanes_ = {};
|
||||
this.renderedVisible_ = true;
|
||||
|
||||
/**
|
||||
* @type {ol.Coordinate}
|
||||
* @private
|
||||
*/
|
||||
this.renderedCenter_ = null;
|
||||
|
||||
/**
|
||||
* @type {number | undefined}
|
||||
* @private
|
||||
*/
|
||||
this.renderedResolution_ = undefined;
|
||||
|
||||
/**
|
||||
* @type {ol.Size}
|
||||
* @private
|
||||
*/
|
||||
this.renderedSize_ = null;
|
||||
|
||||
/**
|
||||
* @type {number | undefined}
|
||||
* @private
|
||||
*/
|
||||
this.renderedRotation_ = undefined;
|
||||
|
||||
/**
|
||||
* The origin (top left) of the layers pane in map coordinates.
|
||||
*
|
||||
* @type {ol.Coordinate}
|
||||
* @private
|
||||
*/
|
||||
this.layersPaneOrigin_ = null;
|
||||
};
|
||||
goog.inherits(ol.renderer.dom.Map, ol.renderer.Map);
|
||||
|
||||
|
||||
/**
|
||||
* Apply the given transform to the layers pane.
|
||||
* @param {number} dx Translation along the x-axis.
|
||||
* @param {number} dy Translation along the y-axis.
|
||||
* @param {number} rotation Rotation angle.
|
||||
* @private
|
||||
*/
|
||||
ol.renderer.dom.Map.prototype.applyTransform_ = function(dx, dy, rotation) {
|
||||
var transform =
|
||||
'translate(' + Math.round(dx) + 'px, ' + Math.round(dy) + 'px) ' +
|
||||
'rotate(' + rotation.toFixed(6) + 'rad) ' +
|
||||
'scale3d(1, 1, 1)';
|
||||
|
||||
var style = this.layersPane_.style;
|
||||
style.WebkitTransform = transform;
|
||||
style.MozTransform = transform;
|
||||
style.OTransform = transform;
|
||||
style.msTransform = transform;
|
||||
style.transform = transform;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.dom.Map.prototype.canRotate = goog.functions.TRUE;
|
||||
ol.renderer.dom.Map.prototype.addLayer = function(layer) {
|
||||
goog.base(this, 'addLayer', layer);
|
||||
this.getMap().render();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.dom.Map.prototype.createLayerRenderer = function(layer) {
|
||||
|
||||
if (layer instanceof ol.layer.TileLayer) {
|
||||
|
||||
var layerPane = goog.dom.createElement(goog.dom.TagName.DIV);
|
||||
layerPane.className = 'ol-layer';
|
||||
layerPane.style.position = 'absolute';
|
||||
goog.dom.appendChild(this.layersPane_, layerPane);
|
||||
|
||||
var layerRenderer = new ol.renderer.dom.TileLayer(this, layer, layerPane);
|
||||
|
||||
this.layerPanes_[goog.getUid(layerRenderer)] = layerPane;
|
||||
|
||||
var layerRenderer = new ol.renderer.dom.TileLayer(this, layer);
|
||||
goog.dom.appendChild(this.layersPane_, layerRenderer.getTarget());
|
||||
return layerRenderer;
|
||||
|
||||
} else {
|
||||
goog.asserts.assert(false);
|
||||
return null;
|
||||
@@ -133,8 +74,8 @@ ol.renderer.dom.Map.prototype.createLayerRenderer = function(layer) {
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.dom.Map.prototype.handleCenterChanged = function() {
|
||||
goog.base(this, 'handleCenterChanged');
|
||||
ol.renderer.dom.Map.prototype.removeLayer = function(layer) {
|
||||
goog.base(this, 'removeLayer', layer);
|
||||
this.getMap().render();
|
||||
};
|
||||
|
||||
@@ -142,145 +83,30 @@ ol.renderer.dom.Map.prototype.handleCenterChanged = function() {
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.dom.Map.prototype.handleResolutionChanged = function() {
|
||||
goog.base(this, 'handleResolutionChanged');
|
||||
this.getMap().render();
|
||||
};
|
||||
ol.renderer.dom.Map.prototype.renderFrame = function(frameState) {
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.dom.Map.prototype.handleRotationChanged = function() {
|
||||
goog.base(this, 'handleRotationChanged');
|
||||
this.getMap().render();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.dom.Map.prototype.handleSizeChanged = function() {
|
||||
goog.base(this, 'handleSizeChanged');
|
||||
this.getMap().render();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Render the map. Sets up the layers pane on first render and adjusts its
|
||||
* position as needed on subsequent calls.
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.dom.Map.prototype.renderFrame = function(time) {
|
||||
var map = this.getMap();
|
||||
if (!map.isDef()) {
|
||||
if (goog.isNull(frameState)) {
|
||||
if (this.renderedVisible_) {
|
||||
goog.style.showElement(this.layersPane_, false);
|
||||
this.renderedVisible_ = false;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
var mapCenter = map.getCenter();
|
||||
var mapSize = map.getSize();
|
||||
var mapResolution = map.getResolution();
|
||||
var mapRotation = map.getRotation();
|
||||
|
||||
goog.asserts.assert(goog.isDefAndNotNull(mapCenter));
|
||||
goog.asserts.assert(goog.isDef(mapResolution));
|
||||
goog.asserts.assert(goog.isDef(mapRotation));
|
||||
goog.asserts.assert(goog.isDefAndNotNull(mapSize));
|
||||
|
||||
if (goog.isNull(this.renderedCenter_)) {
|
||||
// first rendering
|
||||
goog.asserts.assert(!goog.isDef(this.renderedResolution_));
|
||||
goog.asserts.assert(!goog.isDef(this.renderedRotation_));
|
||||
goog.asserts.assert(goog.isNull(this.renderedSize_));
|
||||
this.resetLayersPane_();
|
||||
} else {
|
||||
goog.asserts.assert(goog.isDef(this.renderedResolution_));
|
||||
goog.asserts.assert(!goog.isNull(this.renderedSize_));
|
||||
if (mapResolution !== this.renderedResolution_ ||
|
||||
!mapSize.equals(this.renderedSize_)) {
|
||||
// resolution or size changed, adjust layers pane
|
||||
this.resetLayersPane_();
|
||||
} else if (!mapCenter.equals(this.renderedCenter_) ||
|
||||
mapRotation !== this.renderedRotation_) {
|
||||
// same resolution and size, new center or rotation
|
||||
this.transformLayersPane_();
|
||||
goog.array.forEach(frameState.layersArray, function(layer) {
|
||||
var layerState = frameState.layerStates[goog.getUid(layer)];
|
||||
if (!layerState.ready) {
|
||||
return;
|
||||
}
|
||||
var layerRenderer = this.getLayerRenderer(layer);
|
||||
layerRenderer.renderFrame(frameState, layerState);
|
||||
}, this);
|
||||
|
||||
if (!this.renderedVisible_) {
|
||||
goog.style.showElement(this.layersPane_, true);
|
||||
this.renderedVisible_ = true;
|
||||
}
|
||||
|
||||
this.renderedCenter_ = mapCenter;
|
||||
this.renderedResolution_ = mapResolution;
|
||||
this.renderedRotation_ = mapRotation;
|
||||
this.renderedSize_ = mapSize;
|
||||
|
||||
var requestRenderFrame = false;
|
||||
this.forEachReadyVisibleLayer(function(layer, layerRenderer) {
|
||||
if (layerRenderer.renderFrame(time)) {
|
||||
requestRenderFrame = true;
|
||||
}
|
||||
});
|
||||
|
||||
if (requestRenderFrame) {
|
||||
map.requestRenderFrame();
|
||||
}
|
||||
this.calculateMatrices2D(frameState);
|
||||
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Reset the layers pane to its initial position.
|
||||
* @private
|
||||
*/
|
||||
ol.renderer.dom.Map.prototype.resetLayersPane_ = function() {
|
||||
var map = this.map;
|
||||
var mapSize = map.getSize();
|
||||
var halfWidth = mapSize.width / 2;
|
||||
var halfHeight = mapSize.height / 2;
|
||||
var center = map.getCenter();
|
||||
var resolution = map.getResolution();
|
||||
var origin = new ol.Coordinate(
|
||||
center.x - resolution * halfWidth,
|
||||
center.y + resolution * halfHeight);
|
||||
this.layersPaneOrigin_ = origin;
|
||||
this.setTransformOrigin_(halfWidth, halfHeight);
|
||||
this.applyTransform_(0, 0, map.getRotation());
|
||||
goog.object.forEach(this.layerRenderers, function(layerRenderer) {
|
||||
layerRenderer.setOrigin(origin);
|
||||
});
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Set the transform-origin CSS property of the layers pane.
|
||||
* @param {number} x The x-axis origin.
|
||||
* @param {number} y The y-axis origin.
|
||||
* @private
|
||||
*/
|
||||
ol.renderer.dom.Map.prototype.setTransformOrigin_ = function(x, y) {
|
||||
var origin = Math.round(x) + 'px ' + Math.round(y) + 'px';
|
||||
var style = this.layersPane_.style;
|
||||
style.WebkitTransformOrigin = origin;
|
||||
style.MozTransformOrigin = origin;
|
||||
style.OTransformOrigin = origin;
|
||||
style.msTransformOrigin = origin;
|
||||
style.transformOrigin = origin;
|
||||
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Apply the appropriate transform to the layers pane.
|
||||
* @private
|
||||
*/
|
||||
ol.renderer.dom.Map.prototype.transformLayersPane_ = function() {
|
||||
var map = this.map;
|
||||
var resolution = map.getResolution();
|
||||
var center = map.getCenter();
|
||||
var size = map.getSize();
|
||||
var origin = this.layersPaneOrigin_;
|
||||
var ox = (center.x - origin.x) / resolution;
|
||||
var oy = (origin.y - center.y) / resolution;
|
||||
this.setTransformOrigin_(ox, oy);
|
||||
var dx = ox - (size.width / 2);
|
||||
var dy = oy - (size.height / 2);
|
||||
this.applyTransform_(-dx, -dy, map.getRotation());
|
||||
};
|
||||
|
||||
@@ -1,13 +1,23 @@
|
||||
// FIXME probably need to reset TileLayerZ if offsets get too large
|
||||
// FIXME when zooming out, preserve higher Z divs to avoid white flash
|
||||
|
||||
goog.provide('ol.renderer.dom.TileLayer');
|
||||
|
||||
goog.require('goog.asserts');
|
||||
goog.require('goog.dom');
|
||||
goog.require('goog.events');
|
||||
goog.require('goog.events.Event');
|
||||
goog.require('goog.events.EventType');
|
||||
goog.require('goog.math.Vec2');
|
||||
goog.require('goog.style');
|
||||
goog.require('goog.vec.Mat4');
|
||||
goog.require('ol.Coordinate');
|
||||
goog.require('ol.Extent');
|
||||
goog.require('ol.Size');
|
||||
goog.require('ol.TileCoord');
|
||||
goog.require('ol.TileRange');
|
||||
goog.require('ol.TileState');
|
||||
goog.require('ol.ViewHint');
|
||||
goog.require('ol.dom');
|
||||
goog.require('ol.renderer.dom.Layer');
|
||||
goog.require('ol.tilegrid.TileGrid');
|
||||
|
||||
|
||||
|
||||
@@ -16,212 +26,363 @@ goog.require('ol.renderer.dom.Layer');
|
||||
* @extends {ol.renderer.dom.Layer}
|
||||
* @param {ol.renderer.Map} mapRenderer Map renderer.
|
||||
* @param {ol.layer.TileLayer} tileLayer Tile layer.
|
||||
* @param {!Element} target Target.
|
||||
*/
|
||||
ol.renderer.dom.TileLayer = function(mapRenderer, tileLayer, target) {
|
||||
ol.renderer.dom.TileLayer = function(mapRenderer, tileLayer) {
|
||||
|
||||
var target = goog.dom.createElement(goog.dom.TagName.DIV);
|
||||
target.className = 'ol-layer';
|
||||
target.style.position = 'absolute';
|
||||
|
||||
goog.base(this, mapRenderer, tileLayer, target);
|
||||
|
||||
/**
|
||||
* @type {Object}
|
||||
* @private
|
||||
* @type {boolean}
|
||||
*/
|
||||
this.renderedTiles_ = {};
|
||||
this.renderedVisible_ = true;
|
||||
|
||||
/**
|
||||
* @type {number|undefined}
|
||||
* @private
|
||||
* @type {number}
|
||||
*/
|
||||
this.renderedMapResolution_ = undefined;
|
||||
this.renderedOpacity_ = 1;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Object.<number, ol.renderer.dom.TileLayerZ_>}
|
||||
*/
|
||||
this.tileLayerZs_ = {};
|
||||
|
||||
};
|
||||
goog.inherits(ol.renderer.dom.TileLayer, ol.renderer.dom.Layer);
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.layer.TileLayer} Tile layer.
|
||||
*/
|
||||
ol.renderer.dom.TileLayer.prototype.getTileLayer = function() {
|
||||
return /** @type {ol.layer.TileLayer} */ (this.getLayer());
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
* @return {ol.layer.TileLayer} Layer.
|
||||
*/
|
||||
ol.renderer.dom.TileLayer.prototype.getLayer = function() {
|
||||
return /** @type {ol.layer.TileLayer} */ goog.base(this, 'getLayer');
|
||||
};
|
||||
ol.renderer.dom.TileLayer.prototype.renderFrame =
|
||||
function(frameState, layerState) {
|
||||
|
||||
|
||||
/**
|
||||
* Get the pixel offset between the tile origin and the container origin.
|
||||
* @private
|
||||
* @param {number} z Z.
|
||||
* @param {number} resolution Resolution.
|
||||
* @return {ol.Coordinate} Offset.
|
||||
*/
|
||||
ol.renderer.dom.TileLayer.prototype.getTileOffset_ = function(z, resolution) {
|
||||
var tileLayer = this.getLayer();
|
||||
var tileSource = tileLayer.getTileSource();
|
||||
var tileGrid = tileSource.getTileGrid();
|
||||
var tileOrigin = tileGrid.getOrigin(z);
|
||||
var offset = new ol.Coordinate(
|
||||
Math.round((this.origin.x - tileOrigin.x) / resolution),
|
||||
Math.round((tileOrigin.y - this.origin.y) / resolution));
|
||||
return offset;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Get rid of all tiles that weren't drawn in the most recent rendering.
|
||||
* @param {Object.<number, Object.<string, ol.Tile>>} tilesDrawnByZ Tiles just
|
||||
* rendered.
|
||||
* @private
|
||||
*/
|
||||
ol.renderer.dom.TileLayer.prototype.removeExtraTiles_ =
|
||||
function(tilesDrawnByZ) {
|
||||
var key, tileCoord, tilesDrawn, tile;
|
||||
for (key in this.renderedTiles_) {
|
||||
tileCoord = ol.TileCoord.createFromString(key);
|
||||
tilesDrawn = tilesDrawnByZ[tileCoord.z];
|
||||
if (!(tilesDrawn && key in tilesDrawn)) {
|
||||
tile = this.renderedTiles_[key];
|
||||
delete this.renderedTiles_[key];
|
||||
goog.dom.removeNode(tile.getImage(this));
|
||||
if (!layerState.visible) {
|
||||
if (this.renderedVisible_) {
|
||||
goog.style.showElement(this.target, false);
|
||||
this.renderedVisible_ = false;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.dom.TileLayer.prototype.renderFrame = function(time) {
|
||||
|
||||
var map = this.getMap();
|
||||
if (!map.isDef()) {
|
||||
return;
|
||||
}
|
||||
var mapExtent = /** @type {!ol.Extent} */ map.getRotatedExtent();
|
||||
var mapResolution = /** @type {number} */ map.getResolution();
|
||||
var resolutionChanged = (mapResolution !== this.renderedMapResolution_);
|
||||
|
||||
var tileLayer = this.getLayer();
|
||||
var view2DState = frameState.view2DState;
|
||||
|
||||
var tileLayer = this.getTileLayer();
|
||||
var tileSource = tileLayer.getTileSource();
|
||||
var tileGrid = tileSource.getTileGrid();
|
||||
var z = tileGrid.getZForResolution(view2DState.resolution);
|
||||
var tileResolution = tileGrid.getResolution(z);
|
||||
var tileRange = tileGrid.getTileRangeForExtentAndResolution(
|
||||
frameState.extent, tileResolution);
|
||||
|
||||
// z represents the "best" resolution
|
||||
var z = tileGrid.getZForResolution(mapResolution);
|
||||
|
||||
/**
|
||||
* @type {Object.<number, Object.<string, ol.Tile>>}
|
||||
*/
|
||||
/** @type {Object.<number, Object.<string, ol.Tile>>} */
|
||||
var tilesToDrawByZ = {};
|
||||
tilesToDrawByZ[z] = {};
|
||||
|
||||
var tileRange =
|
||||
tileGrid.getTileRangeForExtentAndResolution(mapExtent, mapResolution);
|
||||
var findInterimTiles = function(z, tileRange) {
|
||||
// FIXME this could be more efficient about filling partial holes
|
||||
var fullyCovered = true;
|
||||
var tile, tileCoord, tileCoordKey, x, y;
|
||||
for (x = tileRange.minX; x <= tileRange.maxX; ++x) {
|
||||
for (y = tileRange.minY; y <= tileRange.maxY; ++y) {
|
||||
tileCoord = new ol.TileCoord(z, x, y);
|
||||
tileCoordKey = tileCoord.toString();
|
||||
if (tilesToDrawByZ[z] && tilesToDrawByZ[z][tileCoordKey]) {
|
||||
return;
|
||||
}
|
||||
tile = tileSource.getTile(tileCoord);
|
||||
if (!goog.isNull(tile) && tile.getState() == ol.TileState.LOADED) {
|
||||
if (!tilesToDrawByZ[z]) {
|
||||
tilesToDrawByZ[z] = {};
|
||||
}
|
||||
tilesToDrawByZ[z][tileCoordKey] = tile;
|
||||
} else {
|
||||
fullyCovered = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
return fullyCovered;
|
||||
};
|
||||
|
||||
var allTilesLoaded = true;
|
||||
var tile, tileCenter, tileCoord, tileState, x, y;
|
||||
for (x = tileRange.minX; x <= tileRange.maxX; ++x) {
|
||||
for (y = tileRange.minY; y <= tileRange.maxY; ++y) {
|
||||
|
||||
tileCoord = new ol.TileCoord(z, x, y);
|
||||
tile = tileSource.getTile(tileCoord);
|
||||
if (goog.isNull(tile)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
tileState = tile.getState();
|
||||
if (tileState == ol.TileState.IDLE) {
|
||||
tileCenter = tileGrid.getTileCoordCenter(tileCoord);
|
||||
frameState.tileQueue.enqueue(tile, tileCenter, tileResolution);
|
||||
} else if (tileState == ol.TileState.LOADED) {
|
||||
tilesToDrawByZ[z][tileCoord.toString()] = tile;
|
||||
continue;
|
||||
} else if (tileState == ol.TileState.ERROR) {
|
||||
continue;
|
||||
}
|
||||
|
||||
allTilesLoaded = false;
|
||||
tileGrid.forEachTileCoordParentTileRange(tileCoord, findInterimTiles);
|
||||
|
||||
// first pass through the tile range to determine all the tiles needed
|
||||
tileRange.forEachTileCoord(z, function(tileCoord) {
|
||||
var tile = tileSource.getTile(tileCoord);
|
||||
if (goog.isNull(tile)) {
|
||||
// we're outside the source's extent, continue
|
||||
return;
|
||||
}
|
||||
|
||||
var key = tile.tileCoord.toString();
|
||||
var state = tile.getState();
|
||||
if (state == ol.TileState.IDLE) {
|
||||
tile.load();
|
||||
} else if (state == ol.TileState.LOADED) {
|
||||
tilesToDrawByZ[z][key] = tile;
|
||||
return;
|
||||
}
|
||||
|
||||
allTilesLoaded = false;
|
||||
|
||||
/**
|
||||
* Look for already loaded tiles at alternate z that can serve as
|
||||
* placeholders until tiles at the current z have loaded.
|
||||
*
|
||||
* TODO: make this more efficent for filling partial holes
|
||||
*/
|
||||
tileGrid.forEachTileCoordParentTileRange(
|
||||
tileCoord,
|
||||
function(altZ, altTileRange) {
|
||||
var fullyCovered = true;
|
||||
altTileRange.forEachTileCoord(altZ, function(altTileCoord) {
|
||||
var tileKey = altTileCoord.toString();
|
||||
if (tilesToDrawByZ[altZ] && tilesToDrawByZ[altZ][tileKey]) {
|
||||
return;
|
||||
}
|
||||
var altTile = tileSource.getTile(altTileCoord);
|
||||
if (!goog.isNull(altTile) &&
|
||||
altTile.getState() == ol.TileState.LOADED) {
|
||||
if (!(altZ in tilesToDrawByZ)) {
|
||||
tilesToDrawByZ[altZ] = {};
|
||||
}
|
||||
tilesToDrawByZ[altZ][tileKey] = altTile;
|
||||
} else {
|
||||
fullyCovered = false;
|
||||
}
|
||||
});
|
||||
return fullyCovered;
|
||||
});
|
||||
|
||||
}, this);
|
||||
}
|
||||
|
||||
/** @type {Array.<number>} */
|
||||
var zs = goog.array.map(goog.object.getKeys(tilesToDrawByZ), Number);
|
||||
goog.array.sort(zs);
|
||||
|
||||
var fragment = document.createDocumentFragment();
|
||||
var altFragment = document.createDocumentFragment();
|
||||
var newTiles = false;
|
||||
var newAltTiles = false;
|
||||
for (var i = 0, ii = zs.length; i < ii; ++i) {
|
||||
var tileZ = zs[i];
|
||||
var tilesToDraw = tilesToDrawByZ[tileZ];
|
||||
var tileOffset = this.getTileOffset_(tileZ, mapResolution);
|
||||
for (var key in tilesToDraw) {
|
||||
var tile = tilesToDraw[key];
|
||||
var tileCoord = tile.tileCoord;
|
||||
var pixelBounds = tileGrid.getPixelBoundsForTileCoordAndResolution(
|
||||
tileCoord, mapResolution);
|
||||
var img = tile.getImage(this);
|
||||
var style = img.style;
|
||||
var append = !(key in this.renderedTiles_);
|
||||
if (append || resolutionChanged) {
|
||||
style.left = (pixelBounds.minX - tileOffset.x) + 'px';
|
||||
style.top = (-pixelBounds.maxY - tileOffset.y) + 'px';
|
||||
style.width = pixelBounds.getWidth() + 'px';
|
||||
style.height = pixelBounds.getHeight() + 'px';
|
||||
}
|
||||
if (append) {
|
||||
this.renderedTiles_[key] = tile;
|
||||
style.position = 'absolute';
|
||||
if (tileZ === z) {
|
||||
goog.dom.appendChild(fragment, img);
|
||||
newTiles = true;
|
||||
} else {
|
||||
goog.dom.appendChild(altFragment, img);
|
||||
newAltTiles = true;
|
||||
/** @type {Object.<number, boolean>} */
|
||||
var newTileLayerZKeys = {};
|
||||
|
||||
var tileSize = tileGrid.getTileSize();
|
||||
var iz, tileCoordKey, tileCoordOrigin, tileLayerZ, tileLayerZKey, tilesToDraw;
|
||||
for (iz = 0; iz < zs.length; ++iz) {
|
||||
tileLayerZKey = zs[iz];
|
||||
if (tileLayerZKey in this.tileLayerZs_) {
|
||||
tileLayerZ = this.tileLayerZs_[tileLayerZKey];
|
||||
} else {
|
||||
tileCoordOrigin =
|
||||
tileGrid.getTileCoordForCoordAndZ(view2DState.center, tileLayerZKey);
|
||||
tileLayerZ = new ol.renderer.dom.TileLayerZ_(tileGrid, tileCoordOrigin);
|
||||
newTileLayerZKeys[tileLayerZKey] = true;
|
||||
this.tileLayerZs_[tileLayerZKey] = tileLayerZ;
|
||||
}
|
||||
tilesToDraw = tilesToDrawByZ[tileLayerZKey];
|
||||
for (tileCoordKey in tilesToDraw) {
|
||||
tileLayerZ.addTile(tilesToDraw[tileCoordKey]);
|
||||
}
|
||||
tileLayerZ.finalizeAddTiles();
|
||||
}
|
||||
|
||||
/** @type {Array.<number>} */
|
||||
var tileLayerZKeys =
|
||||
goog.array.map(goog.object.getKeys(this.tileLayerZs_), Number);
|
||||
goog.array.sort(tileLayerZKeys);
|
||||
|
||||
var i, j, origin, resolution;
|
||||
var transform = goog.vec.Mat4.createNumber();
|
||||
for (i = 0; i < tileLayerZKeys.length; ++i) {
|
||||
tileLayerZKey = tileLayerZKeys[i];
|
||||
tileLayerZ = this.tileLayerZs_[tileLayerZKey];
|
||||
if (!(tileLayerZKey in tilesToDrawByZ)) {
|
||||
goog.dom.removeNode(tileLayerZ.target);
|
||||
delete this.tileLayerZs_[tileLayerZKey];
|
||||
continue;
|
||||
}
|
||||
resolution = tileLayerZ.getResolution();
|
||||
origin = tileLayerZ.getOrigin();
|
||||
goog.vec.Mat4.makeIdentity(transform);
|
||||
goog.vec.Mat4.translate(
|
||||
transform, frameState.size.width / 2, frameState.size.height / 2, 0);
|
||||
goog.vec.Mat4.rotateZ(transform, view2DState.rotation);
|
||||
goog.vec.Mat4.scale(transform, resolution / view2DState.resolution,
|
||||
resolution / view2DState.resolution, 1);
|
||||
goog.vec.Mat4.translate(
|
||||
transform,
|
||||
(origin.x - view2DState.center.x) / resolution,
|
||||
(view2DState.center.y - origin.y) / resolution,
|
||||
0);
|
||||
tileLayerZ.setTransform(transform);
|
||||
if (tileLayerZKey in newTileLayerZKeys) {
|
||||
for (j = tileLayerZKey - 1; j >= 0; --j) {
|
||||
if (j in this.tileLayerZs_) {
|
||||
goog.dom.insertSiblingAfter(
|
||||
tileLayerZ.target, this.tileLayerZs_[j].target);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (newAltTiles) {
|
||||
var child = this.target.firstChild;
|
||||
if (child) {
|
||||
goog.dom.insertSiblingBefore(altFragment, child);
|
||||
if (j < 0) {
|
||||
goog.dom.insertChildAt(this.target, tileLayerZ.target, 0);
|
||||
}
|
||||
} else {
|
||||
goog.dom.appendChild(this.target, altFragment);
|
||||
if (!frameState.viewHints[ol.ViewHint.ANIMATING] &&
|
||||
!frameState.viewHints[ol.ViewHint.PANNING]) {
|
||||
tileLayerZ.removeTilesOutsideExtent(frameState.extent);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (newTiles) {
|
||||
goog.dom.appendChild(this.target, fragment);
|
||||
|
||||
if (layerState.opacity != this.renderedOpacity_) {
|
||||
goog.style.setOpacity(this.target, layerState.opacity);
|
||||
this.renderedOpacity_ = layerState.opacity;
|
||||
}
|
||||
|
||||
this.renderedMapResolution_ = mapResolution;
|
||||
if (layerState.visible && !this.renderedVisible_) {
|
||||
goog.style.showElement(this.target, true);
|
||||
this.renderedVisible_ = true;
|
||||
}
|
||||
|
||||
this.removeExtraTiles_(tilesToDrawByZ);
|
||||
if (!allTilesLoaded) {
|
||||
frameState.animate = true;
|
||||
}
|
||||
|
||||
return !allTilesLoaded;
|
||||
};
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @constructor
|
||||
* @private
|
||||
* @param {ol.tilegrid.TileGrid} tileGrid Tile grid.
|
||||
* @param {ol.TileCoord} tileCoordOrigin Tile coord origin.
|
||||
*/
|
||||
ol.renderer.dom.TileLayerZ_ = function(tileGrid, tileCoordOrigin) {
|
||||
|
||||
/**
|
||||
* @type {!Element}
|
||||
*/
|
||||
this.target = goog.dom.createElement(goog.dom.TagName.DIV);
|
||||
this.target.style.position = 'absolute';
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.tilegrid.TileGrid}
|
||||
*/
|
||||
this.tileGrid_ = tileGrid;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.TileCoord}
|
||||
*/
|
||||
this.tileCoordOrigin_ = tileCoordOrigin;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.Coordinate}
|
||||
*/
|
||||
this.origin_ = tileGrid.getTileCoordExtent(tileCoordOrigin).getTopLeft();
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {number}
|
||||
*/
|
||||
this.resolution_ = tileGrid.getResolution(tileCoordOrigin.z);
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Object.<string, ol.Tile>}
|
||||
*/
|
||||
this.tiles_ = {};
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {DocumentFragment}
|
||||
*/
|
||||
this.documentFragment_ = null;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {goog.vec.Mat4.AnyType}
|
||||
*/
|
||||
this.transform_ = goog.vec.Mat4.createNumberIdentity();
|
||||
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Tile} tile Tile.
|
||||
*/
|
||||
ol.renderer.dom.TileLayerZ_.prototype.addTile = function(tile) {
|
||||
var tileCoord = tile.tileCoord;
|
||||
goog.asserts.assert(tileCoord.z == this.tileCoordOrigin_.z);
|
||||
var tileCoordKey = tileCoord.toString();
|
||||
if (tileCoordKey in this.tiles_) {
|
||||
return;
|
||||
}
|
||||
var tileSize = this.tileGrid_.getTileSize();
|
||||
var image = tile.getImage(this);
|
||||
var style = image.style;
|
||||
style.position = 'absolute';
|
||||
style.left =
|
||||
((tileCoord.x - this.tileCoordOrigin_.x) * tileSize.width) + 'px';
|
||||
style.top =
|
||||
((this.tileCoordOrigin_.y - tileCoord.y) * tileSize.height) + 'px';
|
||||
if (goog.isNull(this.documentFragment_)) {
|
||||
this.documentFragment_ = document.createDocumentFragment();
|
||||
}
|
||||
goog.dom.appendChild(this.documentFragment_, image);
|
||||
this.tiles_[tileCoordKey] = tile;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* FIXME empty description for jsdoc
|
||||
*/
|
||||
ol.renderer.dom.TileLayerZ_.prototype.finalizeAddTiles = function() {
|
||||
if (!goog.isNull(this.documentFragment_)) {
|
||||
goog.dom.appendChild(this.target, this.documentFragment_);
|
||||
this.documentFragment_ = null;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.Coordinate} Origin.
|
||||
*/
|
||||
ol.renderer.dom.TileLayerZ_.prototype.getOrigin = function() {
|
||||
return this.origin_;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {number} Resolution.
|
||||
*/
|
||||
ol.renderer.dom.TileLayerZ_.prototype.getResolution = function() {
|
||||
return this.resolution_;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Extent} extent Extent.
|
||||
*/
|
||||
ol.renderer.dom.TileLayerZ_.prototype.removeTilesOutsideExtent =
|
||||
function(extent) {
|
||||
var tileRange =
|
||||
this.tileGrid_.getTileRangeForExtentAndZ(extent, this.tileCoordOrigin_.z);
|
||||
var tilesToRemove = [];
|
||||
var tile, tileCoordKey;
|
||||
for (tileCoordKey in this.tiles_) {
|
||||
tile = this.tiles_[tileCoordKey];
|
||||
if (!tileRange.contains(tile.tileCoord)) {
|
||||
tilesToRemove.push(tile);
|
||||
}
|
||||
}
|
||||
var i;
|
||||
for (i = 0; i < tilesToRemove.length; ++i) {
|
||||
tile = tilesToRemove[i];
|
||||
tileCoordKey = tile.tileCoord.toString();
|
||||
goog.dom.removeNode(tile.getImage(this));
|
||||
delete this.tiles_[tileCoordKey];
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {goog.vec.Mat4.AnyType} transform Transform.
|
||||
*/
|
||||
ol.renderer.dom.TileLayerZ_.prototype.setTransform = function(transform) {
|
||||
if (!goog.vec.Mat4.equals(transform, this.transform_)) {
|
||||
ol.dom.transformElement2D(this.target, transform, 6);
|
||||
goog.vec.Mat4.setFromArray(this.transform_, transform);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -1,11 +1,15 @@
|
||||
goog.provide('ol.renderer.Map');
|
||||
|
||||
goog.require('goog.Disposable');
|
||||
goog.require('goog.asserts');
|
||||
goog.require('goog.events');
|
||||
goog.require('goog.functions');
|
||||
goog.require('goog.fx.anim');
|
||||
goog.require('goog.fx.anim.Animated');
|
||||
goog.require('goog.vec.Mat4');
|
||||
goog.require('ol.FrameState');
|
||||
goog.require('ol.View2D');
|
||||
goog.require('ol.View2DProperty');
|
||||
|
||||
|
||||
|
||||
@@ -43,23 +47,12 @@ ol.renderer.Map = function(container, map) {
|
||||
*/
|
||||
this.layersListenerKeys_ = null;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {goog.vec.Mat4.Number}
|
||||
*/
|
||||
this.coordinateToPixelMatrix_ = goog.vec.Mat4.createNumber();
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {goog.vec.Mat4.Number}
|
||||
* @type {?number}
|
||||
*/
|
||||
this.pixelToCoordinateMatrix_ = goog.vec.Mat4.createNumber();
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {boolean}
|
||||
*/
|
||||
this.matricesDirty_ = true;
|
||||
this.viewPropertyListenerKey_ = null;
|
||||
|
||||
/**
|
||||
* @private
|
||||
@@ -70,25 +63,17 @@ ol.renderer.Map = function(container, map) {
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.BACKGROUND_COLOR),
|
||||
this.handleBackgroundColorChanged, false, this),
|
||||
|
||||
goog.events.listen(
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.CENTER),
|
||||
this.handleCenterChanged, false, this),
|
||||
|
||||
goog.events.listen(
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.LAYERS),
|
||||
this.handleLayersChanged, false, this),
|
||||
|
||||
goog.events.listen(
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.RESOLUTION),
|
||||
this.handleResolutionChanged, false, this),
|
||||
|
||||
goog.events.listen(
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.ROTATION),
|
||||
this.handleRotationChanged, false, this),
|
||||
|
||||
goog.events.listen(
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.SIZE),
|
||||
this.handleSizeChanged, false, this)
|
||||
this.handleSizeChanged, false, this),
|
||||
|
||||
goog.events.listen(
|
||||
map, ol.Object.getChangedEventType(ol.MapProperty.VIEW),
|
||||
this.handleViewChanged, false, this)
|
||||
];
|
||||
|
||||
};
|
||||
@@ -106,9 +91,35 @@ ol.renderer.Map.prototype.addLayer = function(layer) {
|
||||
|
||||
|
||||
/**
|
||||
* @return {boolean} Can rotate.
|
||||
* @param {ol.FrameState} frameState FrameState.
|
||||
* @protected
|
||||
*/
|
||||
ol.renderer.Map.prototype.canRotate = goog.functions.FALSE;
|
||||
ol.renderer.Map.prototype.calculateMatrices2D = function(frameState) {
|
||||
|
||||
var view2DState = frameState.view2DState;
|
||||
var coordinateToPixelMatrix = frameState.coordinateToPixelMatrix;
|
||||
|
||||
goog.vec.Mat4.makeIdentity(coordinateToPixelMatrix);
|
||||
goog.vec.Mat4.translate(coordinateToPixelMatrix,
|
||||
frameState.size.width / 2,
|
||||
frameState.size.height / 2,
|
||||
0);
|
||||
goog.vec.Mat4.scale(coordinateToPixelMatrix,
|
||||
1 / view2DState.resolution,
|
||||
-1 / view2DState.resolution,
|
||||
1);
|
||||
goog.vec.Mat4.rotateZ(coordinateToPixelMatrix,
|
||||
-view2DState.rotation);
|
||||
goog.vec.Mat4.translate(coordinateToPixelMatrix,
|
||||
-view2DState.center.x,
|
||||
-view2DState.center.y,
|
||||
0);
|
||||
|
||||
var inverted = goog.vec.Mat4.invert(
|
||||
coordinateToPixelMatrix, frameState.pixelToCoordinateMatrix);
|
||||
goog.asserts.assert(inverted);
|
||||
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
@@ -127,6 +138,9 @@ ol.renderer.Map.prototype.disposeInternal = function() {
|
||||
goog.dispose(layerRenderer);
|
||||
});
|
||||
goog.array.forEach(this.mapListenerKeys_, goog.events.unlistenByKey);
|
||||
if (!goog.isNull(this.viewPropertyListenerKey_)) {
|
||||
goog.events.unlistenByKey(this.viewPropertyListenerKey_);
|
||||
}
|
||||
if (!goog.isNull(this.layersListenerKeys_)) {
|
||||
goog.array.forEach(this.layersListenerKeys_, goog.events.unlistenByKey);
|
||||
}
|
||||
@@ -134,37 +148,6 @@ ol.renderer.Map.prototype.disposeInternal = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {function(this: T, ol.layer.Layer, ol.renderer.Layer, number)} f
|
||||
* Function.
|
||||
* @param {T=} opt_obj Object.
|
||||
* @template T
|
||||
*/
|
||||
ol.renderer.Map.prototype.forEachReadyVisibleLayer = function(f, opt_obj) {
|
||||
var layers = this.map.getLayers();
|
||||
if (goog.isDef(layers)) {
|
||||
layers.forEach(function(layer, index) {
|
||||
if (layer.isReady() && layer.getVisible()) {
|
||||
var layerRenderer = this.getLayerRenderer(layer);
|
||||
f.call(opt_obj, layer, layerRenderer, index);
|
||||
}
|
||||
}, this);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Pixel} pixel Pixel.
|
||||
* @return {ol.Coordinate} Coordinate.
|
||||
*/
|
||||
ol.renderer.Map.prototype.getCoordinateFromPixel = function(pixel) {
|
||||
this.updateMatrices_();
|
||||
var vec3 = [pixel.x, pixel.y, 0];
|
||||
goog.vec.Mat4.multVec3(this.pixelToCoordinateMatrix_, vec3, vec3);
|
||||
return new ol.Coordinate(vec3[0], vec3[1]);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.layer.Layer} layer Layer.
|
||||
* @protected
|
||||
@@ -186,38 +169,18 @@ ol.renderer.Map.prototype.getMap = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Coordinate} coordinate Coordinate.
|
||||
* @return {ol.Pixel} Pixel.
|
||||
*/
|
||||
ol.renderer.Map.prototype.getPixelFromCoordinate = function(coordinate) {
|
||||
this.updateMatrices_();
|
||||
var vec3 = [coordinate.x, coordinate.y, 0];
|
||||
goog.vec.Mat4.multVec3(this.coordinateToPixelMatrix_, vec3, vec3);
|
||||
return new ol.Pixel(vec3[0], vec3[1]);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Handle background color changed.
|
||||
*/
|
||||
ol.renderer.Map.prototype.handleBackgroundColorChanged = goog.nullFunction;
|
||||
|
||||
|
||||
/**
|
||||
* @protected
|
||||
*/
|
||||
ol.renderer.Map.prototype.handleCenterChanged = function() {
|
||||
this.matricesDirty_ = true;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.CollectionEvent} collectionEvent Collection event.
|
||||
* @protected
|
||||
*/
|
||||
ol.renderer.Map.prototype.handleLayersAdd = function(collectionEvent) {
|
||||
var layer = /** @type {ol.layer.Layer} */ collectionEvent.elem;
|
||||
var layer = /** @type {ol.layer.Layer} */ (collectionEvent.elem);
|
||||
this.addLayer(layer);
|
||||
};
|
||||
|
||||
@@ -226,10 +189,7 @@ ol.renderer.Map.prototype.handleLayersAdd = function(collectionEvent) {
|
||||
* @protected
|
||||
*/
|
||||
ol.renderer.Map.prototype.handleLayersChanged = function() {
|
||||
var layerRenderers = goog.object.getValues(this.layerRenderers);
|
||||
goog.array.forEach(layerRenderers, function(layerRenderer) {
|
||||
this.removeLayerRenderer(layerRenderer);
|
||||
}, this);
|
||||
goog.disposeAll(goog.object.getValues(this.layerRenderers));
|
||||
this.layerRenderers = {};
|
||||
if (!goog.isNull(this.layersListenerKeys_)) {
|
||||
goog.array.forEach(this.layersListenerKeys_, goog.events.unlistenByKey);
|
||||
@@ -253,7 +213,7 @@ ol.renderer.Map.prototype.handleLayersChanged = function() {
|
||||
* @protected
|
||||
*/
|
||||
ol.renderer.Map.prototype.handleLayersRemove = function(collectionEvent) {
|
||||
var layer = /** @type {ol.layer.Layer} */ collectionEvent.elem;
|
||||
var layer = /** @type {ol.layer.Layer} */ (collectionEvent.elem);
|
||||
this.removeLayer(layer);
|
||||
};
|
||||
|
||||
@@ -261,16 +221,8 @@ ol.renderer.Map.prototype.handleLayersRemove = function(collectionEvent) {
|
||||
/**
|
||||
* @protected
|
||||
*/
|
||||
ol.renderer.Map.prototype.handleResolutionChanged = function() {
|
||||
this.matricesDirty_ = true;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @protected
|
||||
*/
|
||||
ol.renderer.Map.prototype.handleRotationChanged = function() {
|
||||
this.matricesDirty_ = true;
|
||||
ol.renderer.Map.prototype.handleViewPropertyChanged = function() {
|
||||
this.getMap().render();
|
||||
};
|
||||
|
||||
|
||||
@@ -278,7 +230,25 @@ ol.renderer.Map.prototype.handleRotationChanged = function() {
|
||||
* @protected
|
||||
*/
|
||||
ol.renderer.Map.prototype.handleSizeChanged = function() {
|
||||
this.matricesDirty_ = true;
|
||||
this.getMap().render();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @protected
|
||||
*/
|
||||
ol.renderer.Map.prototype.handleViewChanged = function() {
|
||||
if (!goog.isNull(this.viewPropertyListenerKey_)) {
|
||||
goog.events.unlistenByKey(this.viewPropertyListenerKey_);
|
||||
this.viewPropertyListenerKey_ = null;
|
||||
}
|
||||
var view = this.getMap().getView();
|
||||
if (goog.isDefAndNotNull(view)) {
|
||||
this.viewPropertyListenerKey_ = goog.events.listen(
|
||||
view, ol.ObjectEventType.CHANGED,
|
||||
this.handleViewPropertyChanged, false, this);
|
||||
}
|
||||
this.getMap().render();
|
||||
};
|
||||
|
||||
|
||||
@@ -310,9 +280,9 @@ ol.renderer.Map.prototype.removeLayerRenderer = function(layer) {
|
||||
|
||||
/**
|
||||
* Render.
|
||||
* @param {number} time Time.
|
||||
* @param {?ol.FrameState} frameState Frame state.
|
||||
*/
|
||||
ol.renderer.Map.prototype.renderFrame = goog.functions.FALSE;
|
||||
ol.renderer.Map.prototype.renderFrame = goog.nullFunction;
|
||||
|
||||
|
||||
/**
|
||||
@@ -325,44 +295,3 @@ ol.renderer.Map.prototype.setLayerRenderer = function(layer, layerRenderer) {
|
||||
goog.asserts.assert(!(key in this.layerRenderers));
|
||||
this.layerRenderers[key] = layerRenderer;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @private
|
||||
*/
|
||||
ol.renderer.Map.prototype.updateMatrices_ = function() {
|
||||
|
||||
if (this.matricesDirty_) {
|
||||
|
||||
var map = this.map;
|
||||
var center = /** @type {!ol.Coordinate} */ map.getCenter();
|
||||
var resolution = /** @type {number} */ map.getResolution();
|
||||
var rotation = map.getRotation();
|
||||
var size = /** @type {!ol.Size} */ map.getSize();
|
||||
|
||||
goog.vec.Mat4.makeIdentity(this.coordinateToPixelMatrix_);
|
||||
goog.vec.Mat4.translate(this.coordinateToPixelMatrix_,
|
||||
size.width / 2,
|
||||
size.height / 2,
|
||||
0);
|
||||
goog.vec.Mat4.scale(this.coordinateToPixelMatrix_,
|
||||
1 / resolution,
|
||||
-1 / resolution,
|
||||
1);
|
||||
if (this.canRotate() && goog.isDef(rotation)) {
|
||||
goog.vec.Mat4.rotateZ(this.coordinateToPixelMatrix_, -rotation);
|
||||
}
|
||||
goog.vec.Mat4.translate(this.coordinateToPixelMatrix_,
|
||||
-center.x,
|
||||
-center.y,
|
||||
0);
|
||||
|
||||
var inverted = goog.vec.Mat4.invert(
|
||||
this.coordinateToPixelMatrix_, this.pixelToCoordinateMatrix_);
|
||||
goog.asserts.assert(inverted);
|
||||
|
||||
this.matricesDirty_ = false;
|
||||
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
@@ -1,8 +1,13 @@
|
||||
// FIXME move colorMatrix_ elsewhere?
|
||||
|
||||
goog.provide('ol.renderer.webgl.Layer');
|
||||
|
||||
goog.require('goog.vec.Mat4');
|
||||
goog.require('ol.FrameState');
|
||||
goog.require('ol.layer.Layer');
|
||||
goog.require('ol.layer.LayerState');
|
||||
goog.require('ol.renderer.Layer');
|
||||
goog.require('ol.vec.Mat4');
|
||||
|
||||
|
||||
|
||||
@@ -13,7 +18,50 @@ goog.require('ol.renderer.Layer');
|
||||
* @param {ol.layer.Layer} layer Layer.
|
||||
*/
|
||||
ol.renderer.webgl.Layer = function(mapRenderer, layer) {
|
||||
|
||||
goog.base(this, mapRenderer, layer);
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {!goog.vec.Mat4.Float32}
|
||||
*/
|
||||
this.brightnessMatrix_ = goog.vec.Mat4.createFloat32();
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {!goog.vec.Mat4.Float32}
|
||||
*/
|
||||
this.contrastMatrix_ = goog.vec.Mat4.createFloat32();
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {!goog.vec.Mat4.Float32}
|
||||
*/
|
||||
this.hueMatrix_ = goog.vec.Mat4.createFloat32();
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {!goog.vec.Mat4.Float32}
|
||||
*/
|
||||
this.saturationMatrix_ = goog.vec.Mat4.createFloat32();
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {!goog.vec.Mat4.Float32}
|
||||
*/
|
||||
this.colorMatrix_ = goog.vec.Mat4.createFloat32();
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {boolean}
|
||||
*/
|
||||
this.colorMatrixDirty_ = true;
|
||||
|
||||
this.handleLayerBrightnessChange();
|
||||
this.handleLayerContrastChange();
|
||||
this.handleLayerHueChange();
|
||||
this.handleLayerSaturationChange();
|
||||
|
||||
};
|
||||
goog.inherits(ol.renderer.webgl.Layer, ol.renderer.Layer);
|
||||
|
||||
@@ -27,17 +75,28 @@ ol.renderer.webgl.Layer.prototype.dispatchChangeEvent = function() {
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
* @return {ol.renderer.Map} MapRenderer.
|
||||
* @return {!goog.vec.Mat4.Float32} Color matrix.
|
||||
*/
|
||||
ol.renderer.webgl.Layer.prototype.getMapRenderer = function() {
|
||||
return /** @type {ol.renderer.webgl.Map} */ goog.base(
|
||||
this, 'getMapRenderer');
|
||||
ol.renderer.webgl.Layer.prototype.getColorMatrix = function() {
|
||||
if (this.colorMatrixDirty_) {
|
||||
this.updateColorMatrix_();
|
||||
}
|
||||
return this.colorMatrix_;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {goog.vec.Mat4.AnyType} Matrix.
|
||||
* @inheritDoc
|
||||
* @return {ol.renderer.Map} MapRenderer.
|
||||
*/
|
||||
ol.renderer.webgl.Layer.prototype.getMapRenderer = function() {
|
||||
return /** @type {ol.renderer.webgl.Map} */ (goog.base(
|
||||
this, 'getMapRenderer'));
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {!goog.vec.Mat4.Number} Matrix.
|
||||
*/
|
||||
ol.renderer.webgl.Layer.prototype.getMatrix = goog.abstractMethod;
|
||||
|
||||
@@ -52,6 +111,9 @@ ol.renderer.webgl.Layer.prototype.getTexture = goog.abstractMethod;
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.webgl.Layer.prototype.handleLayerBrightnessChange = function() {
|
||||
var value = this.getLayer().getBrightness();
|
||||
ol.vec.Mat4.makeBrightness(this.brightnessMatrix_, value);
|
||||
this.colorMatrixDirty_ = true;
|
||||
this.dispatchChangeEvent();
|
||||
};
|
||||
|
||||
@@ -60,6 +122,9 @@ ol.renderer.webgl.Layer.prototype.handleLayerBrightnessChange = function() {
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.webgl.Layer.prototype.handleLayerContrastChange = function() {
|
||||
var value = this.getLayer().getContrast();
|
||||
ol.vec.Mat4.makeContrast(this.contrastMatrix_, value);
|
||||
this.colorMatrixDirty_ = true;
|
||||
this.dispatchChangeEvent();
|
||||
};
|
||||
|
||||
@@ -68,6 +133,9 @@ ol.renderer.webgl.Layer.prototype.handleLayerContrastChange = function() {
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.webgl.Layer.prototype.handleLayerHueChange = function() {
|
||||
var value = this.getLayer().getHue();
|
||||
ol.vec.Mat4.makeHue(this.hueMatrix_, value);
|
||||
this.colorMatrixDirty_ = true;
|
||||
this.dispatchChangeEvent();
|
||||
};
|
||||
|
||||
@@ -92,6 +160,9 @@ ol.renderer.webgl.Layer.prototype.handleLayerOpacityChange = function() {
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.webgl.Layer.prototype.handleLayerSaturationChange = function() {
|
||||
var saturation = this.getLayer().getSaturation();
|
||||
ol.vec.Mat4.makeSaturation(this.saturationMatrix_, saturation);
|
||||
this.colorMatrixDirty_ = true;
|
||||
this.dispatchChangeEvent();
|
||||
};
|
||||
|
||||
@@ -112,7 +183,21 @@ ol.renderer.webgl.Layer.prototype.handleWebGLContextLost = goog.nullFunction;
|
||||
|
||||
/**
|
||||
* Render.
|
||||
* @param {number} time Time.
|
||||
* @return {boolean} Request render frame.
|
||||
* @param {ol.FrameState} frameState Frame state.
|
||||
* @param {ol.layer.LayerState} layerState Layer state.
|
||||
*/
|
||||
ol.renderer.webgl.Layer.prototype.renderFrame = goog.abstractMethod;
|
||||
|
||||
|
||||
/**
|
||||
* @private
|
||||
*/
|
||||
ol.renderer.webgl.Layer.prototype.updateColorMatrix_ = function() {
|
||||
var colorMatrix = this.colorMatrix_;
|
||||
goog.vec.Mat4.makeIdentity(colorMatrix);
|
||||
goog.vec.Mat4.multMat(colorMatrix, this.contrastMatrix_, colorMatrix);
|
||||
goog.vec.Mat4.multMat(colorMatrix, this.brightnessMatrix_, colorMatrix);
|
||||
goog.vec.Mat4.multMat(colorMatrix, this.saturationMatrix_, colorMatrix);
|
||||
goog.vec.Mat4.multMat(colorMatrix, this.hueMatrix_, colorMatrix);
|
||||
this.colorMatrixDirty_ = false;
|
||||
};
|
||||
|
||||
@@ -1,7 +1,5 @@
|
||||
// FIXME clear textureCache
|
||||
// FIXME defer texture loads until after render when animating
|
||||
// FIXME generational tile texture garbage collector newFrame/get
|
||||
// FIXME defer cleanup until post-render
|
||||
// FIXME check against gl.getParameter(webgl.MAX_TEXTURE_SIZE)
|
||||
|
||||
goog.provide('ol.renderer.webgl.Map');
|
||||
@@ -14,10 +12,9 @@ goog.require('goog.dom.TagName');
|
||||
goog.require('goog.events');
|
||||
goog.require('goog.events.Event');
|
||||
goog.require('goog.events.EventType');
|
||||
goog.require('goog.functions');
|
||||
goog.require('goog.style');
|
||||
goog.require('goog.vec.Mat4');
|
||||
goog.require('goog.webgl');
|
||||
goog.require('ol.Tile');
|
||||
goog.require('ol.layer.Layer');
|
||||
goog.require('ol.layer.TileLayer');
|
||||
goog.require('ol.renderer.webgl.FragmentShader');
|
||||
@@ -119,6 +116,12 @@ ol.renderer.webgl.Map = function(container, map) {
|
||||
this.canvas_.className = 'ol-unselectable';
|
||||
goog.dom.insertChildAt(container, this.canvas_, 0);
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {boolean}
|
||||
*/
|
||||
this.renderedVisible_ = true;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.Size}
|
||||
@@ -143,12 +146,6 @@ ol.renderer.webgl.Map = function(container, map) {
|
||||
goog.events.listen(this.canvas_, ol.webgl.WebGLContextEventType.RESTORED,
|
||||
this.handleWebGLContextResourced, false, this);
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.Color}
|
||||
*/
|
||||
this.clearColor_ = new ol.Color(1, 1, 1, 1);
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {{aPosition: number,
|
||||
@@ -220,15 +217,15 @@ ol.renderer.webgl.Map.prototype.addLayer = function(layer) {
|
||||
|
||||
|
||||
/**
|
||||
* @param {Image} image Image.
|
||||
* @param {ol.Tile} tile Tile.
|
||||
* @param {number} magFilter Mag filter.
|
||||
* @param {number} minFilter Min filter.
|
||||
*/
|
||||
ol.renderer.webgl.Map.prototype.bindImageTexture =
|
||||
function(image, magFilter, minFilter) {
|
||||
ol.renderer.webgl.Map.prototype.bindTileTexture =
|
||||
function(tile, magFilter, minFilter) {
|
||||
var gl = this.getGL();
|
||||
var imageKey = image.src;
|
||||
var textureCacheEntry = this.textureCache_[imageKey];
|
||||
var tileKey = tile.getKey();
|
||||
var textureCacheEntry = this.textureCache_[tileKey];
|
||||
if (goog.isDef(textureCacheEntry)) {
|
||||
gl.bindTexture(goog.webgl.TEXTURE_2D, textureCacheEntry.texture);
|
||||
if (textureCacheEntry.magFilter != magFilter) {
|
||||
@@ -245,7 +242,7 @@ ol.renderer.webgl.Map.prototype.bindImageTexture =
|
||||
var texture = gl.createTexture();
|
||||
gl.bindTexture(goog.webgl.TEXTURE_2D, texture);
|
||||
gl.texImage2D(goog.webgl.TEXTURE_2D, 0, goog.webgl.RGBA, goog.webgl.RGBA,
|
||||
goog.webgl.UNSIGNED_BYTE, image);
|
||||
goog.webgl.UNSIGNED_BYTE, tile.getImage());
|
||||
gl.texParameteri(
|
||||
goog.webgl.TEXTURE_2D, goog.webgl.TEXTURE_MAG_FILTER, magFilter);
|
||||
gl.texParameteri(
|
||||
@@ -254,7 +251,7 @@ ol.renderer.webgl.Map.prototype.bindImageTexture =
|
||||
goog.webgl.CLAMP_TO_EDGE);
|
||||
gl.texParameteri(goog.webgl.TEXTURE_2D, goog.webgl.TEXTURE_WRAP_T,
|
||||
goog.webgl.CLAMP_TO_EDGE);
|
||||
this.textureCache_[imageKey] = {
|
||||
this.textureCache_[tileKey] = {
|
||||
texture: texture,
|
||||
magFilter: magFilter,
|
||||
minFilter: minFilter
|
||||
@@ -263,75 +260,10 @@ ol.renderer.webgl.Map.prototype.bindImageTexture =
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.webgl.Map.prototype.canRotate = goog.functions.TRUE;
|
||||
|
||||
|
||||
/**
|
||||
* @param {number} value Hue value.
|
||||
* @return {!goog.vec.Mat4.Float32} Matrix.
|
||||
*/
|
||||
ol.renderer.webgl.Map.prototype.createHueRotateMatrix = function(value) {
|
||||
var cosHue = Math.cos(value);
|
||||
var sinHue = Math.sin(value);
|
||||
var v00 = 0.213 + cosHue * 0.787 - sinHue * 0.213;
|
||||
var v01 = 0.715 - cosHue * 0.715 - sinHue * 0.715;
|
||||
var v02 = 0.072 - cosHue * 0.072 + sinHue * 0.928;
|
||||
var v03 = 0;
|
||||
var v10 = 0.213 - cosHue * 0.213 + sinHue * 0.143;
|
||||
var v11 = 0.715 + cosHue * 0.285 + sinHue * 0.140;
|
||||
var v12 = 0.072 - cosHue * 0.072 - sinHue * 0.283;
|
||||
var v13 = 0;
|
||||
var v20 = 0.213 - cosHue * 0.213 - sinHue * 0.787;
|
||||
var v21 = 0.715 - cosHue * 0.715 + sinHue * 0.715;
|
||||
var v22 = 0.072 + cosHue * 0.928 + sinHue * 0.072;
|
||||
var v23 = 0;
|
||||
var v30 = 0;
|
||||
var v31 = 0;
|
||||
var v32 = 0;
|
||||
var v33 = 1;
|
||||
var matrix = goog.vec.Mat4.createFloat32();
|
||||
goog.vec.Mat4.setFromValues(matrix,
|
||||
v00, v10, v20, v30,
|
||||
v01, v11, v21, v31,
|
||||
v02, v12, v22, v32,
|
||||
v03, v13, v23, v33);
|
||||
return matrix;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {number} value Brightness value.
|
||||
* @return {!goog.vec.Mat4.Float32} Matrix.
|
||||
*/
|
||||
ol.renderer.webgl.Map.prototype.createBrightnessMatrix = function(value) {
|
||||
var matrix = goog.vec.Mat4.createFloat32Identity();
|
||||
goog.vec.Mat4.setColumnValues(matrix, 3, value, value, value, 1);
|
||||
return matrix;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {number} value Contrast value.
|
||||
* @return {!goog.vec.Mat4.Float32} Matrix.
|
||||
*/
|
||||
ol.renderer.webgl.Map.prototype.createContrastMatrix = function(value) {
|
||||
var matrix = goog.vec.Mat4.createFloat32();
|
||||
goog.vec.Mat4.setDiagonalValues(matrix, value, value, value, 1);
|
||||
var translateValue = (-0.5 * value + 0.5);
|
||||
goog.vec.Mat4.setColumnValues(matrix, 3,
|
||||
translateValue, translateValue, translateValue, 1);
|
||||
return matrix;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.webgl.Map.prototype.createLayerRenderer = function(layer) {
|
||||
var gl = this.getGL();
|
||||
if (layer instanceof ol.layer.TileLayer) {
|
||||
return new ol.renderer.webgl.TileLayer(this, layer);
|
||||
} else {
|
||||
@@ -341,38 +273,6 @@ ol.renderer.webgl.Map.prototype.createLayerRenderer = function(layer) {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {number} value Saturation value.
|
||||
* @return {!goog.vec.Mat4.Float32} Matrix.
|
||||
*/
|
||||
ol.renderer.webgl.Map.prototype.createSaturateMatrix = function(value) {
|
||||
var v00 = 0.213 + 0.787 * value;
|
||||
var v01 = 0.715 - 0.715 * value;
|
||||
var v02 = 0.072 - 0.072 * value;
|
||||
var v03 = 0;
|
||||
var v10 = 0.213 - 0.213 * value;
|
||||
var v11 = 0.715 + 0.285 * value;
|
||||
var v12 = 0.072 - 0.072 * value;
|
||||
var v13 = 0;
|
||||
var v20 = 0.213 - 0.213 * value;
|
||||
var v21 = 0.715 - 0.715 * value;
|
||||
var v22 = 0.072 + 0.928 * value;
|
||||
var v23 = 0;
|
||||
var v30 = 0;
|
||||
var v31 = 0;
|
||||
var v32 = 0;
|
||||
var v33 = 1;
|
||||
var matrix = goog.vec.Mat4.createFloat32();
|
||||
goog.vec.Mat4.setFromValues(matrix,
|
||||
v00, v10, v20, v30,
|
||||
v01, v11, v21, v31,
|
||||
v02, v12, v22, v32,
|
||||
v03, v13, v23, v33);
|
||||
return matrix;
|
||||
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
@@ -464,21 +364,6 @@ ol.renderer.webgl.Map.prototype.getShader = function(shaderObject) {
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.webgl.Map.prototype.handleBackgroundColorChanged = function() {
|
||||
var backgroundColor = this.getMap().getBackgroundColor();
|
||||
this.clearColor_ = new ol.Color(
|
||||
backgroundColor.r / 255,
|
||||
backgroundColor.g / 255,
|
||||
backgroundColor.b / 255,
|
||||
backgroundColor.a / 255);
|
||||
this.getMap().render();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.webgl.Map.prototype.handleCenterChanged = function() {
|
||||
goog.base(this, 'handleCenterChanged');
|
||||
this.getMap().render();
|
||||
};
|
||||
|
||||
@@ -492,33 +377,6 @@ ol.renderer.webgl.Map.prototype.handleLayerRendererChange = function(event) {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.webgl.Map.prototype.handleResolutionChanged = function() {
|
||||
goog.base(this, 'handleResolutionChanged');
|
||||
this.getMap().render();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.webgl.Map.prototype.handleRotationChanged = function() {
|
||||
goog.base(this, 'handleRotationChanged');
|
||||
this.getMap().render();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.webgl.Map.prototype.handleSizeChanged = function() {
|
||||
goog.base(this, 'handleSizeChanged');
|
||||
this.getMap().render();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {goog.events.Event} event Event.
|
||||
* @protected
|
||||
@@ -565,11 +423,11 @@ ol.renderer.webgl.Map.prototype.initializeGL_ = function() {
|
||||
|
||||
|
||||
/**
|
||||
* @param {Image} image Image.
|
||||
* @return {boolean} Is image texture loaded.
|
||||
* @param {ol.Tile} tile Tile.
|
||||
* @return {boolean} Is tile texture loaded.
|
||||
*/
|
||||
ol.renderer.webgl.Map.prototype.isImageTextureLoaded = function(image) {
|
||||
return image.src in this.textureCache_;
|
||||
ol.renderer.webgl.Map.prototype.isTileTextureLoaded = function(tile) {
|
||||
return tile.getKey() in this.textureCache_;
|
||||
};
|
||||
|
||||
|
||||
@@ -601,40 +459,38 @@ ol.renderer.webgl.Map.prototype.removeLayerRenderer = function(layer) {
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.webgl.Map.prototype.renderFrame = function(time) {
|
||||
ol.renderer.webgl.Map.prototype.renderFrame = function(frameState) {
|
||||
|
||||
if (!this.getMap().isDef()) {
|
||||
return;
|
||||
var gl = this.getGL();
|
||||
|
||||
if (goog.isNull(frameState)) {
|
||||
if (this.renderedVisible_) {
|
||||
goog.style.showElement(this.canvas_, false);
|
||||
this.renderedVisible_ = false;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
var requestRenderFrame = false;
|
||||
|
||||
this.forEachReadyVisibleLayer(function(layer, layerRenderer) {
|
||||
if (layerRenderer.renderFrame(time)) {
|
||||
requestRenderFrame = true;
|
||||
goog.array.forEach(frameState.layersArray, function(layer) {
|
||||
var layerState = frameState.layerStates[goog.getUid(layer)];
|
||||
if (!layerState.visible || !layerState.ready) {
|
||||
return;
|
||||
}
|
||||
});
|
||||
var layerRenderer = this.getLayerRenderer(layer);
|
||||
layerRenderer.renderFrame(frameState, layerState);
|
||||
}, this);
|
||||
|
||||
var size = /** @type {ol.Size} */ this.getMap().getSize();
|
||||
var size = frameState.size;
|
||||
if (!this.canvasSize_.equals(size)) {
|
||||
this.canvas_.width = size.width;
|
||||
this.canvas_.height = size.height;
|
||||
this.canvasSize_ = size;
|
||||
}
|
||||
|
||||
var animate = false;
|
||||
this.forEachReadyVisibleLayer(function(layer, layerRenderer) {
|
||||
if (layerRenderer.renderFrame(time)) {
|
||||
animate = true;
|
||||
}
|
||||
});
|
||||
|
||||
var gl = this.getGL();
|
||||
|
||||
gl.bindFramebuffer(goog.webgl.FRAMEBUFFER, null);
|
||||
|
||||
gl.clearColor(this.clearColor_.r, this.clearColor_.g, this.clearColor_.b,
|
||||
this.clearColor_.a);
|
||||
var clearColor = frameState.backgroundColor;
|
||||
gl.clearColor(clearColor.r, clearColor.g, clearColor.b, clearColor.a);
|
||||
gl.clear(goog.webgl.COLOR_BUFFER_BIT);
|
||||
gl.enable(goog.webgl.BLEND);
|
||||
gl.viewport(0, 0, size.width, size.height);
|
||||
@@ -674,28 +530,28 @@ ol.renderer.webgl.Map.prototype.renderFrame = function(time) {
|
||||
this.locations_.aTexCoord, 2, goog.webgl.FLOAT, false, 16, 8);
|
||||
gl.uniform1i(this.locations_.uTexture, 0);
|
||||
|
||||
this.forEachReadyVisibleLayer(function(layer, layerRenderer) {
|
||||
goog.array.forEach(frameState.layersArray, function(layer) {
|
||||
var layerState = frameState.layerStates[goog.getUid(layer)];
|
||||
if (!layerState.visible || !layerState.ready) {
|
||||
return;
|
||||
}
|
||||
var layerRenderer = this.getLayerRenderer(layer);
|
||||
gl.uniformMatrix4fv(
|
||||
this.locations_.uMatrix, false, layerRenderer.getMatrix());
|
||||
var hueRotateMatrix = this.createHueRotateMatrix(layer.getHue());
|
||||
var saturateMatrix = this.createSaturateMatrix(layer.getSaturation());
|
||||
var brightnessMatrix = this.createBrightnessMatrix(layer.getBrightness());
|
||||
var contrastMatrix = this.createContrastMatrix(layer.getContrast());
|
||||
var colorMatrix = goog.vec.Mat4.createFloat32Identity();
|
||||
goog.vec.Mat4.multMat(colorMatrix, contrastMatrix, colorMatrix);
|
||||
goog.vec.Mat4.multMat(colorMatrix, brightnessMatrix, colorMatrix);
|
||||
goog.vec.Mat4.multMat(colorMatrix, saturateMatrix, colorMatrix);
|
||||
goog.vec.Mat4.multMat(colorMatrix, hueRotateMatrix, colorMatrix);
|
||||
gl.uniformMatrix4fv(this.locations_.uColorMatrix, false, colorMatrix);
|
||||
gl.uniformMatrix4fv(
|
||||
this.locations_.uColorMatrix, false, layerRenderer.getColorMatrix());
|
||||
gl.uniform1f(this.locations_.uOpacity, layer.getOpacity());
|
||||
gl.bindTexture(goog.webgl.TEXTURE_2D, layerRenderer.getTexture());
|
||||
gl.drawArrays(goog.webgl.TRIANGLE_STRIP, 0, 4);
|
||||
}, this);
|
||||
|
||||
if (requestRenderFrame) {
|
||||
this.getMap().requestRenderFrame();
|
||||
if (!this.renderedVisible_) {
|
||||
goog.style.showElement(this.canvas_, true);
|
||||
this.renderedVisible_ = true;
|
||||
}
|
||||
|
||||
this.calculateMatrices2D(frameState);
|
||||
|
||||
};
|
||||
|
||||
|
||||
|
||||
@@ -3,12 +3,6 @@ goog.provide('ol.renderer.webgl');
|
||||
goog.require('ol.webgl');
|
||||
|
||||
|
||||
/**
|
||||
* @define {boolean} Free resources immediately.
|
||||
*/
|
||||
ol.renderer.webgl.FREE_RESOURCES_IMMEDIATELY = false;
|
||||
|
||||
|
||||
/**
|
||||
* @return {boolean} Is supported.
|
||||
*/
|
||||
|
||||
@@ -1,7 +1,5 @@
|
||||
// FIXME large resolutions lead to too large framebuffers :-(
|
||||
// FIXME animated shaders! check in redraw
|
||||
// FIXME throttle texture uploads
|
||||
// FIXME prioritize texture uploads
|
||||
|
||||
goog.provide('ol.renderer.webgl.TileLayer');
|
||||
goog.provide('ol.renderer.webgl.tilelayerrenderer');
|
||||
@@ -10,13 +8,14 @@ goog.provide('ol.renderer.webgl.tilelayerrenderer.shader.Vertex');
|
||||
|
||||
goog.require('goog.array');
|
||||
goog.require('goog.asserts');
|
||||
goog.require('goog.debug.Logger');
|
||||
goog.require('goog.events.EventType');
|
||||
goog.require('goog.object');
|
||||
goog.require('goog.structs.PriorityQueue');
|
||||
goog.require('goog.vec.Mat4');
|
||||
goog.require('goog.vec.Vec4');
|
||||
goog.require('goog.webgl');
|
||||
goog.require('ol.Coordinate');
|
||||
goog.require('ol.FrameState');
|
||||
goog.require('ol.Size');
|
||||
goog.require('ol.TileState');
|
||||
goog.require('ol.layer.TileLayer');
|
||||
@@ -88,14 +87,6 @@ ol.renderer.webgl.TileLayer = function(mapRenderer, tileLayer) {
|
||||
|
||||
goog.base(this, mapRenderer, tileLayer);
|
||||
|
||||
if (goog.DEBUG) {
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
this.logger = goog.debug.Logger.getLogger(
|
||||
'ol.renderer.webgl.tilelayerrenderer.' + goog.getUid(this));
|
||||
}
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.renderer.webgl.FragmentShader}
|
||||
@@ -145,7 +136,7 @@ ol.renderer.webgl.TileLayer = function(mapRenderer, tileLayer) {
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {goog.vec.Mat4.AnyType}
|
||||
* @type {!goog.vec.Mat4.Number}
|
||||
*/
|
||||
this.matrix_ = goog.vec.Mat4.createNumber();
|
||||
|
||||
@@ -166,11 +157,12 @@ goog.inherits(ol.renderer.webgl.TileLayer, ol.renderer.webgl.Layer);
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.FrameState} frameState Frame state.
|
||||
* @param {number} framebufferDimension Framebuffer dimension.
|
||||
* @private
|
||||
*/
|
||||
ol.renderer.webgl.TileLayer.prototype.bindFramebuffer_ =
|
||||
function(framebufferDimension) {
|
||||
function(frameState, framebufferDimension) {
|
||||
|
||||
var mapRenderer = this.getMapRenderer();
|
||||
var gl = mapRenderer.getGL();
|
||||
@@ -178,33 +170,14 @@ ol.renderer.webgl.TileLayer.prototype.bindFramebuffer_ =
|
||||
if (!goog.isDef(this.framebufferDimension_) ||
|
||||
this.framebufferDimension_ != framebufferDimension) {
|
||||
|
||||
if (goog.DEBUG) {
|
||||
this.logger.info('re-sizing framebuffer');
|
||||
}
|
||||
|
||||
if (ol.renderer.webgl.FREE_RESOURCES_IMMEDIATELY) {
|
||||
if (goog.DEBUG) {
|
||||
this.logger.info('freeing WebGL resources');
|
||||
}
|
||||
if (!gl.isContextLost()) {
|
||||
gl.deleteFramebuffer(this.framebuffer_);
|
||||
gl.deleteTexture(this.texture_);
|
||||
}
|
||||
} else {
|
||||
var map = this.getMap();
|
||||
goog.events.listenOnce(
|
||||
map,
|
||||
ol.MapEventType.POSTRENDER,
|
||||
goog.partial(function(gl, framebuffer, texture) {
|
||||
if (goog.DEBUG) {
|
||||
this.logger.info('freeing WebGL resources on postrender');
|
||||
}
|
||||
if (!gl.isContextLost()) {
|
||||
gl.deleteFramebuffer(framebuffer);
|
||||
gl.deleteTexture(texture);
|
||||
}
|
||||
}, gl, this.framebuffer_, this.texture_));
|
||||
}
|
||||
var map = this.getMap();
|
||||
frameState.postRenderFunctions.push(
|
||||
goog.partial(function(gl, framebuffer, texture) {
|
||||
if (!gl.isContextLost()) {
|
||||
gl.deleteFramebuffer(framebuffer);
|
||||
gl.deleteTexture(texture);
|
||||
}
|
||||
}, gl, this.framebuffer_, this.texture_));
|
||||
|
||||
var texture = gl.createTexture();
|
||||
gl.bindTexture(goog.webgl.TEXTURE_2D, texture);
|
||||
@@ -247,15 +220,6 @@ ol.renderer.webgl.TileLayer.prototype.disposeInternal = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.layer.TileLayer} Layer.
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.webgl.TileLayer.prototype.getLayer = function() {
|
||||
return /** @type {ol.layer.TileLayer} */ goog.base(this, 'getLayer');
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
@@ -272,6 +236,14 @@ ol.renderer.webgl.TileLayer.prototype.getTexture = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {ol.layer.TileLayer} Tile layer.
|
||||
*/
|
||||
ol.renderer.webgl.TileLayer.prototype.getTileLayer = function() {
|
||||
return /** @type {ol.layer.TileLayer} */ (this.getLayer());
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
@@ -287,28 +259,22 @@ ol.renderer.webgl.TileLayer.prototype.handleWebGLContextLost = function() {
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.renderer.webgl.TileLayer.prototype.renderFrame = function(time) {
|
||||
|
||||
var requestRenderFrame = false;
|
||||
ol.renderer.webgl.TileLayer.prototype.renderFrame =
|
||||
function(frameState, layerState) {
|
||||
|
||||
var mapRenderer = this.getMapRenderer();
|
||||
var map = this.getMap();
|
||||
var gl = mapRenderer.getGL();
|
||||
|
||||
goog.asserts.assert(map.isDef());
|
||||
var mapCenter = map.getCenter();
|
||||
var mapExtent = map.getExtent();
|
||||
var mapResolution = /** @type {number} */ map.getResolution();
|
||||
var mapRotatedExtent = map.getRotatedExtent();
|
||||
var mapRotation = map.getRotation();
|
||||
var view2DState = frameState.view2DState;
|
||||
var center = view2DState.center;
|
||||
|
||||
var tileLayer = this.getLayer();
|
||||
var tileLayer = this.getTileLayer();
|
||||
var tileSource = tileLayer.getTileSource();
|
||||
var tileGrid = tileSource.getTileGrid();
|
||||
var z = tileGrid.getZForResolution(mapResolution);
|
||||
var z = tileGrid.getZForResolution(view2DState.resolution);
|
||||
var tileResolution = tileGrid.getResolution(z);
|
||||
var tileRange = tileGrid.getTileRangeForExtentAndResolution(
|
||||
mapRotatedExtent, tileResolution);
|
||||
frameState.extent, tileResolution);
|
||||
|
||||
var framebufferExtent;
|
||||
|
||||
@@ -337,7 +303,7 @@ ol.renderer.webgl.TileLayer.prototype.renderFrame = function(time) {
|
||||
minX + framebufferExtentSize.width,
|
||||
minY + framebufferExtentSize.height);
|
||||
|
||||
this.bindFramebuffer_(framebufferDimension);
|
||||
this.bindFramebuffer_(frameState, framebufferDimension);
|
||||
gl.viewport(0, 0, framebufferDimension, framebufferDimension);
|
||||
|
||||
gl.clearColor(0, 0, 0, 0);
|
||||
@@ -382,65 +348,73 @@ ol.renderer.webgl.TileLayer.prototype.renderFrame = function(time) {
|
||||
* @type {Object.<number, Object.<string, ol.Tile>>}
|
||||
*/
|
||||
var tilesToDrawByZ = {};
|
||||
tilesToDrawByZ[z] = {};
|
||||
|
||||
/**
|
||||
* @type {Array.<Image>}
|
||||
*/
|
||||
var imagesToLoad = [];
|
||||
var findInterimTiles = function(z, tileRange) {
|
||||
// FIXME this could be more efficient about filling partial holes
|
||||
var fullyCovered = true;
|
||||
var tile, tileCoord, tileCoordKey, x, y;
|
||||
for (x = tileRange.minX; x <= tileRange.maxX; ++x) {
|
||||
for (y = tileRange.minY; y <= tileRange.maxY; ++y) {
|
||||
tileCoord = new ol.TileCoord(z, x, y);
|
||||
tileCoordKey = tileCoord.toString();
|
||||
if (tilesToDrawByZ[z] && tilesToDrawByZ[z][tileCoordKey]) {
|
||||
return;
|
||||
}
|
||||
tile = tileSource.getTile(tileCoord);
|
||||
if (!goog.isNull(tile) &&
|
||||
tile.getState() == ol.TileState.LOADED &&
|
||||
mapRenderer.isTileTextureLoaded(tile)) {
|
||||
if (!tilesToDrawByZ[z]) {
|
||||
tilesToDrawByZ[z] = {};
|
||||
}
|
||||
tilesToDrawByZ[z][tileCoordKey] = tile;
|
||||
} else {
|
||||
fullyCovered = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
return fullyCovered;
|
||||
};
|
||||
|
||||
var tilesToLoad = new goog.structs.PriorityQueue();
|
||||
|
||||
var allTilesLoaded = true;
|
||||
var deltaX, deltaY, priority, tile, tileCenter, tileCoord, tileState, x, y;
|
||||
for (x = tileRange.minX; x <= tileRange.maxX; ++x) {
|
||||
for (y = tileRange.minY; y <= tileRange.maxY; ++y) {
|
||||
|
||||
tilesToDrawByZ[z] = {};
|
||||
tileRange.forEachTileCoord(z, function(tileCoord) {
|
||||
|
||||
var tile = tileSource.getTile(tileCoord);
|
||||
|
||||
if (goog.isNull(tile)) {
|
||||
return;
|
||||
}
|
||||
|
||||
var tileState = tile.getState();
|
||||
if (tileState == ol.TileState.IDLE) {
|
||||
tile.load();
|
||||
} else if (tileState == ol.TileState.LOADED) {
|
||||
var image = tile.getImage();
|
||||
if (mapRenderer.isImageTextureLoaded(image)) {
|
||||
tilesToDrawByZ[z][tileCoord.toString()] = tile;
|
||||
return;
|
||||
} else {
|
||||
imagesToLoad.push(image);
|
||||
tileCoord = new ol.TileCoord(z, x, y);
|
||||
tile = tileSource.getTile(tileCoord);
|
||||
if (goog.isNull(tile)) {
|
||||
continue;
|
||||
}
|
||||
} else if (tileState == ol.TileState.ERROR) {
|
||||
return;
|
||||
|
||||
tileState = tile.getState();
|
||||
if (tileState == ol.TileState.IDLE) {
|
||||
tileCenter = tileGrid.getTileCoordCenter(tileCoord);
|
||||
frameState.tileQueue.enqueue(tile, tileCenter, tileResolution);
|
||||
} else if (tileState == ol.TileState.LOADED) {
|
||||
if (mapRenderer.isTileTextureLoaded(tile)) {
|
||||
tilesToDrawByZ[z][tileCoord.toString()] = tile;
|
||||
continue;
|
||||
} else {
|
||||
tileCenter = tileGrid.getTileCoordCenter(tileCoord);
|
||||
deltaX = tileCenter.x - center.x;
|
||||
deltaY = tileCenter.y - center.y;
|
||||
priority = Math.sqrt(deltaX * deltaX + deltaY * deltaY);
|
||||
tilesToLoad.enqueue(priority, tile);
|
||||
}
|
||||
} else if (tileState == ol.TileState.ERROR) {
|
||||
continue;
|
||||
}
|
||||
|
||||
allTilesLoaded = false;
|
||||
tileGrid.forEachTileCoordParentTileRange(tileCoord, findInterimTiles);
|
||||
|
||||
}
|
||||
|
||||
allTilesLoaded = false;
|
||||
|
||||
// FIXME this could be more efficient about filling partial holes
|
||||
tileGrid.forEachTileCoordParentTileRange(
|
||||
tileCoord,
|
||||
function(z, tileRange) {
|
||||
var fullyCovered = true;
|
||||
tileRange.forEachTileCoord(z, function(tileCoord) {
|
||||
var tileCoordKey = tileCoord.toString();
|
||||
if (tilesToDrawByZ[z] && tilesToDrawByZ[z][tileCoordKey]) {
|
||||
return;
|
||||
}
|
||||
var tile = tileSource.getTile(tileCoord);
|
||||
if (!goog.isNull(tile) &&
|
||||
tile.getState() == ol.TileState.LOADED) {
|
||||
if (!tilesToDrawByZ[z]) {
|
||||
tilesToDrawByZ[z] = {};
|
||||
}
|
||||
tilesToDrawByZ[z][tileCoordKey] = tile;
|
||||
} else {
|
||||
fullyCovered = false;
|
||||
}
|
||||
});
|
||||
return fullyCovered;
|
||||
});
|
||||
|
||||
}, this);
|
||||
}
|
||||
|
||||
/** @type {Array.<number>} */
|
||||
var zs = goog.array.map(goog.object.getKeys(tilesToDrawByZ), Number);
|
||||
@@ -457,29 +431,22 @@ ol.renderer.webgl.TileLayer.prototype.renderFrame = function(time) {
|
||||
framebufferExtentSize.height - 1;
|
||||
goog.vec.Vec4.setFromValues(uTileOffset, sx, sy, tx, ty);
|
||||
gl.uniform4fv(this.locations_.uTileOffset, uTileOffset);
|
||||
mapRenderer.bindImageTexture(
|
||||
tile.getImage(), goog.webgl.LINEAR, goog.webgl.LINEAR);
|
||||
mapRenderer.bindTileTexture(tile, goog.webgl.LINEAR, goog.webgl.LINEAR);
|
||||
gl.drawArrays(goog.webgl.TRIANGLE_STRIP, 0, 4);
|
||||
}, this);
|
||||
}, this);
|
||||
|
||||
if (!goog.array.isEmpty(imagesToLoad)) {
|
||||
goog.events.listenOnce(
|
||||
map,
|
||||
ol.MapEventType.POSTRENDER,
|
||||
goog.partial(function(mapRenderer, imagesToLoad) {
|
||||
if (goog.DEBUG) {
|
||||
this.logger.info(
|
||||
'uploading ' + imagesToLoad.length + ' textures');
|
||||
if (!tilesToLoad.isEmpty()) {
|
||||
frameState.postRenderFunctions.push(
|
||||
goog.partial(function(mapRenderer, tilesToLoad) {
|
||||
var i, tile;
|
||||
// FIXME determine a suitable number of textures to upload per frame
|
||||
for (i = 0; !tilesToLoad.isEmpty() && i < 4; ++i) {
|
||||
tile = /** @type {ol.Tile} */ (tilesToLoad.remove());
|
||||
mapRenderer.bindTileTexture(
|
||||
tile, goog.webgl.LINEAR, goog.webgl.LINEAR);
|
||||
}
|
||||
goog.array.forEach(imagesToLoad, function(image) {
|
||||
mapRenderer.bindImageTexture(
|
||||
image, goog.webgl.LINEAR, goog.webgl.LINEAR);
|
||||
});
|
||||
if (goog.DEBUG) {
|
||||
this.logger.info('uploaded textures');
|
||||
}
|
||||
}, mapRenderer, imagesToLoad));
|
||||
}, mapRenderer, tilesToLoad));
|
||||
}
|
||||
|
||||
if (allTilesLoaded) {
|
||||
@@ -488,25 +455,23 @@ ol.renderer.webgl.TileLayer.prototype.renderFrame = function(time) {
|
||||
} else {
|
||||
this.renderedTileRange_ = null;
|
||||
this.renderedFramebufferExtent_ = null;
|
||||
requestRenderFrame = true;
|
||||
frameState.animate = true;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
goog.vec.Mat4.makeIdentity(this.matrix_);
|
||||
goog.vec.Mat4.translate(this.matrix_,
|
||||
(mapCenter.x - framebufferExtent.minX) /
|
||||
(view2DState.center.x - framebufferExtent.minX) /
|
||||
(framebufferExtent.maxX - framebufferExtent.minX),
|
||||
(mapCenter.y - framebufferExtent.minY) /
|
||||
(view2DState.center.y - framebufferExtent.minY) /
|
||||
(framebufferExtent.maxY - framebufferExtent.minY),
|
||||
0);
|
||||
if (goog.isDef(mapRotation)) {
|
||||
goog.vec.Mat4.rotateZ(this.matrix_, mapRotation);
|
||||
}
|
||||
goog.vec.Mat4.rotateZ(this.matrix_, view2DState.rotation);
|
||||
goog.vec.Mat4.scale(this.matrix_,
|
||||
(mapExtent.maxX - mapExtent.minX) /
|
||||
frameState.size.width * view2DState.resolution /
|
||||
(framebufferExtent.maxX - framebufferExtent.minX),
|
||||
(mapExtent.maxY - mapExtent.minY) /
|
||||
frameState.size.height * view2DState.resolution /
|
||||
(framebufferExtent.maxY - framebufferExtent.minY),
|
||||
1);
|
||||
goog.vec.Mat4.translate(this.matrix_,
|
||||
@@ -514,6 +479,4 @@ ol.renderer.webgl.TileLayer.prototype.renderFrame = function(time) {
|
||||
-0.5,
|
||||
0);
|
||||
|
||||
return requestRenderFrame;
|
||||
|
||||
};
|
||||
|
||||
@@ -6,7 +6,7 @@ goog.require('goog.events');
|
||||
goog.require('goog.events.EventType');
|
||||
goog.require('goog.net.Jsonp');
|
||||
goog.require('ol.TileCoverageArea');
|
||||
goog.require('ol.source.TileSource');
|
||||
goog.require('ol.source.ImageTileSource');
|
||||
goog.require('ol.tilegrid.XYZ');
|
||||
|
||||
|
||||
@@ -25,7 +25,7 @@ ol.BingMapsStyle = {
|
||||
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.source.TileSource}
|
||||
* @extends {ol.source.ImageTileSource}
|
||||
* @param {ol.source.BingMapsOptions} bingMapsOptions Bing Maps options.
|
||||
*/
|
||||
ol.source.BingMaps = function(bingMapsOptions) {
|
||||
@@ -57,7 +57,7 @@ ol.source.BingMaps = function(bingMapsOptions) {
|
||||
}, goog.bind(this.handleImageryMetadataResponse, this));
|
||||
|
||||
};
|
||||
goog.inherits(ol.source.BingMaps, ol.source.TileSource);
|
||||
goog.inherits(ol.source.BingMaps, ol.source.ImageTileSource);
|
||||
|
||||
|
||||
/**
|
||||
|
||||
128
src/ol/source/debugtilesource.js
Normal file
128
src/ol/source/debugtilesource.js
Normal file
@@ -0,0 +1,128 @@
|
||||
goog.provide('ol.source.DebugTileSource');
|
||||
goog.provide('ol.source.DebugTileSourceOptions');
|
||||
|
||||
goog.require('ol.Size');
|
||||
goog.require('ol.Tile');
|
||||
goog.require('ol.TileCoord');
|
||||
goog.require('ol.source.TileSource');
|
||||
goog.require('ol.tilegrid.TileGrid');
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.Tile}
|
||||
* @param {ol.TileCoord} tileCoord Tile coordinate.
|
||||
* @param {ol.tilegrid.TileGrid} tileGrid Tile grid.
|
||||
* @private
|
||||
*/
|
||||
ol.DebugTile_ = function(tileCoord, tileGrid) {
|
||||
|
||||
goog.base(this, tileCoord);
|
||||
|
||||
this.state = ol.TileState.LOADED;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.TileCoord}
|
||||
*/
|
||||
this.tileCoord_ = tileCoord;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.Size}
|
||||
*/
|
||||
this.tileSize_ = tileGrid.getTileSize();
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Object.<number, HTMLCanvasElement>}
|
||||
*/
|
||||
this.canvasByContext_ = {};
|
||||
|
||||
};
|
||||
goog.inherits(ol.DebugTile_, ol.Tile);
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.DebugTile_.prototype.getImage = function(opt_context) {
|
||||
var key = goog.isDef(opt_context) ? goog.getUid(opt_context) : -1;
|
||||
if (key in this.canvasByContext_) {
|
||||
return this.canvasByContext_[key];
|
||||
} else {
|
||||
|
||||
var tileSize = this.tileSize_;
|
||||
|
||||
var canvas = /** @type {HTMLCanvasElement} */
|
||||
(goog.dom.createElement(goog.dom.TagName.CANVAS));
|
||||
canvas.width = tileSize.width;
|
||||
canvas.height = tileSize.height;
|
||||
|
||||
var context = canvas.getContext('2d');
|
||||
|
||||
context.strokeStyle = 'black';
|
||||
context.strokeRect(0.5, 0.5, tileSize.width + 0.5, tileSize.height + 0.5);
|
||||
|
||||
context.fillStyle = 'black';
|
||||
context.textAlign = 'center';
|
||||
context.textBaseline = 'middle';
|
||||
context.font = '24px sans-serif';
|
||||
context.fillText(
|
||||
this.tileCoord_.toString(), tileSize.width / 2, tileSize.height / 2);
|
||||
|
||||
this.canvasByContext_[key] = canvas;
|
||||
return canvas;
|
||||
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @typedef {{extent: (ol.Extent|undefined),
|
||||
* projection: (ol.Projection|undefined),
|
||||
* tileGrid: (ol.tilegrid.TileGrid|undefined)}}
|
||||
*/
|
||||
ol.source.DebugTileSourceOptions;
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.source.TileSource}
|
||||
* @param {ol.source.DebugTileSourceOptions} options Options.
|
||||
*/
|
||||
ol.source.DebugTileSource = function(options) {
|
||||
|
||||
goog.base(this, {
|
||||
extent: options.extent,
|
||||
projection: options.projection,
|
||||
tileGrid: options.tileGrid
|
||||
});
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Object.<string, ol.DebugTile_>}
|
||||
* FIXME will need to expire elements from this cache
|
||||
* FIXME see elemoine's work with goog.structs.LinkedMap
|
||||
*/
|
||||
this.tileCache_ = {};
|
||||
|
||||
};
|
||||
goog.inherits(ol.source.DebugTileSource, ol.source.TileSource);
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.source.DebugTileSource.prototype.getTile = function(tileCoord) {
|
||||
var key = tileCoord.toString();
|
||||
if (goog.object.containsKey(this.tileCache_, key)) {
|
||||
return this.tileCache_[key];
|
||||
} else {
|
||||
var tile = new ol.DebugTile_(tileCoord, this.tileGrid);
|
||||
this.tileCache_[key] = tile;
|
||||
return tile;
|
||||
}
|
||||
};
|
||||
95
src/ol/source/imagetilesource.js
Normal file
95
src/ol/source/imagetilesource.js
Normal file
@@ -0,0 +1,95 @@
|
||||
goog.provide('ol.source.ImageTileSource');
|
||||
goog.provide('ol.source.ImageTileSourceOptions');
|
||||
|
||||
goog.require('ol.Attribution');
|
||||
goog.require('ol.Extent');
|
||||
goog.require('ol.ImageTile');
|
||||
goog.require('ol.Projection');
|
||||
goog.require('ol.TileCoord');
|
||||
goog.require('ol.TileUrlFunction');
|
||||
goog.require('ol.TileUrlFunctionType');
|
||||
goog.require('ol.source.TileSource');
|
||||
goog.require('ol.tilegrid.TileGrid');
|
||||
|
||||
|
||||
/**
|
||||
* @typedef {{attributions: (Array.<ol.Attribution>|undefined),
|
||||
* crossOrigin: (null|string|undefined),
|
||||
* extent: (ol.Extent|undefined),
|
||||
* projection: (ol.Projection|undefined),
|
||||
* tileGrid: (ol.tilegrid.TileGrid|undefined),
|
||||
* tileUrlFunction: (ol.TileUrlFunctionType|undefined)}}
|
||||
*/
|
||||
ol.source.ImageTileSourceOptions;
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.source.TileSource}
|
||||
* @param {ol.source.ImageTileSourceOptions} options Options.
|
||||
*/
|
||||
ol.source.ImageTileSource = function(options) {
|
||||
|
||||
goog.base(this, {
|
||||
attributions: options.attributions,
|
||||
extent: options.extent,
|
||||
projection: options.projection,
|
||||
tileGrid: options.tileGrid
|
||||
});
|
||||
|
||||
/**
|
||||
* @protected
|
||||
* @type {ol.TileUrlFunctionType}
|
||||
*/
|
||||
this.tileUrlFunction = goog.isDef(options.tileUrlFunction) ?
|
||||
options.tileUrlFunction :
|
||||
ol.TileUrlFunction.nullTileUrlFunction;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {?string}
|
||||
*/
|
||||
this.crossOrigin_ =
|
||||
goog.isDef(options.crossOrigin) ? options.crossOrigin : 'anonymous';
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Object.<string, ol.ImageTile>}
|
||||
* FIXME will need to expire elements from this cache
|
||||
* FIXME see elemoine's work with goog.structs.LinkedMap
|
||||
*/
|
||||
this.tileCache_ = {};
|
||||
|
||||
};
|
||||
goog.inherits(ol.source.ImageTileSource, ol.source.TileSource);
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.source.ImageTileSource.prototype.getTile = function(tileCoord) {
|
||||
var key = tileCoord.toString();
|
||||
if (goog.object.containsKey(this.tileCache_, key)) {
|
||||
return this.tileCache_[key];
|
||||
} else {
|
||||
var tileUrl = this.getTileCoordUrl(tileCoord);
|
||||
var tile;
|
||||
if (goog.isDef(tileUrl)) {
|
||||
tile = new ol.ImageTile(tileCoord, tileUrl, this.crossOrigin_);
|
||||
} else {
|
||||
tile = null;
|
||||
}
|
||||
this.tileCache_[key] = tile;
|
||||
return tile;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.TileCoord} tileCoord Tile coordinate.
|
||||
* @return {string|undefined} Tile URL.
|
||||
*/
|
||||
ol.source.ImageTileSource.prototype.getTileCoordUrl = function(tileCoord) {
|
||||
return this.tileUrlFunction(tileCoord);
|
||||
};
|
||||
@@ -26,7 +26,7 @@ ol.source.StamenFlavor = {
|
||||
|
||||
|
||||
/**
|
||||
* @typedef {{flavor: ol.source.StamenFlavor,
|
||||
* @typedef {{flavor: (ol.source.StamenFlavor|undefined),
|
||||
* provider: ol.source.StamenProvider}}
|
||||
*/
|
||||
ol.source.StamenOptions;
|
||||
|
||||
@@ -10,14 +10,14 @@ goog.require('ol.Attribution');
|
||||
goog.require('ol.Projection');
|
||||
goog.require('ol.TileCoord');
|
||||
goog.require('ol.TileUrlFunction');
|
||||
goog.require('ol.source.TileSource');
|
||||
goog.require('ol.source.ImageTileSource');
|
||||
goog.require('ol.tilegrid.TileGrid');
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.source.TileSource}
|
||||
* @extends {ol.source.ImageTileSource}
|
||||
* @param {ol.source.TiledWMSOptions} tiledWMSOptions options.
|
||||
*/
|
||||
ol.source.TiledWMS = function(tiledWMSOptions) {
|
||||
@@ -35,20 +35,8 @@ ol.source.TiledWMS = function(tiledWMSOptions) {
|
||||
if (goog.isDef(tiledWMSOptions.tileGrid)) {
|
||||
tileGrid = tiledWMSOptions.tileGrid;
|
||||
} else {
|
||||
// FIXME Factor this out to a more central/generic place.
|
||||
var size = Math.max(
|
||||
projectionExtent.maxX - projectionExtent.minX,
|
||||
projectionExtent.maxY - projectionExtent.minY);
|
||||
var maxZoom = goog.isDef(tiledWMSOptions.maxZoom) ?
|
||||
tiledWMSOptions.maxZoom : 18;
|
||||
var resolutions = new Array(maxZoom + 1);
|
||||
for (var z = 0, zz = resolutions.length; z < zz; ++z) {
|
||||
resolutions[z] = ol.Projection.EPSG_3857_HALF_SIZE / (128 << z);
|
||||
}
|
||||
tileGrid = new ol.tilegrid.TileGrid({
|
||||
origin: projectionExtent.getTopLeft(),
|
||||
resolutions: resolutions
|
||||
});
|
||||
tileGrid = ol.tilegrid.createForProjection(projection,
|
||||
tiledWMSOptions.maxZoom);
|
||||
}
|
||||
|
||||
var baseParams = {
|
||||
@@ -116,4 +104,4 @@ ol.source.TiledWMS = function(tiledWMSOptions) {
|
||||
});
|
||||
|
||||
};
|
||||
goog.inherits(ol.source.TiledWMS, ol.source.TileSource);
|
||||
goog.inherits(ol.source.TiledWMS, ol.source.ImageTileSource);
|
||||
|
||||
@@ -16,7 +16,7 @@ goog.require('goog.string');
|
||||
goog.require('ol.Projection');
|
||||
goog.require('ol.TileCoverageArea');
|
||||
goog.require('ol.TileUrlFunction');
|
||||
goog.require('ol.source.TileSource');
|
||||
goog.require('ol.source.ImageTileSource');
|
||||
goog.require('ol.tilegrid.XYZ');
|
||||
|
||||
|
||||
@@ -45,7 +45,7 @@ goog.exportSymbol('grid', grid);
|
||||
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.source.TileSource}
|
||||
* @extends {ol.source.ImageTileSource}
|
||||
* @param {ol.source.TileJSONOptions} tileJsonOptions TileJSON optios.
|
||||
*/
|
||||
ol.source.TileJSON = function(tileJsonOptions) {
|
||||
@@ -69,7 +69,7 @@ ol.source.TileJSON = function(tileJsonOptions) {
|
||||
this.deferred_.addCallback(this.handleTileJSONResponse, this);
|
||||
|
||||
};
|
||||
goog.inherits(ol.source.TileJSON, ol.source.TileSource);
|
||||
goog.inherits(ol.source.TileJSON, ol.source.ImageTileSource);
|
||||
|
||||
|
||||
/**
|
||||
|
||||
@@ -14,11 +14,9 @@ goog.require('ol.tilegrid.TileGrid');
|
||||
|
||||
/**
|
||||
* @typedef {{attributions: (Array.<ol.Attribution>|undefined),
|
||||
* crossOrigin: (null|string|undefined),
|
||||
* extent: (ol.Extent|undefined),
|
||||
* projection: (ol.Projection|undefined),
|
||||
* tileGrid: (ol.tilegrid.TileGrid|undefined),
|
||||
* tileUrlFunction: (ol.TileUrlFunctionType|undefined)}}
|
||||
* tileGrid: (ol.tilegrid.TileGrid|undefined)}}
|
||||
*/
|
||||
ol.source.TileSourceOptions;
|
||||
|
||||
@@ -44,29 +42,6 @@ ol.source.TileSource = function(tileSourceOptions) {
|
||||
this.tileGrid = goog.isDef(tileSourceOptions.tileGrid) ?
|
||||
tileSourceOptions.tileGrid : null;
|
||||
|
||||
/**
|
||||
* @protected
|
||||
* @type {ol.TileUrlFunctionType}
|
||||
*/
|
||||
this.tileUrlFunction = goog.isDef(tileSourceOptions.tileUrlFunction) ?
|
||||
tileSourceOptions.tileUrlFunction :
|
||||
ol.TileUrlFunction.nullTileUrlFunction;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {?string}
|
||||
*/
|
||||
this.crossOrigin_ = goog.isDef(tileSourceOptions.crossOrigin) ?
|
||||
tileSourceOptions.crossOrigin : 'anonymous';
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Object.<string, ol.Tile>}
|
||||
* FIXME will need to expire elements from this cache
|
||||
* FIXME see elemoine's work with goog.structs.LinkedMap
|
||||
*/
|
||||
this.tileCache_ = {};
|
||||
|
||||
};
|
||||
goog.inherits(ol.source.TileSource, ol.source.Source);
|
||||
|
||||
@@ -83,31 +58,7 @@ ol.source.TileSource.prototype.getResolutions = function() {
|
||||
* @param {ol.TileCoord} tileCoord Tile coordinate.
|
||||
* @return {ol.Tile} Tile.
|
||||
*/
|
||||
ol.source.TileSource.prototype.getTile = function(tileCoord) {
|
||||
var key = tileCoord.toString();
|
||||
if (goog.object.containsKey(this.tileCache_, key)) {
|
||||
return this.tileCache_[key];
|
||||
} else {
|
||||
var tileUrl = this.getTileCoordUrl(tileCoord);
|
||||
var tile;
|
||||
if (goog.isDef(tileUrl)) {
|
||||
tile = new ol.Tile(tileCoord, tileUrl, this.crossOrigin_);
|
||||
} else {
|
||||
tile = null;
|
||||
}
|
||||
this.tileCache_[key] = tile;
|
||||
return tile;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.TileCoord} tileCoord Tile coordinate.
|
||||
* @return {string|undefined} Tile URL.
|
||||
*/
|
||||
ol.source.TileSource.prototype.getTileCoordUrl = function(tileCoord) {
|
||||
return this.tileUrlFunction(tileCoord);
|
||||
};
|
||||
ol.source.TileSource.prototype.getTile = goog.abstractMethod;
|
||||
|
||||
|
||||
/**
|
||||
|
||||
@@ -11,7 +11,7 @@ goog.require('ol.Size');
|
||||
goog.require('ol.TileCoord');
|
||||
goog.require('ol.TileUrlFunction');
|
||||
goog.require('ol.TileUrlFunctionType');
|
||||
goog.require('ol.source.TileSource');
|
||||
goog.require('ol.source.ImageTileSource');
|
||||
goog.require('ol.tilegrid.XYZ');
|
||||
|
||||
|
||||
@@ -31,7 +31,7 @@ ol.source.XYZOptions;
|
||||
|
||||
/**
|
||||
* @constructor
|
||||
* @extends {ol.source.TileSource}
|
||||
* @extends {ol.source.ImageTileSource}
|
||||
* @param {ol.source.XYZOptions} xyzOptions XYZ options.
|
||||
*/
|
||||
ol.source.XYZ = function(xyzOptions) {
|
||||
@@ -110,4 +110,4 @@ ol.source.XYZ = function(xyzOptions) {
|
||||
});
|
||||
|
||||
};
|
||||
goog.inherits(ol.source.XYZ, ol.source.TileSource);
|
||||
goog.inherits(ol.source.XYZ, ol.source.ImageTileSource);
|
||||
|
||||
117
src/ol/tile.js
117
src/ol/tile.js
@@ -24,10 +24,8 @@ ol.TileState = {
|
||||
* @constructor
|
||||
* @extends {goog.events.EventTarget}
|
||||
* @param {ol.TileCoord} tileCoord Tile coordinate.
|
||||
* @param {string} src Image source URI.
|
||||
* @param {?string} crossOrigin Cross origin.
|
||||
*/
|
||||
ol.Tile = function(tileCoord, src, crossOrigin) {
|
||||
ol.Tile = function(tileCoord) {
|
||||
|
||||
goog.base(this);
|
||||
|
||||
@@ -37,39 +35,10 @@ ol.Tile = function(tileCoord, src, crossOrigin) {
|
||||
this.tileCoord = tileCoord;
|
||||
|
||||
/**
|
||||
* Image URI
|
||||
*
|
||||
* @private
|
||||
* @type {string}
|
||||
*/
|
||||
this.src_ = src;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @protected
|
||||
* @type {ol.TileState}
|
||||
*/
|
||||
this.state_ = ol.TileState.IDLE;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Image}
|
||||
*/
|
||||
this.image_ = new Image();
|
||||
if (!goog.isNull(crossOrigin)) {
|
||||
this.image_.crossOrigin = crossOrigin;
|
||||
}
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Object.<number, Image>}
|
||||
*/
|
||||
this.imageByContext_ = {};
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Array.<number>}
|
||||
*/
|
||||
this.imageListenerKeys_ = null;
|
||||
this.state = ol.TileState.IDLE;
|
||||
|
||||
};
|
||||
goog.inherits(ol.Tile, goog.events.EventTarget);
|
||||
@@ -85,24 +54,16 @@ ol.Tile.prototype.dispatchChangeEvent = function() {
|
||||
|
||||
/**
|
||||
* @param {Object=} opt_context Object.
|
||||
* @return {Image} Image.
|
||||
* @return {HTMLCanvasElement|HTMLImageElement|HTMLVideoElement} Image.
|
||||
*/
|
||||
ol.Tile.prototype.getImage = function(opt_context) {
|
||||
if (goog.isDef(opt_context)) {
|
||||
var image;
|
||||
var key = goog.getUid(opt_context);
|
||||
if (key in this.imageByContext_) {
|
||||
return this.imageByContext_[key];
|
||||
} else if (goog.object.isEmpty(this.imageByContext_)) {
|
||||
image = this.image_;
|
||||
} else {
|
||||
image = /** @type {Image} */ this.image_.cloneNode(false);
|
||||
}
|
||||
this.imageByContext_[key] = image;
|
||||
return image;
|
||||
} else {
|
||||
return this.image_;
|
||||
}
|
||||
ol.Tile.prototype.getImage = goog.abstractMethod;
|
||||
|
||||
|
||||
/**
|
||||
* @return {string} Key.
|
||||
*/
|
||||
ol.Tile.prototype.getKey = function() {
|
||||
return goog.getUid(this).toString();
|
||||
};
|
||||
|
||||
|
||||
@@ -110,59 +71,11 @@ ol.Tile.prototype.getImage = function(opt_context) {
|
||||
* @return {ol.TileState} State.
|
||||
*/
|
||||
ol.Tile.prototype.getState = function() {
|
||||
return this.state_;
|
||||
return this.state;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Tracks loading or read errors.
|
||||
*
|
||||
* @private
|
||||
* FIXME empty description for jsdoc
|
||||
*/
|
||||
ol.Tile.prototype.handleImageError_ = function() {
|
||||
this.state_ = ol.TileState.ERROR;
|
||||
this.unlistenImage_();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Tracks successful image load.
|
||||
*
|
||||
* @private
|
||||
*/
|
||||
ol.Tile.prototype.handleImageLoad_ = function() {
|
||||
this.state_ = ol.TileState.LOADED;
|
||||
this.unlistenImage_();
|
||||
this.dispatchChangeEvent();
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Load not yet loaded URI.
|
||||
*/
|
||||
ol.Tile.prototype.load = function() {
|
||||
if (this.state_ == ol.TileState.IDLE) {
|
||||
this.state_ = ol.TileState.LOADING;
|
||||
goog.asserts.assert(goog.isNull(this.imageListenerKeys_));
|
||||
this.imageListenerKeys_ = [
|
||||
goog.events.listenOnce(this.image_, goog.events.EventType.ERROR,
|
||||
this.handleImageError_, false, this),
|
||||
goog.events.listenOnce(this.image_, goog.events.EventType.LOAD,
|
||||
this.handleImageLoad_, false, this)
|
||||
];
|
||||
this.image_.src = this.src_;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Discards event handlers which listen for load completion or errors.
|
||||
*
|
||||
* @private
|
||||
*/
|
||||
ol.Tile.prototype.unlistenImage_ = function() {
|
||||
goog.asserts.assert(!goog.isNull(this.imageListenerKeys_));
|
||||
goog.array.forEach(this.imageListenerKeys_, goog.events.unlistenByKey);
|
||||
this.imageListenerKeys_ = null;
|
||||
};
|
||||
|
||||
ol.Tile.prototype.load = goog.abstractMethod;
|
||||
|
||||
@@ -316,3 +316,26 @@ ol.tilegrid.TileGrid.prototype.getTileSize = function() {
|
||||
ol.tilegrid.TileGrid.prototype.getZForResolution = function(resolution) {
|
||||
return ol.array.linearFindNearest(this.resolutions_, resolution);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Projection} projection Projection.
|
||||
* @param {number=} opt_maxZoom Maximum zoom level (optional). Default is 18.
|
||||
* @return {ol.tilegrid.TileGrid} TileGrid instance.
|
||||
*/
|
||||
ol.tilegrid.createForProjection = function(projection, opt_maxZoom) {
|
||||
var projectionExtent = projection.getExtent();
|
||||
var size = Math.max(
|
||||
projectionExtent.maxX - projectionExtent.minX,
|
||||
projectionExtent.maxY - projectionExtent.minY);
|
||||
var maxZoom = goog.isDef(opt_maxZoom) ?
|
||||
opt_maxZoom : 18;
|
||||
var resolutions = new Array(maxZoom + 1);
|
||||
for (var z = 0, zz = resolutions.length; z < zz; ++z) {
|
||||
resolutions[z] = size / (256 << z);
|
||||
}
|
||||
return new ol.tilegrid.TileGrid({
|
||||
origin: projectionExtent.getTopLeft(),
|
||||
resolutions: resolutions
|
||||
});
|
||||
};
|
||||
|
||||
120
src/ol/tilequeue.js
Normal file
120
src/ol/tilequeue.js
Normal file
@@ -0,0 +1,120 @@
|
||||
goog.provide('ol.TilePriorityFunction');
|
||||
goog.provide('ol.TileQueue');
|
||||
|
||||
goog.require('goog.events');
|
||||
goog.require('goog.events.EventType');
|
||||
goog.require('goog.structs.PriorityQueue');
|
||||
goog.require('ol.Coordinate');
|
||||
goog.require('ol.Tile');
|
||||
goog.require('ol.TileState');
|
||||
|
||||
|
||||
/**
|
||||
* @typedef {function(ol.Tile, ol.Coordinate, number): (number|undefined)}
|
||||
*/
|
||||
ol.TilePriorityFunction;
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @constructor
|
||||
* @param {ol.TilePriorityFunction} tilePriorityFunction
|
||||
* Tile priority function.
|
||||
*/
|
||||
ol.TileQueue = function(tilePriorityFunction) {
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.TilePriorityFunction}
|
||||
*/
|
||||
this.tilePriorityFunction_ = tilePriorityFunction;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {number}
|
||||
*/
|
||||
this.maxTilesLoading_ = 8;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {number}
|
||||
*/
|
||||
this.tilesLoading_ = 0;
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {goog.structs.PriorityQueue}
|
||||
*/
|
||||
this.queue_ = new goog.structs.PriorityQueue();
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Object.<string, boolean>}
|
||||
*/
|
||||
this.queuedTileKeys_ = {};
|
||||
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Tile} tile Tile.
|
||||
* @param {ol.Coordinate} tileCenter Tile center.
|
||||
* @param {number} tileResolution Tile resolution.
|
||||
*/
|
||||
ol.TileQueue.prototype.enqueue =
|
||||
function(tile, tileCenter, tileResolution) {
|
||||
if (tile.getState() != ol.TileState.IDLE) {
|
||||
return;
|
||||
}
|
||||
var tileKey = tile.getKey();
|
||||
if (!(tileKey in this.queuedTileKeys_)) {
|
||||
var priority = this.tilePriorityFunction_(tile, tileCenter, tileResolution);
|
||||
if (goog.isDef(priority)) {
|
||||
this.queue_.enqueue(priority, arguments);
|
||||
this.queuedTileKeys_[tileKey] = true;
|
||||
} else {
|
||||
// FIXME fire drop event?
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @protected
|
||||
*/
|
||||
ol.TileQueue.prototype.handleTileChange = function() {
|
||||
--this.tilesLoading_;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* FIXME empty description for jsdoc
|
||||
*/
|
||||
ol.TileQueue.prototype.loadMoreTiles = function() {
|
||||
var tile, tileKey;
|
||||
while (!this.queue_.isEmpty() && this.tilesLoading_ < this.maxTilesLoading_) {
|
||||
tile = (/** @type {Array} */ (this.queue_.dequeue()))[0];
|
||||
tileKey = tile.getKey();
|
||||
delete this.queuedTileKeys_[tileKey];
|
||||
goog.events.listen(tile, goog.events.EventType.CHANGE,
|
||||
this.handleTileChange, false, this);
|
||||
tile.load();
|
||||
++this.tilesLoading_;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* FIXME empty description for jsdoc
|
||||
*/
|
||||
ol.TileQueue.prototype.reprioritize = function() {
|
||||
if (!this.queue_.isEmpty()) {
|
||||
var values = /** @type {Array.<Array>} */ (this.queue_.getValues());
|
||||
this.queue_.clear();
|
||||
this.queuedTileKeys_ = {};
|
||||
var i;
|
||||
for (i = 0; i < values.length; ++i) {
|
||||
this.enqueue.apply(this, values[i]);
|
||||
}
|
||||
}
|
||||
};
|
||||
@@ -28,9 +28,9 @@ ol.TileRange.boundingTileRange = function(var_args) {
|
||||
var tileCoord0 = arguments[0];
|
||||
var tileRange = new ol.TileRange(tileCoord0.x, tileCoord0.y,
|
||||
tileCoord0.x, tileCoord0.y);
|
||||
var i;
|
||||
var i, tileCoord;
|
||||
for (i = 1; i < arguments.length; ++i) {
|
||||
var tileCoord = arguments[i];
|
||||
tileCoord = arguments[i];
|
||||
goog.asserts.assert(tileCoord.z == tileCoord0.z);
|
||||
tileRange.minX = Math.min(tileRange.minX, tileCoord.x);
|
||||
tileRange.minY = Math.min(tileRange.minY, tileCoord.y);
|
||||
@@ -71,22 +71,6 @@ ol.TileRange.prototype.equals = function(tileRange) {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {number} z Z.
|
||||
* @param {function(this: T, ol.TileCoord)} f Callback.
|
||||
* @param {T=} opt_obj The object to be used for the value of 'this' within f.
|
||||
* @template T
|
||||
*/
|
||||
ol.TileRange.prototype.forEachTileCoord = function(z, f, opt_obj) {
|
||||
var x, y;
|
||||
for (x = this.minX; x <= this.maxX; ++x) {
|
||||
for (y = this.minY; y <= this.maxY; ++y) {
|
||||
f.call(opt_obj, new ol.TileCoord(z, x, y));
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
* @return {number} Height.
|
||||
|
||||
92
src/ol/vec/mat4.js
Normal file
92
src/ol/vec/mat4.js
Normal file
@@ -0,0 +1,92 @@
|
||||
goog.provide('ol.vec.Mat4');
|
||||
|
||||
goog.require('goog.vec.Mat4');
|
||||
|
||||
|
||||
/**
|
||||
* @param {!goog.vec.Mat4.Float32} matrix Matrix.
|
||||
* @param {number} value Brightness value.
|
||||
* @return {!goog.vec.Mat4.Float32} Matrix.
|
||||
*/
|
||||
ol.vec.Mat4.makeBrightness = function(matrix, value) {
|
||||
goog.vec.Mat4.makeTranslate(matrix, value, value, value);
|
||||
return matrix;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {!goog.vec.Mat4.Float32} matrix Matrix.
|
||||
* @param {number} value Contrast value.
|
||||
* @return {!goog.vec.Mat4.Float32} Matrix.
|
||||
*/
|
||||
ol.vec.Mat4.makeContrast = function(matrix, value) {
|
||||
goog.vec.Mat4.makeScale(matrix, value, value, value);
|
||||
var translateValue = (-0.5 * value + 0.5);
|
||||
goog.vec.Mat4.setColumnValues(matrix, 3,
|
||||
translateValue, translateValue, translateValue, 1);
|
||||
return matrix;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {!goog.vec.Mat4.Float32} matrix Matrix.
|
||||
* @param {number} value Hue value.
|
||||
* @return {!goog.vec.Mat4.Float32} Matrix.
|
||||
*/
|
||||
ol.vec.Mat4.makeHue = function(matrix, value) {
|
||||
var cosHue = Math.cos(value);
|
||||
var sinHue = Math.sin(value);
|
||||
var v00 = 0.213 + cosHue * 0.787 - sinHue * 0.213;
|
||||
var v01 = 0.715 - cosHue * 0.715 - sinHue * 0.715;
|
||||
var v02 = 0.072 - cosHue * 0.072 + sinHue * 0.928;
|
||||
var v03 = 0;
|
||||
var v10 = 0.213 - cosHue * 0.213 + sinHue * 0.143;
|
||||
var v11 = 0.715 + cosHue * 0.285 + sinHue * 0.140;
|
||||
var v12 = 0.072 - cosHue * 0.072 - sinHue * 0.283;
|
||||
var v13 = 0;
|
||||
var v20 = 0.213 - cosHue * 0.213 - sinHue * 0.787;
|
||||
var v21 = 0.715 - cosHue * 0.715 + sinHue * 0.715;
|
||||
var v22 = 0.072 + cosHue * 0.928 + sinHue * 0.072;
|
||||
var v23 = 0;
|
||||
var v30 = 0;
|
||||
var v31 = 0;
|
||||
var v32 = 0;
|
||||
var v33 = 1;
|
||||
goog.vec.Mat4.setFromValues(matrix,
|
||||
v00, v10, v20, v30,
|
||||
v01, v11, v21, v31,
|
||||
v02, v12, v22, v32,
|
||||
v03, v13, v23, v33);
|
||||
return matrix;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {!goog.vec.Mat4.Float32} matrix Matrix.
|
||||
* @param {number} value Saturation value.
|
||||
* @return {!goog.vec.Mat4.Float32} Matrix.
|
||||
*/
|
||||
ol.vec.Mat4.makeSaturation = function(matrix, value) {
|
||||
var v00 = 0.213 + 0.787 * value;
|
||||
var v01 = 0.715 - 0.715 * value;
|
||||
var v02 = 0.072 - 0.072 * value;
|
||||
var v03 = 0;
|
||||
var v10 = 0.213 - 0.213 * value;
|
||||
var v11 = 0.715 + 0.285 * value;
|
||||
var v12 = 0.072 - 0.072 * value;
|
||||
var v13 = 0;
|
||||
var v20 = 0.213 - 0.213 * value;
|
||||
var v21 = 0.715 - 0.715 * value;
|
||||
var v22 = 0.072 + 0.928 * value;
|
||||
var v23 = 0;
|
||||
var v30 = 0;
|
||||
var v31 = 0;
|
||||
var v32 = 0;
|
||||
var v33 = 1;
|
||||
goog.vec.Mat4.setFromValues(matrix,
|
||||
v00, v10, v20, v30,
|
||||
v01, v11, v21, v31,
|
||||
v02, v12, v22, v32,
|
||||
v03, v13, v23, v33);
|
||||
return matrix;
|
||||
};
|
||||
65
src/ol/view.js
Normal file
65
src/ol/view.js
Normal file
@@ -0,0 +1,65 @@
|
||||
goog.provide('ol.View');
|
||||
goog.provide('ol.ViewHint');
|
||||
|
||||
goog.require('goog.array');
|
||||
goog.require('ol.IView');
|
||||
goog.require('ol.IView2D');
|
||||
goog.require('ol.IView3D');
|
||||
|
||||
|
||||
/**
|
||||
* @enum {number}
|
||||
*/
|
||||
ol.ViewHint = {
|
||||
ANIMATING: 0,
|
||||
PANNING: 1
|
||||
};
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @constructor
|
||||
* @implements {ol.IView}
|
||||
* @extends {ol.Object}
|
||||
*/
|
||||
ol.View = function() {
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {Array.<number>}
|
||||
*/
|
||||
this.hints_ = [0, 0];
|
||||
|
||||
};
|
||||
goog.inherits(ol.View, ol.Object);
|
||||
|
||||
|
||||
/**
|
||||
* @return {Array.<number>} Hint.
|
||||
*/
|
||||
ol.View.prototype.getHints = function() {
|
||||
return goog.array.clone(this.hints_);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.View.prototype.getView2D = goog.abstractMethod;
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.View.prototype.getView3D = goog.abstractMethod;
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.ViewHint} hint Hint.
|
||||
* @param {number} delta Delta.
|
||||
*/
|
||||
ol.View.prototype.setHint = function(hint, delta) {
|
||||
goog.asserts.assert(0 <= hint && hint < this.hints_.length);
|
||||
this.hints_[hint] += delta;
|
||||
goog.asserts.assert(this.hints_[hint] >= 0);
|
||||
};
|
||||
344
src/ol/view2d.js
Normal file
344
src/ol/view2d.js
Normal file
@@ -0,0 +1,344 @@
|
||||
// FIXME getView3D has not return type
|
||||
// FIXME remove getExtent?
|
||||
|
||||
goog.provide('ol.View2D');
|
||||
goog.provide('ol.View2DProperty');
|
||||
|
||||
goog.require('ol.Constraints');
|
||||
goog.require('ol.Extent');
|
||||
goog.require('ol.IView2D');
|
||||
goog.require('ol.IView3D');
|
||||
goog.require('ol.Projection');
|
||||
goog.require('ol.ResolutionConstraint');
|
||||
goog.require('ol.RotationConstraint');
|
||||
goog.require('ol.View');
|
||||
|
||||
|
||||
/**
|
||||
* @enum {string}
|
||||
*/
|
||||
ol.View2DProperty = {
|
||||
CENTER: 'center',
|
||||
PROJECTION: 'projection',
|
||||
RESOLUTION: 'resolution',
|
||||
ROTATION: 'rotation'
|
||||
};
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @constructor
|
||||
* @implements {ol.IView2D}
|
||||
* @implements {ol.IView3D}
|
||||
* @extends {ol.View}
|
||||
* @param {ol.View2DOptions=} opt_view2DOptions View2D options.
|
||||
*/
|
||||
ol.View2D = function(opt_view2DOptions) {
|
||||
goog.base(this);
|
||||
var view2DOptions = opt_view2DOptions || {};
|
||||
|
||||
/**
|
||||
* @type {Object.<string, *>}
|
||||
*/
|
||||
var values = {};
|
||||
values[ol.View2DProperty.CENTER] = goog.isDef(view2DOptions.center) ?
|
||||
view2DOptions.center : null;
|
||||
values[ol.View2DProperty.PROJECTION] = ol.Projection.createProjection(
|
||||
view2DOptions.projection, 'EPSG:3857');
|
||||
if (goog.isDef(view2DOptions.resolution)) {
|
||||
values[ol.View2DProperty.RESOLUTION] = view2DOptions.resolution;
|
||||
} else if (goog.isDef(view2DOptions.zoom)) {
|
||||
var projectionExtent = values[ol.View2DProperty.PROJECTION].getExtent();
|
||||
var size = Math.max(
|
||||
projectionExtent.maxX - projectionExtent.minX,
|
||||
projectionExtent.maxY - projectionExtent.minY);
|
||||
values[ol.View2DProperty.RESOLUTION] = size / (256 << view2DOptions.zoom);
|
||||
}
|
||||
values[ol.View2DProperty.ROTATION] = view2DOptions.rotation;
|
||||
this.setValues(values);
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @type {ol.Constraints}
|
||||
*/
|
||||
this.constraints_ = ol.View2D.createConstraints_(view2DOptions);
|
||||
|
||||
};
|
||||
goog.inherits(ol.View2D, ol.View);
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.View2D.prototype.getCenter = function() {
|
||||
return /** @type {ol.Coordinate|undefined} */ (
|
||||
this.get(ol.View2DProperty.CENTER));
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.View2D.prototype,
|
||||
'getCenter',
|
||||
ol.View2D.prototype.getCenter);
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Size} size Box pixel size.
|
||||
* @return {ol.Extent} Extent.
|
||||
*/
|
||||
ol.View2D.prototype.getExtent = function(size) {
|
||||
goog.asserts.assert(this.isDef());
|
||||
var center = this.getCenter();
|
||||
var resolution = this.getResolution();
|
||||
var minX = center.x - resolution * size.width / 2;
|
||||
var minY = center.y - resolution * size.height / 2;
|
||||
var maxX = center.x + resolution * size.width / 2;
|
||||
var maxY = center.y + resolution * size.height / 2;
|
||||
return new ol.Extent(minX, minY, maxX, maxY);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.View2D.prototype.getProjection = function() {
|
||||
return /** @type {ol.Projection|undefined} */ (
|
||||
this.get(ol.View2DProperty.PROJECTION));
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.View2D.prototype,
|
||||
'getProjection',
|
||||
ol.View2D.prototype.getProjection);
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.View2D.prototype.getResolution = function() {
|
||||
return /** @type {number|undefined} */ (
|
||||
this.get(ol.View2DProperty.RESOLUTION));
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.View2D.prototype,
|
||||
'getResolution',
|
||||
ol.View2D.prototype.getResolution);
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Extent} extent Extent.
|
||||
* @param {ol.Size} size Box pixel size.
|
||||
* @return {number} Resolution.
|
||||
*/
|
||||
ol.View2D.prototype.getResolutionForExtent = function(extent, size) {
|
||||
var xResolution = (extent.maxX - extent.minX) / size.width;
|
||||
var yResolution = (extent.maxY - extent.minY) / size.height;
|
||||
return Math.max(xResolution, yResolution);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {number} Map rotation.
|
||||
*/
|
||||
ol.View2D.prototype.getRotation = function() {
|
||||
return /** @type {number|undefined} */ (
|
||||
this.get(ol.View2DProperty.ROTATION)) || 0;
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.View2D.prototype,
|
||||
'getRotation',
|
||||
ol.View2D.prototype.getRotation);
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.View2D.prototype.getView2D = function() {
|
||||
return this;
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
ol.View2D.prototype.getView2DState = function() {
|
||||
goog.asserts.assert(this.isDef());
|
||||
var center = /** @type {ol.Coordinate} */ (this.getCenter());
|
||||
var projection = /** @type {ol.Projection} */ (this.getProjection());
|
||||
var resolution = /** @type {number} */ (this.getResolution());
|
||||
var rotation = /** @type {number} */ (this.getRotation());
|
||||
return {
|
||||
center: new ol.Coordinate(center.x, center.y),
|
||||
projection: projection,
|
||||
resolution: resolution,
|
||||
rotation: rotation
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* FIXME return type
|
||||
*/
|
||||
ol.View2D.prototype.getView3D = function() {
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Extent} extent Extent.
|
||||
* @param {ol.Size} size Box pixel size.
|
||||
*/
|
||||
ol.View2D.prototype.fitExtent = function(extent, size) {
|
||||
this.setCenter(extent.getCenter());
|
||||
var resolution = this.getResolutionForExtent(extent, size);
|
||||
resolution = this.constraints_.resolution(resolution, 0);
|
||||
this.setResolution(resolution);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @return {boolean} Is defined.
|
||||
*/
|
||||
ol.View2D.prototype.isDef = function() {
|
||||
return goog.isDefAndNotNull(this.getCenter()) &&
|
||||
goog.isDef(this.getResolution());
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Coordinate|undefined} center Center.
|
||||
*/
|
||||
ol.View2D.prototype.setCenter = function(center) {
|
||||
this.set(ol.View2DProperty.CENTER, center);
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.View2D.prototype,
|
||||
'setCenter',
|
||||
ol.View2D.prototype.setCenter);
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Projection|undefined} projection Projection.
|
||||
*/
|
||||
ol.View2D.prototype.setProjection = function(projection) {
|
||||
this.set(ol.View2DProperty.PROJECTION, projection);
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.View2D.prototype,
|
||||
'setProjection',
|
||||
ol.View2D.prototype.setProjection);
|
||||
|
||||
|
||||
/**
|
||||
* @param {number|undefined} resolution Resolution.
|
||||
*/
|
||||
ol.View2D.prototype.setResolution = function(resolution) {
|
||||
this.set(ol.View2DProperty.RESOLUTION, resolution);
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.View2D.prototype,
|
||||
'setResolution',
|
||||
ol.View2D.prototype.setResolution);
|
||||
|
||||
|
||||
/**
|
||||
* @param {number|undefined} rotation Rotation.
|
||||
*/
|
||||
ol.View2D.prototype.setRotation = function(rotation) {
|
||||
this.set(ol.View2DProperty.ROTATION, rotation);
|
||||
};
|
||||
goog.exportProperty(
|
||||
ol.View2D.prototype,
|
||||
'setRotation',
|
||||
ol.View2D.prototype.setRotation);
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Map} map Map.
|
||||
* @param {number|undefined} rotation Rotation.
|
||||
* @param {number} delta Delta.
|
||||
*/
|
||||
ol.View2D.prototype.rotate = function(map, rotation, delta) {
|
||||
rotation = this.constraints_.rotation(rotation, delta);
|
||||
this.setRotation(rotation);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @param {ol.Map} map Map.
|
||||
* @param {number|undefined} resolution Resolution to go to.
|
||||
* @param {ol.Coordinate=} opt_anchor Anchor coordinate.
|
||||
*/
|
||||
ol.View2D.prototype.zoom_ = function(map, resolution, opt_anchor) {
|
||||
if (goog.isDefAndNotNull(resolution) && goog.isDefAndNotNull(opt_anchor)) {
|
||||
var anchor = opt_anchor;
|
||||
var oldCenter = /** @type {!ol.Coordinate} */ (this.getCenter());
|
||||
var oldResolution = this.getResolution();
|
||||
var x = anchor.x - resolution * (anchor.x - oldCenter.x) / oldResolution;
|
||||
var y = anchor.y - resolution * (anchor.y - oldCenter.y) / oldResolution;
|
||||
var center = new ol.Coordinate(x, y);
|
||||
map.withFrozenRendering(function() {
|
||||
this.setCenter(center);
|
||||
this.setResolution(resolution);
|
||||
}, this);
|
||||
} else {
|
||||
this.setResolution(resolution);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Map} map Map.
|
||||
* @param {number} delta Delta from previous zoom level.
|
||||
* @param {ol.Coordinate=} opt_anchor Anchor coordinate.
|
||||
*/
|
||||
ol.View2D.prototype.zoom = function(map, delta, opt_anchor) {
|
||||
var resolution = this.constraints_.resolution(this.getResolution(), delta);
|
||||
this.zoom_(map, resolution, opt_anchor);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @param {ol.Map} map Map.
|
||||
* @param {number|undefined} resolution Resolution to go to.
|
||||
* @param {ol.Coordinate=} opt_anchor Anchor coordinate.
|
||||
*/
|
||||
ol.View2D.prototype.zoomToResolution = function(map, resolution, opt_anchor) {
|
||||
resolution = this.constraints_.resolution(resolution, 0);
|
||||
this.zoom_(map, resolution, opt_anchor);
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* @private
|
||||
* @param {ol.View2DOptions} view2DOptions View2D options.
|
||||
* @return {ol.Constraints} Constraints.
|
||||
*/
|
||||
ol.View2D.createConstraints_ = function(view2DOptions) {
|
||||
var resolutionConstraint;
|
||||
if (goog.isDef(view2DOptions.resolutions)) {
|
||||
resolutionConstraint = ol.ResolutionConstraint.createSnapToResolutions(
|
||||
view2DOptions.resolutions);
|
||||
} else {
|
||||
var maxResolution, numZoomLevels, zoomFactor;
|
||||
if (goog.isDef(view2DOptions.maxResolution) &&
|
||||
goog.isDef(view2DOptions.numZoomLevels) &&
|
||||
goog.isDef(view2DOptions.zoomFactor)) {
|
||||
maxResolution = view2DOptions.maxResolution;
|
||||
numZoomLevels = view2DOptions.numZoomLevels;
|
||||
zoomFactor = view2DOptions.zoomFactor;
|
||||
} else {
|
||||
var projectionExtent = ol.Projection.createProjection(
|
||||
view2DOptions.projection, 'EPSG:3857').getExtent();
|
||||
maxResolution = Math.max(
|
||||
projectionExtent.maxX - projectionExtent.minX,
|
||||
projectionExtent.maxY - projectionExtent.minY) / 256;
|
||||
// number of steps we want between two data resolutions
|
||||
var numSteps = 4;
|
||||
numZoomLevels = 29 * numSteps;
|
||||
zoomFactor = Math.exp(Math.log(2) / numSteps);
|
||||
}
|
||||
resolutionConstraint = ol.ResolutionConstraint.createSnapToPower(
|
||||
zoomFactor, maxResolution, numZoomLevels - 1);
|
||||
}
|
||||
// FIXME rotation constraint is not configurable at the moment
|
||||
var rotationConstraint = ol.RotationConstraint.none;
|
||||
return new ol.Constraints(resolutionConstraint, rotationConstraint);
|
||||
};
|
||||
@@ -78,6 +78,7 @@
|
||||
<script type="text/javascript" src="spec/ol/projection.test.js"></script>
|
||||
<script type="text/javascript" src="spec/ol/rectangle.test.js"></script>
|
||||
<script type="text/javascript" src="spec/ol/resolutionconstraint.test.js"></script>
|
||||
<script type="text/javascript" src="spec/ol/view2d.test.js"></script>
|
||||
<script type="text/javascript" src="spec/ol/layer/layer.test.js"></script>
|
||||
<script type="text/javascript" src="spec/ol/source/xyz.test.js"></script>
|
||||
<script type="text/javascript" src="spec/ol/tilecoord.test.js"></script>
|
||||
|
||||
@@ -4,6 +4,7 @@ goog.require('ol.Collection');
|
||||
goog.require('ol.Coordinate');
|
||||
goog.require('ol.Map');
|
||||
goog.require('ol.RendererHint');
|
||||
goog.require('ol.View2D');
|
||||
goog.require('ol.layer.TileLayer');
|
||||
goog.require('ol.source.XYZ');
|
||||
|
||||
@@ -24,56 +25,6 @@ describe('ol.Map', function() {
|
||||
});
|
||||
});
|
||||
|
||||
describe('create constraints', function() {
|
||||
|
||||
describe('create resolution constraint', function() {
|
||||
|
||||
describe('with no options', function() {
|
||||
it('gives a correct resolution constraint function', function() {
|
||||
var options = {};
|
||||
var fn = ol.Map.createConstraints_(options).resolution;
|
||||
expect(fn(156543.03392804097, 0))
|
||||
.toRoughlyEqual(156543.03392804097, 1e-9);
|
||||
expect(fn(78271.51696402048, 0))
|
||||
.toRoughlyEqual(78271.51696402048, 1e-10);
|
||||
});
|
||||
});
|
||||
|
||||
describe('with maxResolution, numZoomLevels, and zoomFactor options',
|
||||
function() {
|
||||
it('gives a correct resolution constraint function', function() {
|
||||
var options = {
|
||||
maxResolution: 81,
|
||||
numZoomLevels: 4,
|
||||
zoomFactor: 3
|
||||
};
|
||||
var fn = ol.Map.createConstraints_(options).resolution;
|
||||
expect(fn(82, 0)).toEqual(81);
|
||||
expect(fn(81, 0)).toEqual(81);
|
||||
expect(fn(27, 0)).toEqual(27);
|
||||
expect(fn(9, 0)).toEqual(9);
|
||||
expect(fn(3, 0)).toEqual(3);
|
||||
expect(fn(2, 0)).toEqual(3);
|
||||
});
|
||||
});
|
||||
|
||||
describe('with resolutions', function() {
|
||||
it('gives a correct resolution constraint function', function() {
|
||||
var options = {
|
||||
resolutions: [97, 76, 65, 54, 0.45]
|
||||
};
|
||||
var fn = ol.Map.createConstraints_(options).resolution;
|
||||
expect(fn(97, 0), 97);
|
||||
expect(fn(76, 0), 76);
|
||||
expect(fn(65, 0), 65);
|
||||
expect(fn(54, 0), 54);
|
||||
expect(fn(0.45, 0), 0.45);
|
||||
});
|
||||
});
|
||||
|
||||
});
|
||||
});
|
||||
|
||||
describe('create interactions', function() {
|
||||
|
||||
var options;
|
||||
@@ -158,11 +109,13 @@ describe('ol.Map', function() {
|
||||
});
|
||||
|
||||
map = new ol.Map({
|
||||
center: new ol.Coordinate(0, 0),
|
||||
layers: new ol.Collection([layer]),
|
||||
renderer: ol.RendererHint.DOM,
|
||||
target: 'map',
|
||||
zoom: 1
|
||||
view: new ol.View2D({
|
||||
center: new ol.Coordinate(0, 0),
|
||||
zoom: 1
|
||||
})
|
||||
});
|
||||
});
|
||||
|
||||
@@ -183,7 +136,7 @@ describe('ol.Map', function() {
|
||||
var duration = 500;
|
||||
var destination = new ol.Coordinate(1000, 1000);
|
||||
|
||||
var origin = map.getCenter();
|
||||
var origin = map.getView().getCenter();
|
||||
var start = new Date().getTime();
|
||||
var x0 = origin.x;
|
||||
var y0 = origin.y;
|
||||
@@ -202,7 +155,7 @@ describe('ol.Map', function() {
|
||||
x = destination.x;
|
||||
y = destination.y;
|
||||
}
|
||||
map.setCenter(new ol.Coordinate(x, y));
|
||||
map.getView().setCenter(new ol.Coordinate(x, y));
|
||||
if (more) {
|
||||
animationDelay.start();
|
||||
}
|
||||
@@ -220,7 +173,7 @@ describe('ol.Map', function() {
|
||||
waits(100);
|
||||
runs(function() {
|
||||
expect(o.callback).toHaveBeenCalled();
|
||||
var loc = map.getCenter();
|
||||
var loc = map.getView().getCenter();
|
||||
expect(loc.x).not.toEqual(origin.x);
|
||||
expect(loc.y).not.toEqual(origin.y);
|
||||
expect(loc.x).not.toEqual(destination.x);
|
||||
@@ -230,7 +183,7 @@ describe('ol.Map', function() {
|
||||
// confirm that the map has reached the destination after the duration
|
||||
waits(duration);
|
||||
runs(function() {
|
||||
var loc = map.getCenter();
|
||||
var loc = map.getView().getCenter();
|
||||
expect(loc.x).toEqual(destination.x);
|
||||
expect(loc.y).toEqual(destination.y);
|
||||
});
|
||||
|
||||
@@ -46,16 +46,19 @@ describe('ol.Object', function() {
|
||||
|
||||
describe('notify', function() {
|
||||
|
||||
var listener1, listener2;
|
||||
var listener1, listener2, listener3;
|
||||
|
||||
beforeEach(function() {
|
||||
listener1 = jasmine.createSpy();
|
||||
goog.events.listen(o, 'k_changed', listener1);
|
||||
|
||||
listener2 = jasmine.createSpy();
|
||||
goog.events.listen(o, 'changed', listener2);
|
||||
|
||||
var o2 = new ol.Object();
|
||||
o2.bindTo('k', o);
|
||||
listener2 = jasmine.createSpy();
|
||||
goog.events.listen(o2, 'k_changed', listener2);
|
||||
listener3 = jasmine.createSpy();
|
||||
goog.events.listen(o2, 'k_changed', listener3);
|
||||
});
|
||||
|
||||
it('dispatches events', function() {
|
||||
@@ -63,24 +66,32 @@ describe('ol.Object', function() {
|
||||
expect(listener1).toHaveBeenCalled();
|
||||
});
|
||||
|
||||
it('dispatches events to bound objects', function() {
|
||||
it('dispatches generic change events to bound objects', function() {
|
||||
o.notify('k');
|
||||
expect(listener2).toHaveBeenCalled();
|
||||
});
|
||||
|
||||
it('dispatches events to bound objects', function() {
|
||||
o.notify('k');
|
||||
expect(listener3).toHaveBeenCalled();
|
||||
});
|
||||
});
|
||||
|
||||
describe('set', function() {
|
||||
|
||||
var listener1, o2, listener2;
|
||||
var listener1, o2, listener2, listener3;
|
||||
|
||||
beforeEach(function() {
|
||||
listener1 = jasmine.createSpy();
|
||||
goog.events.listen(o, 'k_changed', listener1);
|
||||
|
||||
listener2 = jasmine.createSpy();
|
||||
goog.events.listen(o, 'changed', listener2);
|
||||
|
||||
o2 = new ol.Object();
|
||||
o2.bindTo('k', o);
|
||||
listener2 = jasmine.createSpy();
|
||||
goog.events.listen(o2, 'k_changed', listener2);
|
||||
listener3 = jasmine.createSpy();
|
||||
goog.events.listen(o2, 'k_changed', listener3);
|
||||
});
|
||||
|
||||
it('dispatches events to object', function() {
|
||||
@@ -88,15 +99,25 @@ describe('ol.Object', function() {
|
||||
expect(listener1).toHaveBeenCalled();
|
||||
});
|
||||
|
||||
it('dispatches events to bound object', function() {
|
||||
it('dispatches generic change events to object', function() {
|
||||
o.set('k', 1);
|
||||
expect(listener2).toHaveBeenCalled();
|
||||
});
|
||||
|
||||
it('dispatches events to bound object', function() {
|
||||
o.set('k', 1);
|
||||
expect(listener3).toHaveBeenCalled();
|
||||
});
|
||||
|
||||
it('dispatches events to object bound to', function() {
|
||||
o2.set('k', 2);
|
||||
expect(listener1).toHaveBeenCalled();
|
||||
});
|
||||
|
||||
it('dispatches generic change events to object bound to', function() {
|
||||
o2.set('k', 2);
|
||||
expect(listener2).toHaveBeenCalled();
|
||||
});
|
||||
});
|
||||
|
||||
describe('bind', function() {
|
||||
|
||||
@@ -51,36 +51,6 @@ describe('ol.TileRange', function() {
|
||||
});
|
||||
});
|
||||
|
||||
describe('forEachTileCoord', function() {
|
||||
it('iterates as expected', function() {
|
||||
var tileRange = new ol.TileRange(0, 2, 1, 3);
|
||||
|
||||
var tileCoords = [];
|
||||
tileRange.forEachTileCoord(5, function(tileCoord) {
|
||||
tileCoords.push(
|
||||
new ol.TileCoord(tileCoord.z, tileCoord.x, tileCoord.y));
|
||||
});
|
||||
|
||||
expect(tileCoords.length).toEqual(4);
|
||||
|
||||
expect(tileCoords[0].z).toEqual(5);
|
||||
expect(tileCoords[0].x).toEqual(0);
|
||||
expect(tileCoords[0].y).toEqual(2);
|
||||
|
||||
expect(tileCoords[1].z).toEqual(5);
|
||||
expect(tileCoords[1].x).toEqual(0);
|
||||
expect(tileCoords[1].y).toEqual(3);
|
||||
|
||||
expect(tileCoords[2].z).toEqual(5);
|
||||
expect(tileCoords[2].x).toEqual(1);
|
||||
expect(tileCoords[2].y).toEqual(2);
|
||||
|
||||
expect(tileCoords[3].z).toEqual(5);
|
||||
expect(tileCoords[3].x).toEqual(1);
|
||||
expect(tileCoords[3].y).toEqual(3);
|
||||
});
|
||||
});
|
||||
|
||||
describe('getSize', function() {
|
||||
it('returns the expected size', function() {
|
||||
var tileRange = new ol.TileRange(0, 1, 2, 4);
|
||||
|
||||
53
test/spec/ol/view2d.test.js
Normal file
53
test/spec/ol/view2d.test.js
Normal file
@@ -0,0 +1,53 @@
|
||||
goog.require('ol.View2D');
|
||||
|
||||
describe('ol.View2D', function() {
|
||||
describe('create constraints', function() {
|
||||
|
||||
describe('create resolution constraint', function() {
|
||||
|
||||
describe('with no options', function() {
|
||||
it('gives a correct resolution constraint function', function() {
|
||||
var options = {};
|
||||
var fn = ol.View2D.createConstraints_(options).resolution;
|
||||
expect(fn(156543.03392804097, 0))
|
||||
.toRoughlyEqual(156543.03392804097, 1e-9);
|
||||
expect(fn(78271.51696402048, 0))
|
||||
.toRoughlyEqual(78271.51696402048, 1e-10);
|
||||
});
|
||||
});
|
||||
|
||||
describe('with maxResolution, numZoomLevels, and zoomFactor options',
|
||||
function() {
|
||||
it('gives a correct resolution constraint function', function() {
|
||||
var options = {
|
||||
maxResolution: 81,
|
||||
numZoomLevels: 4,
|
||||
zoomFactor: 3
|
||||
};
|
||||
var fn = ol.View2D.createConstraints_(options).resolution;
|
||||
expect(fn(82, 0)).toEqual(81);
|
||||
expect(fn(81, 0)).toEqual(81);
|
||||
expect(fn(27, 0)).toEqual(27);
|
||||
expect(fn(9, 0)).toEqual(9);
|
||||
expect(fn(3, 0)).toEqual(3);
|
||||
expect(fn(2, 0)).toEqual(3);
|
||||
});
|
||||
});
|
||||
|
||||
describe('with resolutions', function() {
|
||||
it('gives a correct resolution constraint function', function() {
|
||||
var options = {
|
||||
resolutions: [97, 76, 65, 54, 0.45]
|
||||
};
|
||||
var fn = ol.View2D.createConstraints_(options).resolution;
|
||||
expect(fn(97, 0)).toEqual(97);
|
||||
expect(fn(76, 0)).toEqual(76);
|
||||
expect(fn(65, 0)).toEqual(65);
|
||||
expect(fn(54, 0)).toEqual(54);
|
||||
expect(fn(0.45, 0)).toEqual(0.45);
|
||||
});
|
||||
});
|
||||
|
||||
});
|
||||
});
|
||||
});
|
||||
Reference in New Issue
Block a user