Smarter opacity handling
This commit is contained in:
@@ -39,7 +39,7 @@ import {create as createTransform, apply as applyTransform} from './transform.js
|
|||||||
* @property {boolean} animate
|
* @property {boolean} animate
|
||||||
* @property {import("./transform.js").Transform} coordinateToPixelTransform
|
* @property {import("./transform.js").Transform} coordinateToPixelTransform
|
||||||
* @property {null|import("./extent.js").Extent} extent
|
* @property {null|import("./extent.js").Extent} extent
|
||||||
* @property {Array<*>} declutterItems
|
* @property {Array<DeclutterItems>} declutterItems
|
||||||
* @property {import("./coordinate.js").Coordinate} focus
|
* @property {import("./coordinate.js").Coordinate} focus
|
||||||
* @property {number} index
|
* @property {number} index
|
||||||
* @property {Array<import("./layer/Layer.js").State>} layerStatesArray
|
* @property {Array<import("./layer/Layer.js").State>} layerStatesArray
|
||||||
@@ -54,6 +54,13 @@ import {create as createTransform, apply as applyTransform} from './transform.js
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @typedef {Object} DeclutterItems
|
||||||
|
* @property {Array<*>} items Declutter items of an executor.
|
||||||
|
* @property {number} opacity Layer opacity.
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @typedef {function(PluggableMap, ?FrameState): any} PostRenderFunction
|
* @typedef {function(PluggableMap, ?FrameState): any} PostRenderFunction
|
||||||
*/
|
*/
|
||||||
|
|||||||
+3
-2
@@ -122,9 +122,10 @@ export function renderDeclutterItems(frameState, declutterTree) {
|
|||||||
}
|
}
|
||||||
const items = frameState.declutterItems;
|
const items = frameState.declutterItems;
|
||||||
for (let z = items.length - 1; z >= 0; --z) {
|
for (let z = items.length - 1; z >= 0; --z) {
|
||||||
const zIndexItems = items[z];
|
const item = items[z];
|
||||||
|
const zIndexItems = item.items;
|
||||||
for (let i = 0, ii = zIndexItems.length; i < ii; i += 3) {
|
for (let i = 0, ii = zIndexItems.length; i < ii; i += 3) {
|
||||||
declutterTree = zIndexItems[i].renderDeclutter(zIndexItems[i + 1], zIndexItems[i + 2], declutterTree);
|
declutterTree = zIndexItems[i].renderDeclutter(zIndexItems[i + 1], zIndexItems[i + 2], item.opacity, declutterTree);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
items.length = 0;
|
items.length = 0;
|
||||||
|
|||||||
@@ -416,10 +416,11 @@ class Executor extends Disposable {
|
|||||||
/**
|
/**
|
||||||
* @param {import("../canvas.js").DeclutterGroup} declutterGroup Declutter group.
|
* @param {import("../canvas.js").DeclutterGroup} declutterGroup Declutter group.
|
||||||
* @param {import("../../Feature.js").FeatureLike} feature Feature.
|
* @param {import("../../Feature.js").FeatureLike} feature Feature.
|
||||||
|
* @param {number} opacity Layer opacity.
|
||||||
* @param {?} declutterTree Declutter tree.
|
* @param {?} declutterTree Declutter tree.
|
||||||
* @return {?} Declutter tree.
|
* @return {?} Declutter tree.
|
||||||
*/
|
*/
|
||||||
renderDeclutter(declutterGroup, feature, declutterTree) {
|
renderDeclutter(declutterGroup, feature, opacity, declutterTree) {
|
||||||
if (declutterGroup && declutterGroup.length > 5) {
|
if (declutterGroup && declutterGroup.length > 5) {
|
||||||
const groupCount = declutterGroup[4];
|
const groupCount = declutterGroup[4];
|
||||||
if (groupCount == 1 || groupCount == declutterGroup.length - 5) {
|
if (groupCount == 1 || groupCount == declutterGroup.length - 5) {
|
||||||
@@ -438,13 +439,19 @@ class Executor extends Disposable {
|
|||||||
declutterTree.insert(box);
|
declutterTree.insert(box);
|
||||||
for (let j = 5, jj = declutterGroup.length; j < jj; ++j) {
|
for (let j = 5, jj = declutterGroup.length; j < jj; ++j) {
|
||||||
const declutterData = /** @type {Array} */ (declutterGroup[j]);
|
const declutterData = /** @type {Array} */ (declutterGroup[j]);
|
||||||
if (declutterData) {
|
const context = declutterData[0];
|
||||||
if (declutterData.length > 11) {
|
const currentAlpha = context.globalAlpha;
|
||||||
this.replayTextBackground_(declutterData[0],
|
if (currentAlpha !== opacity) {
|
||||||
declutterData[13], declutterData[14], declutterData[15], declutterData[16],
|
context.globalAlpha = opacity;
|
||||||
declutterData[11], declutterData[12]);
|
}
|
||||||
}
|
if (declutterData.length > 11) {
|
||||||
drawImage.apply(undefined, declutterData);
|
this.replayTextBackground_(declutterData[0],
|
||||||
|
declutterData[13], declutterData[14], declutterData[15], declutterData[16],
|
||||||
|
declutterData[11], declutterData[12]);
|
||||||
|
}
|
||||||
|
drawImage.apply(undefined, declutterData);
|
||||||
|
if (currentAlpha !== opacity) {
|
||||||
|
context.globalAlpha = currentAlpha;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -430,10 +430,11 @@ export function getCircleArray(radius) {
|
|||||||
* @param {!Object<string, Array<*>>} declutterReplays Declutter replays.
|
* @param {!Object<string, Array<*>>} declutterReplays Declutter replays.
|
||||||
* @param {CanvasRenderingContext2D} context Context.
|
* @param {CanvasRenderingContext2D} context Context.
|
||||||
* @param {number} rotation Rotation.
|
* @param {number} rotation Rotation.
|
||||||
|
* @param {number} opacity Opacity.
|
||||||
* @param {boolean} snapToPixel Snap point symbols and text to integer pixels.
|
* @param {boolean} snapToPixel Snap point symbols and text to integer pixels.
|
||||||
* @param {Array<Array<*>>} declutterItems Declutter items.
|
* @param {Array<import("../../PluggableMap.js").DeclutterItems>} declutterItems Declutter items.
|
||||||
*/
|
*/
|
||||||
export function replayDeclutter(declutterReplays, context, rotation, snapToPixel, declutterItems) {
|
export function replayDeclutter(declutterReplays, context, rotation, opacity, snapToPixel, declutterItems) {
|
||||||
const zs = Object.keys(declutterReplays).map(Number).sort(numberSafeCompareFunction);
|
const zs = Object.keys(declutterReplays).map(Number).sort(numberSafeCompareFunction);
|
||||||
const skippedFeatureUids = {};
|
const skippedFeatureUids = {};
|
||||||
for (let z = 0, zz = zs.length; z < zz; ++z) {
|
for (let z = 0, zz = zs.length; z < zz; ++z) {
|
||||||
@@ -443,7 +444,10 @@ export function replayDeclutter(declutterReplays, context, rotation, snapToPixel
|
|||||||
const executor = executorData[i++];
|
const executor = executorData[i++];
|
||||||
if (executor !== currentExecutor) {
|
if (executor !== currentExecutor) {
|
||||||
currentExecutor = executor;
|
currentExecutor = executor;
|
||||||
declutterItems.push(executor.declutterItems);
|
declutterItems.push({
|
||||||
|
items: executor.declutterItems,
|
||||||
|
opacity: opacity
|
||||||
|
});
|
||||||
}
|
}
|
||||||
const transform = executorData[i++];
|
const transform = executorData[i++];
|
||||||
executor.execute(context, transform, rotation, skippedFeatureUids, snapToPixel);
|
executor.execute(context, transform, rotation, skippedFeatureUids, snapToPixel);
|
||||||
|
|||||||
@@ -79,7 +79,7 @@ class CanvasLayerRenderer extends LayerRenderer {
|
|||||||
useContainer(target, transform, opacity) {
|
useContainer(target, transform, opacity) {
|
||||||
const layerClassName = this.getLayer().getClassName();
|
const layerClassName = this.getLayer().getClassName();
|
||||||
let container, context;
|
let container, context;
|
||||||
if (target) {
|
if (target && target.style.opacity === '') {
|
||||||
const canvas = target.firstElementChild;
|
const canvas = target.firstElementChild;
|
||||||
if (canvas instanceof HTMLCanvasElement) {
|
if (canvas instanceof HTMLCanvasElement) {
|
||||||
context = canvas.getContext('2d');
|
context = canvas.getContext('2d');
|
||||||
|
|||||||
@@ -164,7 +164,7 @@ class CanvasVectorLayerRenderer extends CanvasLayerRenderer {
|
|||||||
if (declutterReplays) {
|
if (declutterReplays) {
|
||||||
const viewHints = frameState.viewHints;
|
const viewHints = frameState.viewHints;
|
||||||
const hifi = !(viewHints[ViewHint.ANIMATING] || viewHints[ViewHint.INTERACTING]);
|
const hifi = !(viewHints[ViewHint.ANIMATING] || viewHints[ViewHint.INTERACTING]);
|
||||||
replayDeclutter(declutterReplays, context, rotation, hifi, frameState.declutterItems);
|
replayDeclutter(declutterReplays, context, rotation, 1, hifi, frameState.declutterItems);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (clipped) {
|
if (clipped) {
|
||||||
@@ -174,8 +174,9 @@ class CanvasVectorLayerRenderer extends CanvasLayerRenderer {
|
|||||||
this.postRender(context, frameState);
|
this.postRender(context, frameState);
|
||||||
|
|
||||||
const opacity = layerState.opacity;
|
const opacity = layerState.opacity;
|
||||||
if (opacity !== parseFloat(canvas.style.opacity)) {
|
const container = this.container;
|
||||||
canvas.style.opacity = opacity;
|
if (opacity !== parseFloat(container.style.opacity)) {
|
||||||
|
container.style.opacity = opacity === 1 ? '' : opacity;
|
||||||
}
|
}
|
||||||
|
|
||||||
return this.container;
|
return this.container;
|
||||||
|
|||||||
@@ -478,7 +478,7 @@ class CanvasVectorTileLayerRenderer extends CanvasTileLayerRenderer {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (declutterReplays) {
|
if (declutterReplays) {
|
||||||
replayDeclutter(declutterReplays, context, rotation, hifi, frameState.declutterItems);
|
replayDeclutter(declutterReplays, context, rotation, layerState.opacity, hifi, frameState.declutterItems);
|
||||||
}
|
}
|
||||||
|
|
||||||
return this.container;
|
return this.container;
|
||||||
|
|||||||
Reference in New Issue
Block a user