Manage buffers in WebGL map renderer
This commit is contained in:
@@ -132,19 +132,6 @@ ol.renderer.webgl.Layer.prototype.bindFramebuffer =
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @inheritDoc
|
|
||||||
*/
|
|
||||||
ol.renderer.webgl.Layer.prototype.disposeInternal = function() {
|
|
||||||
var mapRenderer = this.getWebGLMapRenderer();
|
|
||||||
var gl = mapRenderer.getGL();
|
|
||||||
if (!gl.isContextLost()) {
|
|
||||||
gl.deleteBuffer(this.arrayBuffer_);
|
|
||||||
}
|
|
||||||
goog.base(this, 'disposeInternal');
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return {!goog.vec.Mat4.Float32} Color matrix.
|
* @return {!goog.vec.Mat4.Float32} Color matrix.
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -22,6 +22,7 @@ goog.require('ol.renderer.webgl.FragmentShader');
|
|||||||
goog.require('ol.renderer.webgl.ImageLayer');
|
goog.require('ol.renderer.webgl.ImageLayer');
|
||||||
goog.require('ol.renderer.webgl.TileLayer');
|
goog.require('ol.renderer.webgl.TileLayer');
|
||||||
goog.require('ol.renderer.webgl.VertexShader');
|
goog.require('ol.renderer.webgl.VertexShader');
|
||||||
|
goog.require('ol.structs.Buffer');
|
||||||
goog.require('ol.structs.LRUCache');
|
goog.require('ol.structs.LRUCache');
|
||||||
goog.require('ol.webgl');
|
goog.require('ol.webgl');
|
||||||
goog.require('ol.webgl.WebGLContextEventType');
|
goog.require('ol.webgl.WebGLContextEventType');
|
||||||
@@ -33,6 +34,12 @@ goog.require('ol.webgl.WebGLContextEventType');
|
|||||||
ol.WEBGL_TEXTURE_CACHE_HIGH_WATER_MARK = 1024;
|
ol.WEBGL_TEXTURE_CACHE_HIGH_WATER_MARK = 1024;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @typedef {{buffer: WebGLBuffer}}
|
||||||
|
*/
|
||||||
|
ol.renderer.webgl.BufferCacheEntry;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @typedef {{magFilter: number, minFilter: number, texture: WebGLTexture}}
|
* @typedef {{magFilter: number, minFilter: number, texture: WebGLTexture}}
|
||||||
*/
|
*/
|
||||||
@@ -170,9 +177,20 @@ ol.renderer.webgl.Map = function(container, map) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* @private
|
* @private
|
||||||
* @type {WebGLBuffer}
|
* @type {ol.structs.Buffer}
|
||||||
*/
|
*/
|
||||||
this.arrayBuffer_ = null;
|
this.arrayBuffer_ = new ol.structs.Buffer([
|
||||||
|
-1, -1, 0, 0,
|
||||||
|
1, -1, 1, 0,
|
||||||
|
-1, 1, 0, 1,
|
||||||
|
1, 1, 1, 1
|
||||||
|
]);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @private
|
||||||
|
* @type {Object.<number, ol.renderer.webgl.BufferCacheEntry>}
|
||||||
|
*/
|
||||||
|
this.bufferCache_ = {};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @private
|
* @private
|
||||||
@@ -216,6 +234,46 @@ ol.renderer.webgl.Map = function(container, map) {
|
|||||||
goog.inherits(ol.renderer.webgl.Map, ol.renderer.Map);
|
goog.inherits(ol.renderer.webgl.Map, ol.renderer.Map);
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param {number} target Target.
|
||||||
|
* @param {ol.structs.Buffer} buf Buffer.
|
||||||
|
*/
|
||||||
|
ol.renderer.webgl.Map.prototype.bindBuffer = function(target, buf) {
|
||||||
|
var gl = this.getGL();
|
||||||
|
var arr = buf.getArray();
|
||||||
|
// FIXME dirty set should be in buffer cache
|
||||||
|
var dirtySet = buf.getDirtySet();
|
||||||
|
var bufferKey = goog.getUid(buf);
|
||||||
|
if (bufferKey in this.bufferCache_) {
|
||||||
|
var bufferCacheEntry = this.bufferCache_[bufferKey];
|
||||||
|
gl.bindBuffer(target, bufferCacheEntry.buffer);
|
||||||
|
dirtySet.forEachRange(function(start, stop) {
|
||||||
|
// FIXME check if slice is really efficient here
|
||||||
|
var slice = arr.slice(start, stop);
|
||||||
|
gl.bufferSubData(
|
||||||
|
target,
|
||||||
|
start,
|
||||||
|
target == goog.webgl.ARRAY_BUFFER ?
|
||||||
|
new Float32Array(slice) :
|
||||||
|
new Uint16Array(slice));
|
||||||
|
});
|
||||||
|
} else {
|
||||||
|
var buffer = gl.createBuffer();
|
||||||
|
gl.bindBuffer(target, buffer);
|
||||||
|
// FIXME should get STATIC/STREAM from buf
|
||||||
|
gl.bufferData(
|
||||||
|
target,
|
||||||
|
target == goog.webgl.ARRAY_BUFFER ?
|
||||||
|
new Float32Array(arr) : new Uint16Array(arr),
|
||||||
|
goog.webgl.STATIC_DRAW);
|
||||||
|
this.bufferCache_[bufferKey] = {
|
||||||
|
buffer: buffer
|
||||||
|
};
|
||||||
|
}
|
||||||
|
dirtySet.clear();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @param {ol.Tile} tile Tile.
|
* @param {ol.Tile} tile Tile.
|
||||||
* @param {number} magFilter Mag filter.
|
* @param {number} magFilter Mag filter.
|
||||||
@@ -276,12 +334,31 @@ ol.renderer.webgl.Map.prototype.createLayerRenderer = function(layer) {
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param {ol.structs.Buffer} buf Buffer.
|
||||||
|
*/
|
||||||
|
ol.renderer.webgl.Map.prototype.deleteBuffer = function(buf) {
|
||||||
|
var gl = this.getGL();
|
||||||
|
var arr = buf.getArray();
|
||||||
|
var bufferKey = goog.getUid(buf);
|
||||||
|
goog.asserts.assert(bufferKey in this.bufferCache_);
|
||||||
|
var bufferCacheEntry = this.bufferCache_[bufferKey];
|
||||||
|
if (!gl.isContextLost()) {
|
||||||
|
gl.deleteBuffer(bufferCacheEntry.buffer);
|
||||||
|
}
|
||||||
|
delete this.bufferCache_[bufferKey];
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @inheritDoc
|
* @inheritDoc
|
||||||
*/
|
*/
|
||||||
ol.renderer.webgl.Map.prototype.disposeInternal = function() {
|
ol.renderer.webgl.Map.prototype.disposeInternal = function() {
|
||||||
var gl = this.getGL();
|
var gl = this.getGL();
|
||||||
if (!gl.isContextLost()) {
|
if (!gl.isContextLost()) {
|
||||||
|
goog.object.forEach(this.bufferCache_, function(bufferCacheEntry) {
|
||||||
|
gl.deleteBuffer(bufferCacheEntry.buffer);
|
||||||
|
});
|
||||||
goog.object.forEach(this.programCache_, function(program) {
|
goog.object.forEach(this.programCache_, function(program) {
|
||||||
gl.deleteProgram(program);
|
gl.deleteProgram(program);
|
||||||
});
|
});
|
||||||
@@ -409,7 +486,7 @@ ol.renderer.webgl.Map.prototype.handleWebGLContextLost = function(event) {
|
|||||||
}
|
}
|
||||||
event.preventDefault();
|
event.preventDefault();
|
||||||
this.locations_ = null;
|
this.locations_ = null;
|
||||||
this.arrayBuffer_ = null;
|
this.bufferCache_ = {};
|
||||||
this.shaderCache_ = {};
|
this.shaderCache_ = {};
|
||||||
this.programCache_ = {};
|
this.programCache_ = {};
|
||||||
this.textureCache_.clear();
|
this.textureCache_.clear();
|
||||||
@@ -511,19 +588,7 @@ ol.renderer.webgl.Map.prototype.renderFrame = function(frameState) {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
if (goog.isNull(this.arrayBuffer_)) {
|
this.bindBuffer(goog.webgl.ARRAY_BUFFER, this.arrayBuffer_);
|
||||||
var arrayBuffer = gl.createBuffer();
|
|
||||||
gl.bindBuffer(goog.webgl.ARRAY_BUFFER, arrayBuffer);
|
|
||||||
gl.bufferData(goog.webgl.ARRAY_BUFFER, new Float32Array([
|
|
||||||
-1, -1, 0, 0,
|
|
||||||
1, -1, 1, 0,
|
|
||||||
-1, 1, 0, 1,
|
|
||||||
1, 1, 1, 1
|
|
||||||
]), goog.webgl.STATIC_DRAW);
|
|
||||||
this.arrayBuffer_ = arrayBuffer;
|
|
||||||
} else {
|
|
||||||
gl.bindBuffer(goog.webgl.ARRAY_BUFFER, this.arrayBuffer_);
|
|
||||||
}
|
|
||||||
|
|
||||||
gl.enableVertexAttribArray(this.locations_.a_position);
|
gl.enableVertexAttribArray(this.locations_.a_position);
|
||||||
gl.vertexAttribPointer(
|
gl.vertexAttribPointer(
|
||||||
|
|||||||
@@ -23,6 +23,7 @@ goog.require('ol.math');
|
|||||||
goog.require('ol.renderer.webgl.FragmentShader');
|
goog.require('ol.renderer.webgl.FragmentShader');
|
||||||
goog.require('ol.renderer.webgl.Layer');
|
goog.require('ol.renderer.webgl.Layer');
|
||||||
goog.require('ol.renderer.webgl.VertexShader');
|
goog.require('ol.renderer.webgl.VertexShader');
|
||||||
|
goog.require('ol.structs.Buffer');
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@@ -113,9 +114,14 @@ ol.renderer.webgl.TileLayer = function(mapRenderer, tileLayer) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* @private
|
* @private
|
||||||
* @type {WebGLBuffer}
|
* @type {ol.structs.Buffer}
|
||||||
*/
|
*/
|
||||||
this.arrayBuffer_ = null;
|
this.arrayBuffer_ = new ol.structs.Buffer([
|
||||||
|
0, 0, 0, 1,
|
||||||
|
1, 0, 1, 1,
|
||||||
|
0, 1, 0, 0,
|
||||||
|
1, 1, 1, 0
|
||||||
|
]);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @private
|
* @private
|
||||||
@@ -150,10 +156,7 @@ goog.inherits(ol.renderer.webgl.TileLayer, ol.renderer.webgl.Layer);
|
|||||||
*/
|
*/
|
||||||
ol.renderer.webgl.TileLayer.prototype.disposeInternal = function() {
|
ol.renderer.webgl.TileLayer.prototype.disposeInternal = function() {
|
||||||
var mapRenderer = this.getWebGLMapRenderer();
|
var mapRenderer = this.getWebGLMapRenderer();
|
||||||
var gl = mapRenderer.getGL();
|
mapRenderer.deleteBuffer(this.arrayBuffer_);
|
||||||
if (!gl.isContextLost()) {
|
|
||||||
gl.deleteBuffer(this.arrayBuffer_);
|
|
||||||
}
|
|
||||||
goog.base(this, 'disposeInternal');
|
goog.base(this, 'disposeInternal');
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -188,7 +191,6 @@ ol.renderer.webgl.TileLayer.prototype.getTileLayer = function() {
|
|||||||
ol.renderer.webgl.TileLayer.prototype.handleWebGLContextLost = function() {
|
ol.renderer.webgl.TileLayer.prototype.handleWebGLContextLost = function() {
|
||||||
goog.base(this, 'handleWebGLContextLost');
|
goog.base(this, 'handleWebGLContextLost');
|
||||||
this.locations_ = null;
|
this.locations_ = null;
|
||||||
this.arrayBuffer_ = null;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
@@ -269,20 +271,7 @@ ol.renderer.webgl.TileLayer.prototype.renderFrame =
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
if (goog.isNull(this.arrayBuffer_)) {
|
mapRenderer.bindBuffer(goog.webgl.ARRAY_BUFFER, this.arrayBuffer_);
|
||||||
var arrayBuffer = gl.createBuffer();
|
|
||||||
gl.bindBuffer(goog.webgl.ARRAY_BUFFER, arrayBuffer);
|
|
||||||
gl.bufferData(goog.webgl.ARRAY_BUFFER, new Float32Array([
|
|
||||||
0, 0, 0, 1,
|
|
||||||
1, 0, 1, 1,
|
|
||||||
0, 1, 0, 0,
|
|
||||||
1, 1, 1, 0
|
|
||||||
]), goog.webgl.STATIC_DRAW);
|
|
||||||
this.arrayBuffer_ = arrayBuffer;
|
|
||||||
} else {
|
|
||||||
gl.bindBuffer(goog.webgl.ARRAY_BUFFER, this.arrayBuffer_);
|
|
||||||
}
|
|
||||||
|
|
||||||
gl.enableVertexAttribArray(this.locations_.aPosition);
|
gl.enableVertexAttribArray(this.locations_.aPosition);
|
||||||
gl.vertexAttribPointer(
|
gl.vertexAttribPointer(
|
||||||
this.locations_.aPosition, 2, goog.webgl.FLOAT, false, 16, 0);
|
this.locations_.aPosition, 2, goog.webgl.FLOAT, false, 16, 0);
|
||||||
|
|||||||
Reference in New Issue
Block a user