Skip to content

Commit 858be3c

Browse files
authored
refactor(components): [tour] replace rect with path (element-plus#15315)
1 parent 30034a5 commit 858be3c

File tree

1 file changed

+47
-64
lines changed

1 file changed

+47
-64
lines changed

‎packages/components/tour/src/mask.vue‎

Lines changed: 47 additions & 64 deletions
Original file line numberDiff line numberDiff line change
@@ -3,14 +3,14 @@
33
v-if="visible"
44
:class="ns.e('mask')"
55
:style="({
6-
position: 'fixed',
7-
left: 0,
8-
right: 0,
9-
top: 0,
10-
bottom: 0,
11-
zIndex,
12-
pointerEvents: pos && targetAreaClickable ? 'none' : 'auto',
13-
} as any)"
6+
position: 'fixed',
7+
left: 0,
8+
right: 0,
9+
top: 0,
10+
bottom: 0,
11+
zIndex,
12+
pointerEvents: pos && targetAreaClickable ? 'none' : 'auto',
13+
} as any)"
1414
v-bind="$attrs"
1515
>
1616
<svg
@@ -19,62 +19,17 @@
1919
height: '100%',
2020
}"
2121
>
22-
<defs>
23-
<mask :id="maskId">
24-
<rect x="0" y="0" width="100vw" height="100vh" fill="white" />
25-
<rect
26-
v-if="pos"
27-
:class="ns.e('hollow')"
28-
:x="pos.left"
29-
:y="pos.top"
30-
:rx="pos.radius"
31-
:width="pos.width"
32-
:height="pos.height"
33-
fill="black"
34-
/>
35-
</mask>
36-
</defs>
37-
<rect
38-
x="0"
39-
y="0"
40-
width="100%"
41-
height="100%"
42-
:fill="fill"
43-
:mask="`url(#${maskId})`"
44-
/>
45-
<template v-if="pos">
46-
<rect v-bind="COVER_PROPS" x="0" y="0" width="100%" :height="pos.top" />
47-
<rect
48-
v-bind="COVER_PROPS"
49-
x="0"
50-
y="0"
51-
:width="pos.left"
52-
height="100%"
53-
/>
54-
<rect
55-
v-bind="COVER_PROPS"
56-
x="0"
57-
:y="pos.top + pos.height"
58-
width="100%"
59-
:height="`calc(100vh - ${pos.top + pos.height}px)`"
60-
/>
61-
<rect
62-
v-bind="COVER_PROPS"
63-
:x="pos.left + pos.width"
64-
y="0"
65-
:width="`calc(100vw - ${pos.left + pos.width}px)`"
66-
height="100%"
67-
/>
68-
</template>
22+
<path :class="ns.e('hollow')" :style="pathStyle" :d="path" />
6923
</svg>
7024
</div>
7125
</template>
7226

7327
<script setup lang="ts">
74-
import { inject, toRef } from 'vue'
75-
import { useId, useLockscreen } from '@element-plus/hooks'
28+
import { computed, inject, toRef } from 'vue'
29+
import { useLockscreen } from '@element-plus/hooks'
7630
import { maskProps } from './mask'
7731
import { tourKey } from './helper'
32+
import type { CSSProperties } from 'vue'
7833
7934
defineOptions({
8035
name: 'ElTourMask',
@@ -84,16 +39,44 @@ defineOptions({
8439
const props = defineProps(maskProps)
8540
8641
const { ns } = inject(tourKey)!
42+
const radius = computed(() => props.pos?.radius ?? 2)
43+
const roundInfo = computed(() => {
44+
const v = radius.value
45+
const baseInfo = `a${v},${v} 0 0 1`
46+
return {
47+
topRight: `${baseInfo} ${v},${v}`,
48+
bottomRight: `${baseInfo} ${-v},${v}`,
49+
bottomLeft: `${baseInfo} ${-v},${-v}`,
50+
topLeft: `${baseInfo} ${v},${-v}`,
51+
}
52+
})
8753
88-
const id = useId()
89-
const maskId = `el-tour-mask-${id.value}`
54+
const path = computed(() => {
55+
const width = window.innerWidth
56+
const height = window.innerHeight
57+
const info = roundInfo.value
58+
const _path = `M${width},0 L0,0 L0,${height} L${width},${height} L${width},0 Z`
59+
const _radius = radius.value
60+
return props.pos
61+
? `${_path} M${props.pos.left + _radius},${props.pos.top} h${
62+
props.pos.width - _radius * 2
63+
} ${info.topRight} v${props.pos.height - _radius * 2} ${
64+
info.bottomRight
65+
} h${-props.pos.width + _radius * 2} ${info.bottomLeft} v${
66+
-props.pos.height + _radius * 2
67+
} ${info.topLeft} z`
68+
: _path
69+
})
70+
71+
const pathStyle = computed<CSSProperties>(() => {
72+
return {
73+
fill: props.fill,
74+
pointerEvents: 'auto',
75+
cursor: 'auto',
76+
}
77+
})
9078
9179
useLockscreen(toRef(props, 'visible'), {
9280
ns,
9381
})
94-
95-
const COVER_PROPS = {
96-
fill: 'transparent',
97-
'pointer-events': 'auto',
98-
}
9982
</script>

0 commit comments

Comments
 (0)