openlayers中地图中的标注点是可以通过多个图层叠加的方式来展现,比如说在WEB开发中,在一个容器中有很多个div盒子,这些盒子的背景颜色是全透明的,但是每个盒子的一部分区域可以写上自己想要的效果,再叠加到一起看起来就像是在一个div中实现的一样。openlayers中的图层大致可以理解成这个意思。
在Map对象上的layers这个option属性接收的是一个数组Array,这里面可以放置的图层就很多了,所以对于我们在操作就灵活很多。此处有疑问移步上篇# VueJS中的Openlayers渲染地图
Feature、Style设置标注点的两个构造方法
- Feature是为我们创建一个feature对象的构造方法,包含经纬度及其他自定义的属性。但是这个类仅仅是创建一个地图要素(feature),只是创建这个我们是看不到任何效果的,就像是我们在做web开发中,没有样式的html,效果是看不见的。所以需要为feature设置样式Style
- Style类就是为我们解决feature的样式问题,在openlayers中,可以设置基础的图形、文字,也可以使用自定义的图片,或者是两者的组合
比如图中北京市的标注是由文字和一个小圆点组合而成
实现一个点的标注
//导入ol标注相关的方法和属性
import Feature from "ol/Feature";
import { Point } from "ol/geom";
import {
Circle as CircleStyle,
RegularShape,
Fill,
Stroke,
Style,
Icon,
Text,
} from "ol/style";
export default{
data() {
return {
//在响应式数据中定义需要展现的图层
cityLayer: new VectorLayer({
name: "cityLayer",
source: new VectorSource({}),
style: null,
}),
};
},
}
- 初始化Map的时候在layers配置中,把
cityLayer这个图层加入进去,否则没有加载的图层不会显示
//创建点的标注实例和样式
renderPoint() {
let feature = new Feature({
geometry: new Point([116.405289, 39.904987]),//设置标注点的经纬度
name: "北京",
//可以写一些自定义的属性
});
//为feature设置样式
feature.setStyle(
new Style({
image: new CircleStyle({
radius: 5,
stroke: new Stroke({
color: "#fff",
}),
fill: new Fill({
color: "#3399CC",
}),
}),
text: new Text({
text: '北京-110',
textAlign: "center",
font: "14px PingFangSC-Regular",
offsetX: 0,
offsetY: -20,
padding: [6, 6, 3, 6],
backgroundStroke: new Stroke({
color: "rgba(0, 0, 0, 0)",
width: 1,
}),
backgroundFill: new Fill({
color: "rgba(0,194,233, 0.4)",
}),
fill: new Fill({
color: "rgba(255, 255, 255, 1)",
}),
}),
})
);
this.cityLayer.getSource().addFeatures([feature]);
}
实现地图标注全国各直辖市、省会等城市
在此之前需要用到一个基础的data数据,就是全国各主要城市的经纬度,大致结构是这样
const chinaData = [{ name: "北京", value: [116.405289, 39.904987]
},{
name: "天津",
value: [117.190186, 39.125595]
}]
创建features和设置style
renderFeatures() {
//清除该图层所有的feature要素
this.cityLayer.getSource().clear();
//创建features
let features = this.createFeature(chinaData);
//将features加入到图层中
this.cityLayer.getSource().addFeatures(features);
},
createFeature(chinaData) {
let features = [];
for (const city of chinaData) {
let feature = new Feature({
geometry: new Point(city.value),
name: city.name,
});
feature.setStyle(
new Style({
image: new CircleStyle({
radius: 5,
stroke: new Stroke({
color: "#fff",
}),
fill: new Fill({
color: "#3399CC",
}),
}),
text: new Text({
text: city.name,
textAlign: "center",
font: "14px PingFangSC-Regular",
offsetX: 0,
offsetY: -20,
padding: [6, 6, 3, 6],
backgroundStroke: new Stroke({
color: "rgba(0, 0, 0, 0)",
width: 1,
}),
backgroundFill: new Fill({
color: "rgba(0,194,233, 0.4)",
}),
fill: new Fill({
color: "rgba(255, 255, 255, 1)",
}),
}),
})
);
// feature.setStyle(createCommandNumberStyle(command))
features.push(feature);
}
return features;
},
几个实用API
- 1、setVisible 设置图层的显示隐藏,接收一个bool类型的参数
- 2、fit 自定义显示地图的缩放等级,地图的缩放等级和中心点在不确定的情况下,使用默认值显得不太合适,需要根据获取到的数据来确定这些值,这时,fit方法就派上用场了。具体使用
this.map.getView().fit([最小经度, 最小纬度, 最大经度, 最大纬度],{
size: this.map.getSize(),
maxZoom: 18,
duration: 1000,
padding: [150, 450, 350, 450]
});