是否可以为 LineString 的每个段设置不同的颜色而不会对性能造成巨大影响?
Is it possible to set different colors to each segment of a LineString without meeting a huge performance hit?
我的 openlayers 3 应用程序在地图上绘制了几个 LineString 特征(从几十个到 2000-3000 个)。
当为 LineStrings 的每个部分设置不同的颜色时,我遇到了巨大的性能损失(从地图上的几个 LineStrings 开始)。缩放和平移变得完全没有反应,使我的应用程序无法以这种形式使用。
由于我不想为每个段设置新的几何形状(而只是更改其颜色),我想必须有一种更有效的方法来实现这一点?
这是我的代码:
var styleFunction = function(feature, resolution) {
var i = 0, geometry = feature.getGeometry();
geometry.forEachSegment(function (start, end) {
color = colors[i];
styles.push(new ol.style.Style({
geometry: new ol.geom.LineString([start, end]),
fill: new ol.style.Fill({
color: color
}),
stroke: new ol.style.Stroke({
color: color,
width: 2
})
}));
i++;
});
return styles;
}
var vectorLayer = new ol.layer.Vector({
source: vectorSource,
style: styleFunction
});
您可以尝试优化以下几点:
缓存填充和描边样式
var fillStyles = colors.map(function(color, i) {
return new ol.style.Fill({
color: color
})
});
var strokeStyles = colors.map(function(color, i) {
return new ol.style.Stroke({
color: color,
width: 2
})
});
缓存每个功能的样式
vectorSource.forEach(function(feature, i) {
var geometry = feature.getGeometry();
var styles = [];
var i = 0;
geometry.forEachSegment(function (start, end) {
styles.push(new ol.style.Style({
geometry: new ol.geom.LineString([start, end]),
fill: fillStyles[i],
stroke: strokeStyles[i]
}));
i++;
});
feature.setStyle(styles);
});
禁用在动画和交互期间更新渲染
var vectorLayer = new ol.layer.Vector({
source: vectorSource,
updateWhileAnimating: false,
updateWhileInteracting: false
});
参见 ol.layer.Vector。
如果这些都没有帮助,您可能还想看看 ol.source.ImageVector(example)。
由于我们无法解决问题,即使有 tsauerwein 的建议,此功能也暂时搁置了。现在我们带着新的想法回到它并实际找到了 "solution"。
我在问题中没有说清楚的是,LineString 的段根据其起点的 属性 着色。如果这个 属性 的值在它们之间没有变化,那么几个连续的段可能因此共享相同的颜色。
我们的想法是避免为每个段创建新样式,而是仅在必要时(当颜色更改时)创建新样式:
let i = 0,
color = '#FE2EF7', //pink. should not be displayed
previousColor = '#FE2EF7',
lineString,
lastCoordinate = geometry.getLastCoordinate();
geometry.forEachSegment(((start, end) => {
color = this.getColorFromProperty(LinePoints[i].myProperty);
//First segment
if (lineString == null) {
lineString = new ol.geom.LineString([start, end]);
} else {
//Color changes: push the current segment and start a new one
if (color !== previousColor) {
styles.push(new ol.style.Style({
geometry: lineString,
fill: new ol.style.Fill({
color: previousColor
}),
stroke: new ol.style.Stroke({
color: previousColor,
width: 2
})
}));
lineString = new ol.geom.LineString([start, end]);
} else {
//Color is same: continue the current segment
lineString.appendCoordinate(end);
}
//Last segment
if (end[0] === lastCoordinate[0] && end[1] === lastCoordinate[1]) {
styles.push(new ol.style.Style({
geometry: lineString,
fill: new ol.style.Fill({
color: color
}),
stroke: new ol.style.Stroke({
color: color,
width: 2
})
}));
}
}
previousColor = color;
i++;
}
我的 openlayers 3 应用程序在地图上绘制了几个 LineString 特征(从几十个到 2000-3000 个)。
当为 LineStrings 的每个部分设置不同的颜色时,我遇到了巨大的性能损失(从地图上的几个 LineStrings 开始)。缩放和平移变得完全没有反应,使我的应用程序无法以这种形式使用。
由于我不想为每个段设置新的几何形状(而只是更改其颜色),我想必须有一种更有效的方法来实现这一点?
这是我的代码:
var styleFunction = function(feature, resolution) {
var i = 0, geometry = feature.getGeometry();
geometry.forEachSegment(function (start, end) {
color = colors[i];
styles.push(new ol.style.Style({
geometry: new ol.geom.LineString([start, end]),
fill: new ol.style.Fill({
color: color
}),
stroke: new ol.style.Stroke({
color: color,
width: 2
})
}));
i++;
});
return styles;
}
var vectorLayer = new ol.layer.Vector({
source: vectorSource,
style: styleFunction
});
您可以尝试优化以下几点:
缓存填充和描边样式
var fillStyles = colors.map(function(color, i) {
return new ol.style.Fill({
color: color
})
});
var strokeStyles = colors.map(function(color, i) {
return new ol.style.Stroke({
color: color,
width: 2
})
});
缓存每个功能的样式
vectorSource.forEach(function(feature, i) {
var geometry = feature.getGeometry();
var styles = [];
var i = 0;
geometry.forEachSegment(function (start, end) {
styles.push(new ol.style.Style({
geometry: new ol.geom.LineString([start, end]),
fill: fillStyles[i],
stroke: strokeStyles[i]
}));
i++;
});
feature.setStyle(styles);
});
禁用在动画和交互期间更新渲染
var vectorLayer = new ol.layer.Vector({
source: vectorSource,
updateWhileAnimating: false,
updateWhileInteracting: false
});
参见 ol.layer.Vector。
如果这些都没有帮助,您可能还想看看 ol.source.ImageVector(example)。
由于我们无法解决问题,即使有 tsauerwein 的建议,此功能也暂时搁置了。现在我们带着新的想法回到它并实际找到了 "solution"。
我在问题中没有说清楚的是,LineString 的段根据其起点的 属性 着色。如果这个 属性 的值在它们之间没有变化,那么几个连续的段可能因此共享相同的颜色。
我们的想法是避免为每个段创建新样式,而是仅在必要时(当颜色更改时)创建新样式:
let i = 0,
color = '#FE2EF7', //pink. should not be displayed
previousColor = '#FE2EF7',
lineString,
lastCoordinate = geometry.getLastCoordinate();
geometry.forEachSegment(((start, end) => {
color = this.getColorFromProperty(LinePoints[i].myProperty);
//First segment
if (lineString == null) {
lineString = new ol.geom.LineString([start, end]);
} else {
//Color changes: push the current segment and start a new one
if (color !== previousColor) {
styles.push(new ol.style.Style({
geometry: lineString,
fill: new ol.style.Fill({
color: previousColor
}),
stroke: new ol.style.Stroke({
color: previousColor,
width: 2
})
}));
lineString = new ol.geom.LineString([start, end]);
} else {
//Color is same: continue the current segment
lineString.appendCoordinate(end);
}
//Last segment
if (end[0] === lastCoordinate[0] && end[1] === lastCoordinate[1]) {
styles.push(new ol.style.Style({
geometry: lineString,
fill: new ol.style.Fill({
color: color
}),
stroke: new ol.style.Stroke({
color: color,
width: 2
})
}));
}
}
previousColor = color;
i++;
}