openlaleyrs实现动态样式
参考超图的案列,利用postrender事件监听重复触发方法,在方法中重设vectorContext的样式来实现。
官方示例:超图-动画要素图
官方对每个加入的feature都单独创建了postrender事件监听,然后在动画结束后销毁,但是如果要做循环播放的动画,事件就不能被销毁。随之而来的问题就是feature越多监听也越多,浏览器就会卡。
因此将代码逻辑简化,只设置了一个监听,方法中直接改变所有的要素样式。
改动代码如下:
var source = new ol.source.Vector({
wrapX: false
});
var fs = []
source.on('addfeature', function (e) {
//把添加的feature都放入一个数组中,之后循环对数组中的要素做动态效果,
//当然也可以从layer的source中去features,直接对全部要素做效果
fs.push(e.feature)
});
var vector = new ol.layer.Vector({
source: source
});
var r = 0
var isAdd = true
function flashAll(event){
// var duration = 3000;
// var start = new Date().getTime();
// var frameState = event.frameState;
// var elapsed = frameState.time - start;
// var elapsedRatio = elapsed / duration;
//使用全局变量r来控制半径很灵活,当然也可以用event.frameState.time来根据时间计算出一个值
var elapsedRatio = r;
if(isAdd){r=r+0.01}else{r=r-0.01}
if(r>=1 || r<=0)isAdd=!isAdd
for (var i=0 ;i<fs.length;i++){
var feature = fs[i];
// ol6 废除了 event.vectorContext 接口,通过 ol.render.getVectorContext 来获取 vectorContext
var vectorContext = new ol.render.getVectorContext(event);
var flashGeom = feature.getGeometry().clone();
//easing类的方法把输入的0到1的数字转换为渐进曲线上的新值,使得连续变化的数字有渐进效果
var radius = ol.easing.inAndOut(elapsedRatio) * 25 + 5;
var opacity = ol.easing.inAndOut(1 - elapsedRatio);
var style = new ol.style.Style({
image: new ol.style.Circle({
radius: radius,
stroke: new ol.style.Stroke({
color: 'rgba(255, 0, 0, ' + (opacity*0.5+0.5) + ')',
width: 0.25 + opacity
})
})
});
vectorContext.setStyle(style);
vectorContext.drawGeometry(flashGeom);
}
//重要,让postrender事件不断触发来不断地重绘要素style,从而实现动态变化的效果
map.render();
}
vector.on('postrender', flashAll);
map.addLayer(vector);
//这个方法是原案例中为图层添加随机feature的
window.setInterval(addRandomFeature, 1000);
效果:
记录一下原理,之后配合style就可以做各种效果了。