Merge pull request #10048 from ahocevar/early-empty-state
Early EMPTY state for VectorRenderTile
This commit is contained in:
@@ -112,12 +112,10 @@ class TileQueue extends PriorityQueue {
|
|||||||
if (state === TileState.ABORT) {
|
if (state === TileState.ABORT) {
|
||||||
abortedTiles = true;
|
abortedTiles = true;
|
||||||
} else if (state === TileState.IDLE && !(tileKey in this.tilesLoadingKeys_)) {
|
} else if (state === TileState.IDLE && !(tileKey in this.tilesLoadingKeys_)) {
|
||||||
|
this.tilesLoadingKeys_[tileKey] = true;
|
||||||
|
++this.tilesLoading_;
|
||||||
|
++newLoads;
|
||||||
tile.load();
|
tile.load();
|
||||||
if (tile.getState() === TileState.LOADING) {
|
|
||||||
this.tilesLoadingKeys_[tileKey] = true;
|
|
||||||
++this.tilesLoading_;
|
|
||||||
++newLoads;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (newLoads === 0 && abortedTiles) {
|
if (newLoads === 0 && abortedTiles) {
|
||||||
|
|||||||
@@ -200,11 +200,10 @@ class VectorTile extends UrlTile {
|
|||||||
const minZoom = sourceTileGrid.getMinZoom();
|
const minZoom = sourceTileGrid.getMinZoom();
|
||||||
|
|
||||||
const previousSourceTiles = this.sourceTilesByTileKey_[tile.getKey()];
|
const previousSourceTiles = this.sourceTilesByTileKey_[tile.getKey()];
|
||||||
let sourceTiles, covered, empty, loadedZ;
|
let sourceTiles, covered, loadedZ;
|
||||||
if (previousSourceTiles && previousSourceTiles.length > 0 && previousSourceTiles[0].tileCoord[0] === sourceZ) {
|
if (previousSourceTiles && previousSourceTiles.length > 0 && previousSourceTiles[0].tileCoord[0] === sourceZ) {
|
||||||
sourceTiles = previousSourceTiles;
|
sourceTiles = previousSourceTiles;
|
||||||
covered = true;
|
covered = true;
|
||||||
empty = false;
|
|
||||||
loadedZ = sourceZ;
|
loadedZ = sourceZ;
|
||||||
} else {
|
} else {
|
||||||
sourceTiles = [];
|
sourceTiles = [];
|
||||||
@@ -212,7 +211,6 @@ class VectorTile extends UrlTile {
|
|||||||
do {
|
do {
|
||||||
--loadedZ;
|
--loadedZ;
|
||||||
covered = true;
|
covered = true;
|
||||||
empty = true;
|
|
||||||
sourceTileGrid.forEachTileCoord(extent, loadedZ, function(sourceTileCoord) {
|
sourceTileGrid.forEachTileCoord(extent, loadedZ, function(sourceTileCoord) {
|
||||||
const coordKey = getKey(sourceTileCoord);
|
const coordKey = getKey(sourceTileCoord);
|
||||||
let sourceTile;
|
let sourceTile;
|
||||||
@@ -220,7 +218,6 @@ class VectorTile extends UrlTile {
|
|||||||
sourceTile = this.sourceTileByCoordKey_[coordKey];
|
sourceTile = this.sourceTileByCoordKey_[coordKey];
|
||||||
const state = sourceTile.getState();
|
const state = sourceTile.getState();
|
||||||
if (state === TileState.LOADED || state === TileState.ERROR || state === TileState.EMPTY) {
|
if (state === TileState.LOADED || state === TileState.ERROR || state === TileState.EMPTY) {
|
||||||
empty = empty && state === TileState.EMPTY;
|
|
||||||
sourceTiles.push(sourceTile);
|
sourceTiles.push(sourceTile);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -233,20 +230,15 @@ class VectorTile extends UrlTile {
|
|||||||
sourceTile.projection = projection;
|
sourceTile.projection = projection;
|
||||||
sourceTile.resolution = sourceTileGrid.getResolution(sourceTileCoord[0]);
|
sourceTile.resolution = sourceTileGrid.getResolution(sourceTileCoord[0]);
|
||||||
this.sourceTileByCoordKey_[coordKey] = sourceTile;
|
this.sourceTileByCoordKey_[coordKey] = sourceTile;
|
||||||
empty = false;
|
|
||||||
sourceTile.addEventListener(EventType.CHANGE, this.handleTileChange.bind(this));
|
sourceTile.addEventListener(EventType.CHANGE, this.handleTileChange.bind(this));
|
||||||
sourceTile.load();
|
sourceTile.load();
|
||||||
} else {
|
|
||||||
sourceTile = null;
|
|
||||||
}
|
}
|
||||||
} else {
|
|
||||||
empty = false;
|
|
||||||
}
|
}
|
||||||
covered = false;
|
covered = false;
|
||||||
if (sourceTile === undefined) {
|
if (!sourceTile) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (sourceTile !== null && tile.getState() === TileState.IDLE) {
|
if (sourceTile.getState() !== TileState.EMPTY && tile.getState() === TileState.IDLE) {
|
||||||
tile.loadingSourceTiles++;
|
tile.loadingSourceTiles++;
|
||||||
const key = listen(sourceTile, EventType.CHANGE, function() {
|
const key = listen(sourceTile, EventType.CHANGE, function() {
|
||||||
const state = sourceTile.getState();
|
const state = sourceTile.getState();
|
||||||
@@ -274,14 +266,14 @@ class VectorTile extends UrlTile {
|
|||||||
} while (!covered && loadedZ > minZoom);
|
} while (!covered && loadedZ > minZoom);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!empty && tile.getState() === TileState.IDLE) {
|
if (tile.getState() === TileState.IDLE) {
|
||||||
tile.setState(TileState.LOADING);
|
tile.setState(TileState.LOADING);
|
||||||
}
|
}
|
||||||
if (covered || empty) {
|
if (covered) {
|
||||||
tile.hifi = sourceZ === loadedZ;
|
tile.hifi = sourceZ === loadedZ;
|
||||||
tile.sourceZ = loadedZ;
|
tile.sourceZ = loadedZ;
|
||||||
if (tile.getState() < TileState.LOADED) {
|
if (tile.getState() < TileState.LOADED) {
|
||||||
tile.setState(empty ? TileState.EMPTY : TileState.LOADED);
|
tile.setState(TileState.LOADED);
|
||||||
} else if (!previousSourceTiles || !equals(sourceTiles, previousSourceTiles)) {
|
} else if (!previousSourceTiles || !equals(sourceTiles, previousSourceTiles)) {
|
||||||
this.removeSourceTiles(tile);
|
this.removeSourceTiles(tile);
|
||||||
this.addSourceTiles(tile, sourceTiles);
|
this.addSourceTiles(tile, sourceTiles);
|
||||||
@@ -336,8 +328,8 @@ class VectorTile extends UrlTile {
|
|||||||
const tileCoord = [z, x, y];
|
const tileCoord = [z, x, y];
|
||||||
let urlTileCoord = this.getTileCoordForTileUrlFunction(tileCoord, projection);
|
let urlTileCoord = this.getTileCoordForTileUrlFunction(tileCoord, projection);
|
||||||
const sourceExtent = this.getTileGrid().getExtent();
|
const sourceExtent = this.getTileGrid().getExtent();
|
||||||
|
const tileGrid = this.getTileGridForProjection(projection);
|
||||||
if (urlTileCoord && sourceExtent) {
|
if (urlTileCoord && sourceExtent) {
|
||||||
const tileGrid = this.getTileGridForProjection(projection);
|
|
||||||
const tileExtent = tileGrid.getTileCoordExtent(urlTileCoord);
|
const tileExtent = tileGrid.getTileCoordExtent(urlTileCoord);
|
||||||
// make extent 1 pixel smaller so we don't load tiles for < 0.5 pixel render space
|
// make extent 1 pixel smaller so we don't load tiles for < 0.5 pixel render space
|
||||||
bufferExtent(tileExtent, -tileGrid.getResolution(z), tileExtent);
|
bufferExtent(tileExtent, -tileGrid.getResolution(z), tileExtent);
|
||||||
@@ -345,9 +337,21 @@ class VectorTile extends UrlTile {
|
|||||||
urlTileCoord = null;
|
urlTileCoord = null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
let empty = true;
|
||||||
|
if (urlTileCoord !== null) {
|
||||||
|
const sourceTileGrid = this.tileGrid;
|
||||||
|
const resolution = tileGrid.getResolution(z);
|
||||||
|
const sourceZ = sourceTileGrid.getZForResolution(resolution, 1);
|
||||||
|
// make extent 1 pixel smaller so we don't load tiles for < 0.5 pixel render space
|
||||||
|
const extent = tileGrid.getTileCoordExtent(urlTileCoord);
|
||||||
|
bufferExtent(extent, -resolution, extent);
|
||||||
|
sourceTileGrid.forEachTileCoord(extent, sourceZ, function(sourceTileCoord) {
|
||||||
|
empty = empty && !this.tileUrlFunction(sourceTileCoord, pixelRatio, projection);
|
||||||
|
}.bind(this));
|
||||||
|
}
|
||||||
const newTile = new VectorRenderTile(
|
const newTile = new VectorRenderTile(
|
||||||
tileCoord,
|
tileCoord,
|
||||||
urlTileCoord !== null ? TileState.IDLE : TileState.EMPTY,
|
empty ? TileState.EMPTY : TileState.IDLE,
|
||||||
urlTileCoord,
|
urlTileCoord,
|
||||||
this.tileGrid,
|
this.tileGrid,
|
||||||
this.getSourceTiles.bind(this, pixelRatio, projection),
|
this.getSourceTiles.bind(this, pixelRatio, projection),
|
||||||
|
|||||||
@@ -71,19 +71,13 @@ describe('ol.source.VectorTile', function() {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
it('handles empty tiles', function(done) {
|
it('handles empty tiles', function() {
|
||||||
const source = new VectorTileSource({
|
const source = new VectorTileSource({
|
||||||
format: new GeoJSON(),
|
format: new GeoJSON(),
|
||||||
url: ''
|
url: ''
|
||||||
});
|
});
|
||||||
const tile = source.getTile(0, 0, 0, 1, source.getProjection());
|
const tile = source.getTile(0, 0, 0, 1, source.getProjection());
|
||||||
|
expect(tile.getState()).to.be(TileState.EMPTY);
|
||||||
const key = listen(tile, 'change', function(e) {
|
|
||||||
unlistenByKey(key);
|
|
||||||
expect(tile.getState()).to.be(TileState.EMPTY);
|
|
||||||
done();
|
|
||||||
});
|
|
||||||
tile.load();
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it('creates empty tiles outside the source extent', function() {
|
it('creates empty tiles outside the source extent', function() {
|
||||||
@@ -103,14 +97,30 @@ describe('ol.source.VectorTile', function() {
|
|||||||
expect(tile.getState()).to.be(TileState.EMPTY);
|
expect(tile.getState()).to.be(TileState.EMPTY);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('creates empty tiles when the tileUrlFunction returns undefined', function() {
|
||||||
|
const source = new VectorTileSource({
|
||||||
|
tileUrlFunction: function(tileCoord) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
const tile = source.getTile(1, 1, 1, 1, source.getProjection());
|
||||||
|
expect(tile.getState()).to.be(TileState.EMPTY);
|
||||||
|
});
|
||||||
|
|
||||||
it('creates non-empty tiles outside the world extent when wrapX === true', function() {
|
it('creates non-empty tiles outside the world extent when wrapX === true', function() {
|
||||||
const source = new VectorTileSource({});
|
const source = new VectorTileSource({
|
||||||
|
url: '{z}/{x}/{y}.pbf'
|
||||||
|
});
|
||||||
const tile = source.getTile(0, -1, 0, 1, source.getProjection());
|
const tile = source.getTile(0, -1, 0, 1, source.getProjection());
|
||||||
expect(tile.getState()).to.be(TileState.IDLE);
|
expect(tile.getState()).to.be(TileState.IDLE);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('creates non-empty tiles for overzoomed resolutions', function() {
|
it('creates non-empty tiles for overzoomed resolutions', function() {
|
||||||
const source = new VectorTileSource({
|
const source = new VectorTileSource({
|
||||||
|
url: '{z}/{x}/{y}.pbf',
|
||||||
|
tileLoadFunction: function(tile) {
|
||||||
|
tile.setLoader(function() {});
|
||||||
|
},
|
||||||
maxZoom: 16
|
maxZoom: 16
|
||||||
});
|
});
|
||||||
const tile = source.getTile(24, 9119385, 5820434, 1, source.getProjection());
|
const tile = source.getTile(24, 9119385, 5820434, 1, source.getProjection());
|
||||||
|
|||||||
Reference in New Issue
Block a user