Test rendercomplete waits for icon load
This commit is contained in:
@@ -25,6 +25,7 @@ import VectorSource from '../../../../src/ol/source/Vector.js';
|
|||||||
import View from '../../../../src/ol/View.js';
|
import View from '../../../../src/ol/View.js';
|
||||||
import WebGLPointsLayer from '../../../../src/ol/layer/WebGLPoints.js';
|
import WebGLPointsLayer from '../../../../src/ol/layer/WebGLPoints.js';
|
||||||
import XYZ from '../../../../src/ol/source/XYZ.js';
|
import XYZ from '../../../../src/ol/source/XYZ.js';
|
||||||
|
import {Icon, Style} from '../../../../src/ol/style.js';
|
||||||
import {LineString, Point, Polygon} from '../../../../src/ol/geom.js';
|
import {LineString, Point, Polygon} from '../../../../src/ol/geom.js';
|
||||||
import {TRUE} from '../../../../src/ol/functions.js';
|
import {TRUE} from '../../../../src/ol/functions.js';
|
||||||
import {
|
import {
|
||||||
@@ -403,105 +404,186 @@ describe('ol/Map', function () {
|
|||||||
});
|
});
|
||||||
|
|
||||||
describe('rendercomplete event', function () {
|
describe('rendercomplete event', function () {
|
||||||
let map;
|
let map, target;
|
||||||
|
|
||||||
beforeEach(function () {
|
beforeEach(function () {
|
||||||
const target = document.createElement('div');
|
target = document.createElement('div');
|
||||||
target.style.width = '100px';
|
target.style.width = '100px';
|
||||||
target.style.height = '100px';
|
target.style.height = '100px';
|
||||||
document.body.appendChild(target);
|
document.body.appendChild(target);
|
||||||
map = new Map({
|
|
||||||
target: target,
|
|
||||||
layers: [
|
|
||||||
new TileLayer({
|
|
||||||
opacity: 0.5,
|
|
||||||
source: new XYZ({
|
|
||||||
url: 'spec/ol/data/osm-{z}-{x}-{y}.png',
|
|
||||||
}),
|
|
||||||
}),
|
|
||||||
new ImageLayer({
|
|
||||||
source: new ImageStatic({
|
|
||||||
url: 'spec/ol/data/osm-0-0-0.png',
|
|
||||||
imageExtent: getProjection('EPSG:3857').getExtent(),
|
|
||||||
projection: 'EPSG:3857',
|
|
||||||
}),
|
|
||||||
}),
|
|
||||||
new VectorLayer({
|
|
||||||
source: new VectorSource({
|
|
||||||
url: 'spec/ol/data/point.json',
|
|
||||||
format: new GeoJSON(),
|
|
||||||
}),
|
|
||||||
}),
|
|
||||||
new VectorLayer({
|
|
||||||
source: new VectorSource({
|
|
||||||
url: 'spec/ol/data/point.json',
|
|
||||||
format: new GeoJSON(),
|
|
||||||
strategy: tileStrategy(createXYZ()),
|
|
||||||
}),
|
|
||||||
}),
|
|
||||||
new VectorLayer({
|
|
||||||
source: new VectorSource({
|
|
||||||
features: [new Feature(new Point([0, 0]))],
|
|
||||||
}),
|
|
||||||
}),
|
|
||||||
new VectorLayer({
|
|
||||||
source: new VectorSource({
|
|
||||||
loader: function (extent, resolution, projection) {
|
|
||||||
this.addFeature(new Feature(new Point([0, 0])));
|
|
||||||
},
|
|
||||||
}),
|
|
||||||
}),
|
|
||||||
new WebGLPointsLayer({
|
|
||||||
source: new VectorSource({
|
|
||||||
features: [new Feature(new Point([0, 0]))],
|
|
||||||
}),
|
|
||||||
style: {
|
|
||||||
symbol: {
|
|
||||||
color: 'red',
|
|
||||||
symbolType: 'circle',
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}),
|
|
||||||
],
|
|
||||||
});
|
|
||||||
});
|
});
|
||||||
|
|
||||||
afterEach(function () {
|
afterEach(function () {
|
||||||
document.body.removeChild(map.getTargetElement());
|
disposeMap(map);
|
||||||
map.setTarget(null);
|
|
||||||
map.dispose();
|
|
||||||
map.getLayers().forEach((layer) => layer.dispose());
|
map.getLayers().forEach((layer) => layer.dispose());
|
||||||
});
|
});
|
||||||
|
|
||||||
it('triggers when all tiles and sources are loaded and faded in', function (done) {
|
describe('renderer ready property', function () {
|
||||||
const layers = map.getLayers().getArray();
|
beforeEach(function () {
|
||||||
expect(layers[6].getRenderer().ready).to.be(false);
|
map = new Map({
|
||||||
map.once('rendercomplete', function () {
|
target: target,
|
||||||
expect(map.tileQueue_.getTilesLoading()).to.be(0);
|
layers: [
|
||||||
expect(layers[1].getSource().image_.getState()).to.be(
|
new TileLayer({
|
||||||
ImageState.LOADED
|
opacity: 0.5,
|
||||||
|
source: new XYZ({
|
||||||
|
url: 'spec/ol/data/osm-{z}-{x}-{y}.png',
|
||||||
|
}),
|
||||||
|
}),
|
||||||
|
new ImageLayer({
|
||||||
|
source: new ImageStatic({
|
||||||
|
url: 'spec/ol/data/osm-0-0-0.png',
|
||||||
|
imageExtent: getProjection('EPSG:3857').getExtent(),
|
||||||
|
projection: 'EPSG:3857',
|
||||||
|
}),
|
||||||
|
}),
|
||||||
|
new VectorLayer({
|
||||||
|
source: new VectorSource({
|
||||||
|
url: 'spec/ol/data/point.json',
|
||||||
|
format: new GeoJSON(),
|
||||||
|
}),
|
||||||
|
}),
|
||||||
|
new VectorLayer({
|
||||||
|
source: new VectorSource({
|
||||||
|
url: 'spec/ol/data/point.json',
|
||||||
|
format: new GeoJSON(),
|
||||||
|
strategy: tileStrategy(createXYZ()),
|
||||||
|
}),
|
||||||
|
}),
|
||||||
|
new VectorLayer({
|
||||||
|
source: new VectorSource({
|
||||||
|
features: [new Feature(new Point([0, 0]))],
|
||||||
|
}),
|
||||||
|
}),
|
||||||
|
new VectorLayer({
|
||||||
|
source: new VectorSource({
|
||||||
|
loader: function (extent, resolution, projection) {
|
||||||
|
this.addFeature(new Feature(new Point([0, 0])));
|
||||||
|
},
|
||||||
|
}),
|
||||||
|
}),
|
||||||
|
new WebGLPointsLayer({
|
||||||
|
source: new VectorSource({
|
||||||
|
features: [new Feature(new Point([0, 0]))],
|
||||||
|
}),
|
||||||
|
style: {
|
||||||
|
symbol: {
|
||||||
|
color: 'red',
|
||||||
|
symbolType: 'circle',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}),
|
||||||
|
],
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('triggers when all tiles and sources are loaded and faded in', function (done) {
|
||||||
|
const layers = map.getLayers().getArray();
|
||||||
|
expect(layers[6].getRenderer().ready).to.be(false);
|
||||||
|
map.once('rendercomplete', function () {
|
||||||
|
expect(map.tileQueue_.getTilesLoading()).to.be(0);
|
||||||
|
expect(layers[1].getSource().image_.getState()).to.be(
|
||||||
|
ImageState.LOADED
|
||||||
|
);
|
||||||
|
expect(layers[2].getSource().getFeatures().length).to.be(1);
|
||||||
|
expect(layers[6].getRenderer().ready).to.be(true);
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
map.setView(
|
||||||
|
new View({
|
||||||
|
center: [0, 0],
|
||||||
|
zoom: 0,
|
||||||
|
})
|
||||||
);
|
);
|
||||||
expect(layers[2].getSource().getFeatures().length).to.be(1);
|
|
||||||
expect(layers[6].getRenderer().ready).to.be(true);
|
|
||||||
done();
|
|
||||||
});
|
});
|
||||||
map.setView(
|
|
||||||
new View({
|
it('ignores invisible layers', function (done) {
|
||||||
center: [0, 0],
|
map.getLayers().forEach((layer, i) => layer.setVisible(i === 4));
|
||||||
zoom: 0,
|
map.setView(
|
||||||
})
|
new View({
|
||||||
);
|
center: [0, 0],
|
||||||
|
zoom: 0,
|
||||||
|
})
|
||||||
|
);
|
||||||
|
map.once('rendercomplete', () => done());
|
||||||
|
});
|
||||||
});
|
});
|
||||||
it('ignores invisible layers', function (done) {
|
|
||||||
map.getLayers().forEach(function (layer, i) {
|
describe('icon loading', function () {
|
||||||
layer.setVisible(i === 4);
|
/** @type {Icon} */
|
||||||
|
let icon;
|
||||||
|
beforeEach(function () {
|
||||||
|
icon = new Icon({
|
||||||
|
src: 'spec/ol/data/dot.png',
|
||||||
|
});
|
||||||
|
|
||||||
|
const delay = 100;
|
||||||
|
// Delay icon change events
|
||||||
|
let states = [{state: icon.getImageState()}];
|
||||||
|
icon.listenImageChange = function (listener) {
|
||||||
|
if (!listener._delay) {
|
||||||
|
listener._delay = (e) => {
|
||||||
|
const key = setTimeout(() => {
|
||||||
|
states.shift();
|
||||||
|
listener.call(this, e);
|
||||||
|
}, delay);
|
||||||
|
Object.assign(states[states.length - 1], {key, listener});
|
||||||
|
states.push({
|
||||||
|
state: Icon.prototype.getImageState.call(this),
|
||||||
|
});
|
||||||
|
};
|
||||||
|
}
|
||||||
|
return Icon.prototype.listenImageChange.call(this, listener._delay);
|
||||||
|
};
|
||||||
|
icon.unlistenImageChange = function (listener) {
|
||||||
|
states = states.filter((state) => {
|
||||||
|
if (state.listener !== listener) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
clearTimeout(listener.key);
|
||||||
|
return false;
|
||||||
|
});
|
||||||
|
const addedListener = listener._delay;
|
||||||
|
delete listener._delay;
|
||||||
|
return Icon.prototype.unlistenImageChange.call(this, addedListener);
|
||||||
|
};
|
||||||
|
icon.getImageState = function () {
|
||||||
|
return states[0].state;
|
||||||
|
};
|
||||||
|
});
|
||||||
|
|
||||||
|
it('waits for icons to load', function (done) {
|
||||||
|
map = new Map({
|
||||||
|
target: target,
|
||||||
|
view: new View({
|
||||||
|
center: [0, 0],
|
||||||
|
resolution: 1,
|
||||||
|
}),
|
||||||
|
layers: [
|
||||||
|
new VectorLayer({
|
||||||
|
source: new VectorSource({
|
||||||
|
features: [new Feature(new Point([0, 0]))],
|
||||||
|
}),
|
||||||
|
style: new Style({
|
||||||
|
image: icon,
|
||||||
|
}),
|
||||||
|
}),
|
||||||
|
],
|
||||||
|
});
|
||||||
|
let loaded = false;
|
||||||
|
icon.listenImageChange(function (e) {
|
||||||
|
if (e.target.getImageState() === ImageState.LOADED) {
|
||||||
|
loaded = true;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
map.once('rendercomplete', function () {
|
||||||
|
try {
|
||||||
|
expect(loaded).to.be(true);
|
||||||
|
done();
|
||||||
|
} catch (e) {
|
||||||
|
done(e);
|
||||||
|
}
|
||||||
|
});
|
||||||
});
|
});
|
||||||
map.setView(
|
|
||||||
new View({
|
|
||||||
center: [0, 0],
|
|
||||||
zoom: 0,
|
|
||||||
})
|
|
||||||
);
|
|
||||||
map.once('rendercomplete', () => done());
|
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user