show labels in wrapped worlds
test labels in wrapped world
This commit is contained in:
+55
-36
@@ -17,6 +17,7 @@ import {
|
|||||||
import {
|
import {
|
||||||
applyTransform,
|
applyTransform,
|
||||||
containsCoordinate,
|
containsCoordinate,
|
||||||
|
containsExtent,
|
||||||
equals,
|
equals,
|
||||||
getCenter,
|
getCenter,
|
||||||
getHeight,
|
getHeight,
|
||||||
@@ -622,9 +623,9 @@ class Graticule extends VectorLayer {
|
|||||||
drawLabels_(event) {
|
drawLabels_(event) {
|
||||||
const rotation = event.frameState.viewState.rotation;
|
const rotation = event.frameState.viewState.rotation;
|
||||||
const extent = event.frameState.extent;
|
const extent = event.frameState.extent;
|
||||||
let rotationCenter, rotationExtent;
|
const rotationCenter = getCenter(extent);
|
||||||
|
let rotationExtent = extent;
|
||||||
if (rotation) {
|
if (rotation) {
|
||||||
rotationCenter = getCenter(extent);
|
|
||||||
const width = getWidth(extent);
|
const width = getWidth(extent);
|
||||||
const height = getHeight(extent);
|
const height = getHeight(extent);
|
||||||
const cr = Math.abs(Math.cos(rotation));
|
const cr = Math.abs(Math.cos(rotation));
|
||||||
@@ -637,42 +638,60 @@ class Graticule extends VectorLayer {
|
|||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
const vectorContext = getVectorContext(event);
|
let startWorld = 0;
|
||||||
let poolIndex = this.meridians_.length + this.parallels_.length;
|
let endWorld = 0;
|
||||||
let feature, index, l, textPoint;
|
let labelsAtStart = this.latLabelPosition_ < 0.5;
|
||||||
|
const projectionExtent = this.projection_.getExtent();
|
||||||
if (this.meridiansLabels_) {
|
const worldWidth = getWidth(projectionExtent);
|
||||||
for (index = 0, l = this.meridiansLabels_.length; index < l; ++index) {
|
if (this.getSource().getWrapX() && this.projection_.canWrapX() && !containsExtent(projectionExtent, extent)) {
|
||||||
const lineString = this.meridians_[index];
|
startWorld = Math.floor((extent[0] - projectionExtent[0]) / worldWidth);
|
||||||
if (!rotation) {
|
endWorld = Math.ceil((extent[2] - projectionExtent[2]) / worldWidth);
|
||||||
textPoint = this.getMeridianPoint_(lineString, extent, index);
|
const inverted = Math.abs(rotation) > Math.PI / 2;
|
||||||
} else {
|
labelsAtStart = labelsAtStart !== inverted;
|
||||||
const clone = lineString.clone();
|
|
||||||
clone.rotate(-rotation, rotationCenter);
|
|
||||||
textPoint = this.getMeridianPoint_(clone, rotationExtent, index);
|
|
||||||
textPoint.rotate(rotation, rotationCenter);
|
|
||||||
}
|
|
||||||
feature = this.featurePool_[poolIndex++];
|
|
||||||
feature.setGeometry(textPoint);
|
|
||||||
feature.set('graticule_label', this.meridiansLabels_[index].text);
|
|
||||||
vectorContext.drawFeature(feature, this.lonLabelStyle_(feature));
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
if (this.parallelsLabels_) {
|
const vectorContext = getVectorContext(event);
|
||||||
for (index = 0, l = this.parallels_.length; index < l; ++index) {
|
|
||||||
const lineString = this.parallels_[index];
|
for (let world = startWorld; world <= endWorld; ++world) {
|
||||||
if (!rotation) {
|
let poolIndex = this.meridians_.length + this.parallels_.length;
|
||||||
textPoint = this.getParallelPoint_(lineString, extent, index);
|
let feature, index, l, textPoint;
|
||||||
} else {
|
|
||||||
const clone = lineString.clone();
|
if (this.meridiansLabels_) {
|
||||||
clone.rotate(-rotation, rotationCenter);
|
for (index = 0, l = this.meridiansLabels_.length; index < l; ++index) {
|
||||||
textPoint = this.getParallelPoint_(clone, rotationExtent, index);
|
const lineString = this.meridians_[index];
|
||||||
textPoint.rotate(rotation, rotationCenter);
|
if (!rotation && world === 0) {
|
||||||
|
textPoint = this.getMeridianPoint_(lineString, extent, index);
|
||||||
|
} else {
|
||||||
|
const clone = lineString.clone();
|
||||||
|
clone.translate(world * worldWidth, 0);
|
||||||
|
clone.rotate(-rotation, rotationCenter);
|
||||||
|
textPoint = this.getMeridianPoint_(clone, rotationExtent, index);
|
||||||
|
textPoint.rotate(rotation, rotationCenter);
|
||||||
|
}
|
||||||
|
feature = this.featurePool_[poolIndex++];
|
||||||
|
feature.setGeometry(textPoint);
|
||||||
|
feature.set('graticule_label', this.meridiansLabels_[index].text);
|
||||||
|
vectorContext.drawFeature(feature, this.lonLabelStyle_(feature));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (this.parallelsLabels_) {
|
||||||
|
if (world === startWorld && labelsAtStart || world === endWorld && !labelsAtStart) {
|
||||||
|
for (index = 0, l = this.parallels_.length; index < l; ++index) {
|
||||||
|
const lineString = this.parallels_[index];
|
||||||
|
if (!rotation && world === 0) {
|
||||||
|
textPoint = this.getParallelPoint_(lineString, extent, index);
|
||||||
|
} else {
|
||||||
|
const clone = lineString.clone();
|
||||||
|
clone.translate(world * worldWidth, 0);
|
||||||
|
clone.rotate(-rotation, rotationCenter);
|
||||||
|
textPoint = this.getParallelPoint_(clone, rotationExtent, index);
|
||||||
|
textPoint.rotate(rotation, rotationCenter);
|
||||||
|
}
|
||||||
|
feature = this.featurePool_[poolIndex++];
|
||||||
|
feature.setGeometry(textPoint);
|
||||||
|
feature.set('graticule_label', this.parallelsLabels_[index].text);
|
||||||
|
vectorContext.drawFeature(feature, this.latLabelStyle_(feature));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
feature = this.featurePool_[poolIndex++];
|
|
||||||
feature.setGeometry(textPoint);
|
|
||||||
feature.set('graticule_label', this.parallelsLabels_[index].text);
|
|
||||||
vectorContext.drawFeature(feature, this.latLabelStyle_(feature));
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
import Graticule from '../../../src/ol/layer/Graticule.js';
|
import Graticule from '../../../src/ol/layer/Graticule.js';
|
||||||
import Map from '../../../src/ol/Map.js';
|
import Map from '../../../src/ol/Map.js';
|
||||||
import {get as getProjection} from '../../../src/ol/proj.js';
|
import {fromLonLat, get as getProjection} from '../../../src/ol/proj.js';
|
||||||
import Stroke from '../../../src/ol/style/Stroke.js';
|
import Stroke from '../../../src/ol/style/Stroke.js';
|
||||||
import Text from '../../../src/ol/style/Text.js';
|
import Text from '../../../src/ol/style/Text.js';
|
||||||
import Feature from '../../../src/ol/Feature.js';
|
import Feature from '../../../src/ol/Feature.js';
|
||||||
@@ -31,7 +31,48 @@ describe('ol.layer.Graticule', function() {
|
|||||||
expect(graticule.parallelsLabels_).to.be(null);
|
expect(graticule.parallelsLabels_).to.be(null);
|
||||||
});
|
});
|
||||||
|
|
||||||
it('creates a graticule with labels', function() {
|
it('creates a graticule with normal world labels', function() {
|
||||||
|
const feature = new Feature();
|
||||||
|
graticule = new Graticule({
|
||||||
|
showLabels: true,
|
||||||
|
wrapX: false
|
||||||
|
});
|
||||||
|
new Map({
|
||||||
|
layers: [graticule]
|
||||||
|
});
|
||||||
|
const extent = [-25614353.926475704, -7827151.696402049,
|
||||||
|
25614353.926475704, 7827151.696402049];
|
||||||
|
const projection = getProjection('EPSG:3857');
|
||||||
|
const resolution = 39135.75848201024;
|
||||||
|
graticule.loaderFunction(extent, resolution, projection);
|
||||||
|
const event = {
|
||||||
|
context: document.createElement('canvas').getContext('2d'),
|
||||||
|
inversePixelTransform: [1, 0, 0, 1, 0, 0],
|
||||||
|
frameState: {
|
||||||
|
coordinateToPixelTransform: [1, 0, 0, 1, 0, 0],
|
||||||
|
extent: extent,
|
||||||
|
pixelRatio: 1,
|
||||||
|
viewState: {
|
||||||
|
projection: projection,
|
||||||
|
resolution: resolution,
|
||||||
|
rotation: 0
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
graticule.drawLabels_(event);
|
||||||
|
expect(graticule.meridiansLabels_.length).to.be(13);
|
||||||
|
expect(graticule.meridiansLabels_[0].text).to.be('0° 00′ 00″');
|
||||||
|
expect(graticule.meridiansLabels_[0].geom.getCoordinates()[0]).to.roughlyEqual(0, 1e-9);
|
||||||
|
expect(graticule.parallelsLabels_.length).to.be(3);
|
||||||
|
expect(graticule.parallelsLabels_[0].text).to.be('0° 00′ 00″');
|
||||||
|
expect(graticule.parallelsLabels_[0].geom.getCoordinates()[1]).to.roughlyEqual(0, 1e-9);
|
||||||
|
feature.set('graticule_label', graticule.meridiansLabels_[0].text);
|
||||||
|
expect(graticule.lonLabelStyle_(feature).getText().getText()).to.be('0° 00′ 00″');
|
||||||
|
feature.set('graticule_label', graticule.parallelsLabels_[0].text);
|
||||||
|
expect(graticule.latLabelStyle_(feature).getText().getText()).to.be('0° 00′ 00″');
|
||||||
|
});
|
||||||
|
|
||||||
|
it('creates a graticule with wrapped world labels', function() {
|
||||||
const feature = new Feature();
|
const feature = new Feature();
|
||||||
graticule = new Graticule({
|
graticule = new Graticule({
|
||||||
showLabels: true
|
showLabels: true
|
||||||
@@ -61,7 +102,8 @@ describe('ol.layer.Graticule', function() {
|
|||||||
graticule.drawLabels_(event);
|
graticule.drawLabels_(event);
|
||||||
expect(graticule.meridiansLabels_.length).to.be(13);
|
expect(graticule.meridiansLabels_.length).to.be(13);
|
||||||
expect(graticule.meridiansLabels_[0].text).to.be('0° 00′ 00″');
|
expect(graticule.meridiansLabels_[0].text).to.be('0° 00′ 00″');
|
||||||
expect(graticule.meridiansLabels_[0].geom.getCoordinates()[0]).to.roughlyEqual(0, 1e-9);
|
const coordinates = fromLonLat([360, 0]);
|
||||||
|
expect(graticule.meridiansLabels_[0].geom.getCoordinates()[0]).to.roughlyEqual(coordinates[0], 1e-9);
|
||||||
expect(graticule.parallelsLabels_.length).to.be(3);
|
expect(graticule.parallelsLabels_.length).to.be(3);
|
||||||
expect(graticule.parallelsLabels_[0].text).to.be('0° 00′ 00″');
|
expect(graticule.parallelsLabels_[0].text).to.be('0° 00′ 00″');
|
||||||
expect(graticule.parallelsLabels_[0].geom.getCoordinates()[1]).to.roughlyEqual(0, 1e-9);
|
expect(graticule.parallelsLabels_[0].geom.getCoordinates()[1]).to.roughlyEqual(0, 1e-9);
|
||||||
|
|||||||
Reference in New Issue
Block a user