越学习openlayer你会发现openlayer是真的很强大,今天记录一下学习的成果,需求是作那种室内的CAD的场景而后里面展现人员icon而且实时展现人员的位置信息,以及点击弹出对应人员的一些位置信息,姓名,电话等等,这个在工业互联网中是很常见的,接下来就开始操做了前端
因为我是在vue+ts中写的,因此下面的代码片断多是基于vue来写的vue
第一步,咱们须要创建一个底图,这个底图能够是谷歌地图也能够是咱们拿到的cad渲染出来的静态底图数组
let extent = [pointer.x, pointer.y, pointer2.x, pointer2.y]; // 图片图层四至
// pointer pointer2分别是静态图片左下角和右上角的基于基站的坐标
console.log(extent)
let projection = new olprojProjection({
code: "xkcd-image",
units: "pixels",
extent: extent
});
this.map = new olMap({
target: DOM接点的ID,
layers: [
new ollayerImage({
source: new olsourceImageStatic({
url: 静态图片的地址, // 静态地图,若是是本地的,在vuecli3中将图片放在public里
projection: projection,
imageExtent: extent // 映射到地图的范围
})
})
],
view: new olView({
center: getCenter(extent),
projection: projection,
zoom: 2.2,
minZoom: 1,
maxZoom: 12
}),
// 加载控件到地图容器中
// 加载鼠标位置控件
controls: defaults().extend([mousePositionControl])
});
第二步,底图创建好以后,接下来绘制人员图标,我这边和后台的数据对接方式是ws,就是后台实时推送人员的位置信息,前端渲染,这个时候很刚入学者会每一个icon创建一个layer,其实不是这样的,你能够先创建一个定位图层layer,一个layer一个source就能够了,学习
新建定位图层this
// 建立定位图层
this.positionLayer = new ollayerVector({
source: new olsourceVector(),
style: new olstyleStyle()
})
this.map.addLayer(this.positionLayer)
而后拿到数据以后,我这边获取的数据接口是一个list,也就是一个数组,须要for循环来添加iconurl
list.forEach((value: any, index: number) => {
let time = new Date().getTime()
if (!that.personListCache.has(value.id)) {
// 绘制人员定位信息
let personS = that.createPerson(value)
console.log(value)
console.log(personS)
that.personListCache.set(value.id, { spriteObj: personS, lastModified: time })
} else {
let personIn = that.personListCache.get(value.id)
// console.log(personIn.spriteObj.getGeometry().getCoordinates())
// var geometry = new olgeomPoint([value.x, value.y])
// personIn.spriteObj.setGeometry(geometry)
personIn.lastModified = time
if (personIn) {
personIn.oldObj = {
x: personIn.spriteObj.getGeometry().getCoordinates()[0],
y: personIn.spriteObj.getGeometry().getCoordinates()[1]
}
personIn.newObj = {
x: value.x,
y: value.y
}
if (personIn.oldObj.x === personIn.newObj.x && personIn.oldObj.y === personIn.newObj.y) {
// that.updataPersonPos(personIn)
} else {
that.updataPersonPos(personIn)
}
}
}
})
创建一个map的缘由是,后台不肯定是否会新增重复的人员给我,故创建一个map对象判断是否以及绘制在底图上,若是绘制在底图上了,那么只用改变他的位置也就是xy或者说是经纬度,若是没有就去调用createPerson方法去绘制iconspa
createPerson(value: any) {
var startMarker = new olFeature({
type: 'person',
msg: value,
geometry: new olgeomPoint([value.x, value.y])
})
let srcImg = value.type === 'type1' ? './images/type1.png' : value.type === 'type2' ? './images/type2.png' : './images/type3.png'
var startStyle = new olstyleStyle({
image: new olstyleIcon({
anchor: [0.5, 0.5],
scale: 0.3,
src: srcImg,
imgSize: [117, 158]
}),
text: new Text({
text: value.name,
// font: '14px font-size',
padding: [4, 7, 4, 7],
fill: new Fill({ color: '#fff' }),
backgroundFill: new Fill({ color: '#3737379e' }),
offsetY: -34
})
})
startMarker.setStyle(startStyle)
this.positionLayer.getSource().addFeature(startMarker)
return startMarker
}
注意红色部分,很关键,第一次的我是直接把startStyle放到了positionLayer上,致使绘制出来的全部的icon的信息都是同样的,至于上面的三目运算你们应该知道,icon的类型不同绘制出来的图标也是须要不同的3d
好了,自定义底图上添加静态icon就完成了,code
接下啦看看效果图吧,底图我随便换了一个静态图片,icon也是对象
索嘎,完工