现在path:src/utils文件夹加入一个EsriConfig.js文件,我们将option和Modules移入进入然后导出。
并且在path:computents/Map/index文件中导入
import { Option, Modules } from "@/utils/EsriConfig";
此时,就将模块抽离开了。
注意,现在option成了大写
export const Option = {
url: "https://js.arcgis.com/4.15/init.js",
css: "https://js.arcgis.com/4.18/esri/themes/light/main.css"
};
export const Modules = [
"esri/Map",
"esri/Basemap",
"esri/views/MapView",
"esri/layers/BaseTileLayer",
"esri/Color",
"esri/request",
"esri/Graphic",
"esri/layers/GraphicsLayer",
"esri/layers/GeoJSONLayer",
"esri/layers/support/LabelClass",
"esri/widgets/BasemapGallery/BasemapGalleryViewModel",
"esri/views/draw/Draw",
"esri/widgets/Sketch/SketchViewModel",
"esri/widgets/ScaleBar",
];
这个一个同目录级别的文件,数据传递方式使用的是子传父。在里面就干一件事,点击传递切换。
<template>
<ul class="tool">
<li v-for="(item, index) in source" :key="index" @click.stop="togglelay(item)">
<img :src="item.image"> <span :class="item.checked ? 'active': ''">{{item.name}}</span>
</li>
</ul>
</template>
<script>
// import {} from ''
export default {
name: "basetogle",
data() {
return {
source: [
{checked: true, value: 'google_lay' ,name: "影像图层", image: require("@/assets/img/yingxiang.jpg")},
{checked: false, value: 'raster_lay', name: "地形图层", image: require("@/assets/img/dixing.jpg")},
{checked: false, value: 'tmts_lay', name: "地质图层", image: require("@/assets/img/dizhitu.png")},
]
};
},
mounted() {},
methods: {
togglelay(item) {
this.$emit('togle', item)
}
}
// End
};
</script>
<style lang='stylus' scoped>
.tool {
position: absolute;
top: 100px;
right: 60px;
background-color: #fff;
color: #c0c4cc;
font-size: 12px;
width: 120px;
height: 60px;
overflow: hidden;
transition: all 0.45s;
li {
transition: all 0.45s;
height: 60px;
width: 80px;
display: inline-block;
position: absolute;
right: 0px;
padding: 1px;
img {
width: 100%;
height: 100%;
}
span {
position: absolute;
bottom: 3px;
left: 3px;
}
.active {
color: #fff;
}
&:first-child {
right: 40px;
}
&:last-child {
right: -40px;
}
}
&:hover {
overflow: unset;
width: 220px;
transform-style: preserve-3d;
}
&:hover li:nth-child(1) {
right: 140px;
transform: translateZ(10px);
}
&:hover li:nth-child(2) {
right: 70px;
transform: translateZ(10px);
}
&:hover li:nth-child(3) {
right: 0px;
transform: translateZ(10px);
}
}
</style>
1. 导入模板后加入,并绑定好方法关系,在basetogle方法中使用的方式拿到所有图层。
2. 遍历过滤,在之前封装的天地图函数方法中我们有两个属性会用到它,visible 和baselayer 。为了防止加入的图层受到影响它会为我们做最好的判断。
//template
<basetogle @togle="basetogle" ref="basetogle"></basetogle> // 使用
// script
import basetogle from './basetogle' //导入
// 在methods方法中注册方法
basetogle(attr) {
if (this.$refs.basetogle.source) {
let source = this.$refs.basetogle.source;
source.forEach(k => {
if (attr.value === k.value) k.checked = true;
else k.checked = false;
});
}
新建一个子组件vue 模板,就叫bar吧。
这个组件什么事情也不做,双向绑定让他显示就行了。
<template>
<div id="mousePosition">
<span>经度:{{attr.x}}</span>
<span>纬度:{{attr.y}}</span>
</div>
</template>
<script>
// import {} from ''
export default {
name: "bar",
props: ['attr'],
mounted() {},
methods: {}
// End
};
</script>
<style lang='css' scoped>
div#mousePosition {
text-align: center;
width: 274px;
height: 30px;
background-color: rgba(40, 40, 40, 0.4);
position: absolute;
bottom: 10px;
left: 50%;
transform: translateX(-50%);
font-size: 12px;
color: white;
line-height: 30px;
}
div#mousePosition span:last-child {
margin-left: 20px;
}
</style>
//template
<bar :attr="mouse"></bar> // 使用
// script
import basetogle from './basetogle' //导入
import bar from './bar'
// data/return 注册数据
mouse: { x: '', y: '' },
// methods/init/Map 实例化之后
view.on('pointer-move', this.__MouseAttr)
// methods 注册
__MouseAttr(evt) {
this.mouse.x = view.toMap(evt).longitude.toFixed(6);
this.mouse.y = view.toMap(evt).latitude.toFixed(6);
}
// methods/init/Map 实例化之后
view.ui.add(this.scaleRuler, {position: 'bottom-left'})
// comput注册属性
scaleRuler() { // 比例尺
return new this.getEsri.ScaleBar({view, style: 'ruler', unit: 'metric'})
}
// methods/init/Map 实例化之后
view.ui.components = [];
// methods/init/Map 实例化之后
view.on(['click', 'double-click'], e => e.stopPropagation());
// 不过加入了这个会阻止事件传递,绘制矩形图形draw对象时候无法终止操作。arcgis用的不是很溜,体验也不好
// An highlighted block
<template>
<div class="Container">
<div id="map"></div>
<basetogle @togle="basetogle" ref="basetogle"></basetogle>
<bar :attr="mouse"></bar>
</div>
</template>
<script>
const option = {
url: "https://js.arcgis.com/4.15/init.js",
css: "https://js.arcgis.com/4.18/esri/themes/light/main.css"
};
const Modules = [
"esri/Map",
"esri/Basemap",
"esri/views/MapView",
"esri/request",
"esri/layers/BaseTileLayer",
];
let map, view;
import { loadModules } from "esri-loader";
import { Option, Modules } from "@/utils/EsriConfig";
import { mapState, mapMutations, mapGetters } from 'vuex'
import { TintLayer } from './Baselayer' // 导入自定义的天地图对象文件。
import basetogle from './basetogle'
import bar from './bar'
export default {
name: "index",
components: { bar, basetogle },
data() {
return {
mouse: { x: '', y: '' },
};
},
mounted() {
this.init();
},
methods: {
init() {
loadModules(Modules, option).then(this.setModule).then(this.initMap);
},
setModule(args) {
let esri = {};
for (let k in args) {
let name = Modules[k].split("/").pop();
esri[name] = args[k];
}
this.setEsri(esri);
},
initMap() {
const google_lay = TintLayer({
url: 'http://mt0.google.cn/vt/lyrs=t,r&hl=zh-CN&gl=cn&x={x}&y={y}&z={z}',
id: 'google_lay',
visible: true,
baselayer: true,
store: this.getEsri
});
const raster_lay = TintLayer({
url: 'http://mt0.google.cn/vt/lyrs=s@702&hl=zh-CN&gl=cn&x={x}&y={y}&z={z}&s=Ga',
id: 'raster_lay',
visible: false,
baselayer: true,
store: this.getEsri
});
const basemap = new this.esri.Basemap({ baseLayers: [google_lay, raster_lay] });
map = new this.esri.Map({ basemap });
view = new this.esri.MapView({
container: "map",
map,
center: [114, 30],
zoom: 6
});
view.on(['click', 'double-click'], e => e.stopPropagation()); // 清除默认双击放大事件
view.ui.add(this.scaleRuler, {position: 'bottom-left'})
view.ui.components = [];
view.on('pointer-move', this.__MouseAttr)
},
basetogle(attr) {
if (this.$refs.basetogle.source) {
let source = this.$refs.basetogle.source;
source.forEach(k => {
if (attr.value === k.value) k.checked = true;
else k.checked = false;
});
}
const layers = map.allLayers.items;
layers.forEach(v => {
if (attr.value === v.id && v.baselayer) v.visible = true;
else if (attr.value !== v.id && v.baselayer) v.visible = false;
})
},
__MouseAttr(evt) {
this.mouse.x = view.toMap(evt).longitude.toFixed(6);
this.mouse.y = view.toMap(evt).latitude.toFixed(6);
},
},
computed: {
scaleRuler() { // 比例尺
return new this.getEsri.ScaleBar({view, style: 'ruler', unit: 'metric'})
},
...mapState({
esri: state => state.map.esri,
}),
...mapGetters(['getEsri'])
},
// End
}
</script>
<style lang='stylus' scoped>
.Container {
width: 100%;
height: 100%;
#map {
width: 100%;
height: 100%;
}
}
</style>
可有有人会说地图和经纬度不是有ui微件吗,我只能说我喜欢按我的风格来设计。