1、先上个图,来自官方:
2、说明:图形包括三个组件,一个是多边形、一个圆、一个text(A,B,C,D,E,F...)。
3、图形定义:
<svg width="200" height="200">
<PolyGraph :stats="stats"></PolyGraph>
</svg>
这个PolyGraph是一个自定义SFC:
<script setup>
import AxisLabel from './AxisLabel.vue'
import { computed } from 'vue'
import { valueToPoint } from './util.js'
const props = defineProps({
stats: Array
})
const points = computed(() => {
const total = props.stats.length
return props.stats
.map((stat, i) => {
const { x, y } = valueToPoint(stat.value, i, total)
return `${x},${y}`
})
.join(' ')
})
</script>
<template>
<g>
<polygon :points="points"></polygon>
<circle cx="100" cy="100" r="80"></circle>
<axis-label
v-for="(stat, index) in stats"
:stat="stat"
:index="index"
:total="stats.length"
>
</axis-label>
</g>
</template>
说明:定义一个props: stats是一个数组,points:方法是将值转为坐标,并且用' '空格连接,这个与SVG中的多边形的points是一致。
polygon:svg中显示多边形的关键词。
circle:svg中的圆,由圆心(cx,cy),及半径r组成。
axis-label:是一组text,是自定义SFC:
<script setup>
import { computed } from 'vue'
import { valueToPoint } from './util.js'
const props = defineProps({
stat: Object,
index: Number,
total: Number
})
const point = computed(() =>
valueToPoint(+props.stat.value + 10, props.index, props.total)
)
</script>
<template>
<text :x="point.x" :y="point.y">{{stat.label}}</text>
</template>
4、函数说明:
export function valueToPoint(value, index, total) {
const x = 0
const y = -value * 0.8
const angle = ((Math.PI * 2) / total) * index
const cos = Math.cos(angle)
const sin = Math.sin(angle)
const tx = x * cos - y * sin + 100
const ty = x * sin + y * cos + 100
return {
x: tx,
y: ty
}
}
说明:
angle:(Math.PI * 2) / total),将一个圆周,分成total分。
cos0:1
sin0:0
将value值,通过index ,来转换为对应的坐标,这个100与圆有关系,可以加以修改,这样就会平移不同的value。
5、最后官方地址:https://cn.vuejs.org/examples/#svg
可以亲自测试下,然后想一想。