Merge pull request #13269 from mike-000/TileTexture-tilePixelRatio-gutter

Pass tilePixelRatio and gutter to TileTexture
This commit is contained in:
Tim Schaub
2022-02-07 13:45:22 -07:00
committed by GitHub
6 changed files with 112 additions and 10 deletions
+10 -1
View File
@@ -308,6 +308,9 @@ class WebGLTileLayerRenderer extends WebGLLayerRenderer {
const tileLayer = this.getLayer(); const tileLayer = this.getLayer();
const tileSource = tileLayer.getRenderSource(); const tileSource = tileLayer.getRenderSource();
const tileGrid = tileSource.getTileGridForProjection(viewState.projection); const tileGrid = tileSource.getTileGridForProjection(viewState.projection);
const tilePixelRatio = tileSource.getTilePixelRatio(frameState.pixelRatio);
const gutter = tileSource.getGutterForProjection(viewState.projection);
const tileTextureCache = this.tileTextureCache_; const tileTextureCache = this.tileTextureCache_;
const tileRange = tileGrid.getTileRangeForExtentAndZ( const tileRange = tileGrid.getTileRangeForExtentAndZ(
extent, extent,
@@ -352,7 +355,13 @@ class WebGLTileLayerRenderer extends WebGLLayerRenderer {
viewState.projection viewState.projection
); );
if (!tileTexture) { if (!tileTexture) {
tileTexture = new TileTexture(tile, tileGrid, this.helper); tileTexture = new TileTexture(
tile,
tileGrid,
this.helper,
tilePixelRatio,
gutter
);
tileTextureCache.set(cacheKey, tileTexture); tileTextureCache.set(cacheKey, tileTexture);
} else { } else {
if (this.isDrawableTile_(tile)) { if (this.isDrawableTile_(tile)) {
+45 -9
View File
@@ -9,6 +9,9 @@ import ReprojTile from '../reproj/Tile.js';
import TileState from '../TileState.js'; import TileState from '../TileState.js';
import WebGLArrayBuffer from './Buffer.js'; import WebGLArrayBuffer from './Buffer.js';
import {ARRAY_BUFFER, STATIC_DRAW} from '../webgl.js'; import {ARRAY_BUFFER, STATIC_DRAW} from '../webgl.js';
import {IMAGE_SMOOTHING_DISABLED} from '../renderer/canvas/common.js';
import {assign} from '../obj.js';
import {createCanvasContext2D} from '../dom.js';
import {toSize} from '../size.js'; import {toSize} from '../size.js';
/** /**
@@ -123,8 +126,10 @@ class TileTexture extends EventTarget {
* @param {TileType} tile The tile. * @param {TileType} tile The tile.
* @param {import("../tilegrid/TileGrid.js").default} grid Tile grid. * @param {import("../tilegrid/TileGrid.js").default} grid Tile grid.
* @param {import("../webgl/Helper.js").default} helper WebGL helper. * @param {import("../webgl/Helper.js").default} helper WebGL helper.
* @param {number} [opt_tilePixelRatio=1] Tile pixel ratio.
* @param {number} [opt_gutter=0] The size in pixels of the gutter around image tiles to ignore.
*/ */
constructor(tile, grid, helper) { constructor(tile, grid, helper, opt_tilePixelRatio, opt_gutter) {
super(); super();
/** /**
@@ -140,6 +145,11 @@ class TileTexture extends EventTarget {
this.size = toSize(grid.getTileSize(tile.tileCoord[0])); this.size = toSize(grid.getTileSize(tile.tileCoord[0]));
this.tilePixelRatio_ =
opt_tilePixelRatio !== undefined ? opt_tilePixelRatio : 1;
this.gutter_ = opt_gutter !== undefined ? opt_gutter : 0;
this.bandCount = NaN; this.bandCount = NaN;
this.helper_ = helper; this.helper_ = helper;
@@ -192,21 +202,47 @@ class TileTexture extends EventTarget {
const tile = this.tile; const tile = this.tile;
if (tile instanceof ImageTile || tile instanceof ReprojTile) { if (tile instanceof ImageTile || tile instanceof ReprojTile) {
let image = tile.getImage();
if (this.gutter_ !== 0) {
const gutter = this.tilePixelRatio_ * this.gutter_;
const width = Math.round(image.width - 2 * gutter);
const height = Math.round(image.height - 2 * gutter);
const context = createCanvasContext2D(width, height);
if (!tile.interpolate) {
assign(context, IMAGE_SMOOTHING_DISABLED);
}
context.drawImage(
image,
gutter,
gutter,
width,
height,
0,
0,
width,
height
);
image = context.canvas;
}
const texture = gl.createTexture(); const texture = gl.createTexture();
this.textures.push(texture); this.textures.push(texture);
this.bandCount = 4; this.bandCount = 4;
uploadImageTexture(gl, texture, tile.getImage(), tile.interpolate); uploadImageTexture(gl, texture, image, tile.interpolate);
return; return;
} }
const pixelSize = [
this.size[0] * this.tilePixelRatio_,
this.size[1] * this.tilePixelRatio_,
];
const data = tile.getData(); const data = tile.getData();
const isFloat = data instanceof Float32Array; const isFloat = data instanceof Float32Array;
const pixelCount = this.size[0] * this.size[1]; const pixelCount = pixelSize[0] * pixelSize[1];
const DataType = isFloat ? Float32Array : Uint8Array; const DataType = isFloat ? Float32Array : Uint8Array;
const bytesPerElement = DataType.BYTES_PER_ELEMENT; const bytesPerElement = DataType.BYTES_PER_ELEMENT;
const bytesPerRow = data.byteLength / this.size[1]; const bytesPerRow = data.byteLength / pixelSize[1];
this.bandCount = Math.floor(bytesPerRow / bytesPerElement / this.size[0]); this.bandCount = Math.floor(bytesPerRow / bytesPerElement / pixelSize[0]);
const textureCount = Math.ceil(this.bandCount / 4); const textureCount = Math.ceil(this.bandCount / 4);
if (textureCount === 1) { if (textureCount === 1) {
@@ -216,7 +252,7 @@ class TileTexture extends EventTarget {
helper, helper,
texture, texture,
data, data,
this.size, pixelSize,
this.bandCount, this.bandCount,
tile.interpolate tile.interpolate
); );
@@ -235,8 +271,8 @@ class TileTexture extends EventTarget {
let dataIndex = 0; let dataIndex = 0;
let rowOffset = 0; let rowOffset = 0;
const colCount = this.size[0] * this.bandCount; const colCount = pixelSize[0] * this.bandCount;
for (let rowIndex = 0; rowIndex < this.size[1]; ++rowIndex) { for (let rowIndex = 0; rowIndex < pixelSize[1]; ++rowIndex) {
for (let colIndex = 0; colIndex < colCount; ++colIndex) { for (let colIndex = 0; colIndex < colCount; ++colIndex) {
const dataValue = data[rowOffset + colIndex]; const dataValue = data[rowOffset + colIndex];
@@ -261,7 +297,7 @@ class TileTexture extends EventTarget {
helper, helper,
texture, texture,
textureData, textureData,
this.size, pixelSize,
bandCount, bandCount,
tile.interpolate tile.interpolate
); );
Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

@@ -0,0 +1,32 @@
import DataTile from '../../../../src/ol/source/DataTile.js';
import Map from '../../../../src/ol/Map.js';
import TileLayer from '../../../../src/ol/layer/WebGLTile.js';
import View from '../../../../src/ol/View.js';
const size = 512;
const data = new Uint8Array(size * size);
for (let row = 0; row < size; ++row) {
for (let col = 0; col < size; ++col) {
data[row * size + col] = (row + col) % 2 === 0 ? 255 : 0;
}
}
new Map({
target: 'map',
layers: [
new TileLayer({
source: new DataTile({
maxZoom: 0,
loader: () => data,
tilePixelRatio: 2,
}),
}),
],
view: new View({
center: [0, 0],
zoom: 4,
}),
});
render();
Binary file not shown.

After

Width:  |  Height:  |  Size: 9.0 KiB

@@ -0,0 +1,25 @@
import Map from '../../../../src/ol/Map.js';
import TileLayer from '../../../../src/ol/layer/WebGLTile.js';
import TileWMS from '../../../../src/ol/source/TileWMS.js';
import View from '../../../../src/ol/View.js';
const tileWms = new TileWMS({
params: {
'LAYERS': 'layer',
},
gutter: 20,
url: '/data/tiles/wms/wms20.png',
transition: 0,
});
new Map({
pixelRatio: 1.5,
layers: [new TileLayer({source: tileWms})],
target: 'map',
view: new View({
center: [0, 0],
zoom: 5,
}),
});
render();