mirror of
https://github.com/wanglin2/mind-map.git
synced 2026-02-21 10:27:44 +08:00
185 lines
3.9 KiB
Vue
185 lines
3.9 KiB
Vue
<template>
|
|
<div
|
|
v-if="showMiniMap"
|
|
class="navigatorBox"
|
|
:class="{ isDark: isDark }"
|
|
ref="navigatorBox"
|
|
:style="{ width: width + 'px' }"
|
|
@mousedown="onMousedown"
|
|
@mousemove="onMousemove"
|
|
@mouseup="onMouseup"
|
|
>
|
|
<div
|
|
class="svgBox"
|
|
ref="svgBox"
|
|
:style="{
|
|
transform: `scale(${svgBoxScale})`,
|
|
left: svgBoxLeft + 'px',
|
|
top: svgBoxTop + 'px'
|
|
}"
|
|
>
|
|
<img :src="mindMapImg" @mousedown.prevent />
|
|
</div>
|
|
<div class="windowBox" :style="viewBoxStyle"></div>
|
|
</div>
|
|
</template>
|
|
|
|
<script>
|
|
import { mapState } from 'vuex'
|
|
|
|
export default {
|
|
props: {
|
|
mindMap: {
|
|
type: Object
|
|
}
|
|
},
|
|
data() {
|
|
return {
|
|
showMiniMap: false,
|
|
timer: null,
|
|
boxWidth: 0,
|
|
boxHeight: 0,
|
|
svgBoxScale: 1,
|
|
svgBoxLeft: 0,
|
|
svgBoxTop: 0,
|
|
viewBoxStyle: {
|
|
left: 0,
|
|
top: 0,
|
|
bottom: 0,
|
|
right: 0
|
|
},
|
|
mindMapImg: '',
|
|
width: 0,
|
|
setSizeTimer: null
|
|
}
|
|
},
|
|
computed: {
|
|
...mapState({
|
|
isDark: state => state.localConfig.isDark
|
|
})
|
|
},
|
|
mounted() {
|
|
this.setSize()
|
|
window.addEventListener('resize', this.setSize)
|
|
this.$bus.$on('toggle_mini_map', this.toggle_mini_map)
|
|
this.$bus.$on('data_change', this.data_change)
|
|
this.$bus.$on('view_data_change', this.data_change)
|
|
this.$bus.$on('node_tree_render_end', this.data_change)
|
|
},
|
|
destroyed() {
|
|
window.removeEventListener('resize', this.setSize)
|
|
this.$bus.$off('toggle_mini_map', this.toggle_mini_map)
|
|
this.$bus.$off('data_change', this.data_change)
|
|
this.$bus.$off('view_data_change', this.data_change)
|
|
this.$bus.$off('node_tree_render_end', this.data_change)
|
|
},
|
|
methods: {
|
|
// 切换显示小地图
|
|
toggle_mini_map(show) {
|
|
this.showMiniMap = show
|
|
this.$nextTick(() => {
|
|
if (this.$refs.navigatorBox) {
|
|
this.init()
|
|
}
|
|
if (this.$refs.svgBox) {
|
|
this.drawMiniMap()
|
|
}
|
|
})
|
|
},
|
|
|
|
// 思维导图数据改变,更新小地图
|
|
data_change() {
|
|
if (!this.showMiniMap) {
|
|
return
|
|
}
|
|
clearTimeout(this.timer)
|
|
this.timer = setTimeout(() => {
|
|
this.drawMiniMap()
|
|
}, 500)
|
|
},
|
|
|
|
// 计算容器宽度
|
|
setSize() {
|
|
clearTimeout(this.setSizeTimer)
|
|
this.setSizeTimer = setTimeout(() => {
|
|
this.width = Math.min(window.innerWidth - 80, 370)
|
|
this.$nextTick(() => {
|
|
if (this.showMiniMap) {
|
|
this.init()
|
|
this.drawMiniMap()
|
|
}
|
|
})
|
|
}, 300)
|
|
},
|
|
|
|
// 获取宽高
|
|
init() {
|
|
let { width, height } = this.$refs.navigatorBox.getBoundingClientRect()
|
|
this.boxWidth = width
|
|
this.boxHeight = height
|
|
},
|
|
|
|
drawMiniMap() {
|
|
let {
|
|
getImgUrl,
|
|
viewBoxStyle,
|
|
miniMapBoxScale,
|
|
miniMapBoxLeft,
|
|
miniMapBoxTop
|
|
} = this.mindMap.miniMap.calculationMiniMap(this.boxWidth, this.boxHeight)
|
|
// 渲染到小地图
|
|
getImgUrl(img => {
|
|
this.mindMapImg = img
|
|
})
|
|
this.viewBoxStyle = viewBoxStyle
|
|
this.svgBoxScale = miniMapBoxScale
|
|
this.svgBoxLeft = miniMapBoxLeft
|
|
this.svgBoxTop = miniMapBoxTop
|
|
},
|
|
|
|
onMousedown(e) {
|
|
this.mindMap.miniMap.onMousedown(e)
|
|
},
|
|
|
|
onMousemove(e) {
|
|
this.mindMap.miniMap.onMousemove(e)
|
|
},
|
|
|
|
onMouseup(e) {
|
|
this.mindMap.miniMap.onMouseup(e)
|
|
}
|
|
}
|
|
}
|
|
</script>
|
|
|
|
<style lang="less" scoped>
|
|
.navigatorBox {
|
|
position: absolute;
|
|
height: 220px;
|
|
background-color: #fff;
|
|
bottom: 80px;
|
|
right: 70px;
|
|
box-shadow: 0 0 16px #989898;
|
|
border-radius: 4px;
|
|
border: 1px solid #eee;
|
|
cursor: pointer;
|
|
user-select: none;
|
|
|
|
&.isDark {
|
|
background-color: #262a2e;
|
|
}
|
|
|
|
.svgBox {
|
|
position: absolute;
|
|
left: 0;
|
|
transform-origin: left top;
|
|
}
|
|
|
|
.windowBox {
|
|
position: absolute;
|
|
border: 2px solid rgb(238, 69, 69);
|
|
transition: all 0.3s;
|
|
}
|
|
}
|
|
</style>
|